Chr*_*ken 7 c# datetime json.net xamarin.android xamarin
我正在使用JSON.Net来序列化DTO,我在物理设备上遇到以下异常.这适用于我们测试过的所有其他设备,但在Samsung Galaxy Tab 3lite SM-T110运行版本4.2.2 上失败.
我遇到了这个问题但是当我升级到Xamarin 3.0时,它变成了以下内容:
06-03 21:17:41.687 E/mono-rt (22071): [ERROR] FATAL UNHANDLED EXCEPTION: System.TimeZoneNotFoundException: Exception of type 'System.TimeZoneNotFoundException' was thrown.
06-03 21:17:41.687 E/mono-rt (22071): at System.TimeZoneInfo.get_Local () [0x00000] in <filename unknown>:0
06-03 21:17:41.687 E/mono-rt (22071): at Newtonsoft.Json.Utilities.DateTimeUtils.GetUtcOffset (DateTime d) [0x00000] in <filename unknown>:0
06-03 21:17:41.687 E/mono-rt (22071): at Newtonsoft.Json.Utilities.DateTimeUtils.WriteDateTimeString (System.Char[] chars, Int32 start, DateTime value, Nullable`1 offset, DateTimeKind kind, DateFormatHandling format) [0x00000] in <filename unknown>:0
06-03 21:17:41.687 E/mono-rt (22071): at Newtonsoft.Json.JsonTextWriter.WriteValue (DateTime value) [0x00000] in <filename unknown>:0
06-03 21:17:41.687 E/mono-rt (22071): at Newtonsoft.Json.JsonWriter.WriteValue (Newtonsoft.Json.JsonWriter writer, PrimitiveTypeCode typeCode, System.Object value) [0x00000] in <filename unknown>:0
06-03 21:17:41.687 E/mono-rt (22071): at Newtonsoft.Json.Serialization.JsonSerializerInternalWriter.SerializePrimitive (Newtonsoft.Json.JsonWriter writer, System.Object value, Newtonsoft.Json.Serialization.JsonPrimitiveContract contract, Newtonsoft.Json.Serialization.
06-03 21:17:41.695 I/mono-stdout(22071): Executing Command: UpdateRegistration
The program 'Mono' has exited with code 0 (0x0).
Run Code Online (Sandbox Code Playgroud)
编辑这是我试图序列化的DTO.您可以看到构造函数被调用的时间,它将其设置为DateTime.Now.难道这只是假设当地时区?
public class RecordTargetFrequency : BaseCommand, ICommand {
public Guid TargetId { get; private set; }
public Guid? LocationId { get; private set; }
public Guid TherapistId { get; private set; }
public bool? Increase { get; private set; }
public DateTime TimeStamp { get; private set; }
public RecordTargetFrequency(Guid targetId, Guid? locationId, Guid therapistId, bool? increase) {
TimeStamp = DateTime.Now;
TargetId = targetId;
LocationId = locationId;
TherapistId = therapistId;
Increase = increase;
}
public void Validate() {
ValidateGuid(TargetId);
ValidateGuid(TherapistId);
}
}
Run Code Online (Sandbox Code Playgroud)
然后我用这一行序列化它:
JsonConvert.SerializeObject(executedCommand);
Run Code Online (Sandbox Code Playgroud)
是的,TimeZoneInfo.Local在Mono上有些不妥.我在这里看到了三种不同的故障模式:
我没有一个很好的解决方案,但是如果你想记录一个时间戳,那么DateTime.UtcNow无论如何都要使用它会更好.那你根本不需要担心时区.在大多数情况下,您应该只是按时间存储和处理日期/时间值,而不关心时区甚至涉及哪个日历.
如果您可以获得时区ID,Java.Util.TimeZone.Default您可以America/New_York在此处获取 - 然后另一种方法是使用我的Noda Time项目,其中包括IANA数据库.所以你可以创建一个ZonedDateTime代表你所需要的东西.我们也支持Json.NET序列化,因此该部分不应成为问题.
但是,我鼓励你只使用UTC,除非你真的需要当地时间.
还有几个选项 - 您可能需要考虑使用DateTimeOffset而不是DateTime; 如果您只是尝试将值序列化为"带有UTC偏移的日期和时间",那么DateTimeOffset.Now可能会完全按照您的要求进行操作.
(如果这些都没有帮助,请提供更多关于您需要什么以及您希望JSON看起来像什么的背景信息.)