Can you tell JSON.Net to serialize DateTime as Utc even if unspecified? Can you tell JSON.Net to serialize DateTime as Utc even if unspecified? asp.net asp.net

Can you tell JSON.Net to serialize DateTime as Utc even if unspecified?


Set DateTimeZoneHandling on JsonSerializerSettings to Utc. That will convert all dates to UTC before serializing them.

public void SerializeObjectDateTimeZoneHandling(){  string json = JsonConvert.SerializeObject(    new DateTime(2000, 1, 1, 1, 1, 1, DateTimeKind.Unspecified),    new JsonSerializerSettings    {      DateTimeZoneHandling = DateTimeZoneHandling.Utc    });  Assert.AreEqual(@"""2000-01-01T01:01:01Z""", json);}

Documentation: DateTimeZoneHandling setting


The response above totally works, and so I used that to create an attribute to convert an API response from PST to UTC.

First I needed to create a JsonConverter

public class UTCDateTimeConverter : Newtonsoft.Json.JsonConverter {    private TimeZoneInfo pacificZone = TimeZoneInfo.FindSystemTimeZoneById("Pacific Standard Time");    public override bool CanConvert(Type objectType) {        return objectType == typeof(DateTime);    }    public override object ReadJson(JsonReader reader, Type objectType, object existingValue, JsonSerializer serializer) {        if (reader.Value == null) return null;        var pacificTime = DateTime.Parse(reader.Value.ToString());        return TimeZoneInfo.ConvertTimeToUtc(pacificTime, pacificZone);    }    public override void WriteJson(JsonWriter writer, object value, JsonSerializer serializer) {        writer.WriteValue(TimeZoneInfo.ConvertTimeFromUtc((DateTime) value, pacificZone));    }}

Then I had to apply that to the properties that needed to be converted

public class Order{    [JsonConverter(typeof(UTCDateTimeConverter))]    public DateTime OrderDate {get;set;}}


As @dez mentioned in a comment, you can "mark" the DateTime objects as UTC directly in .net code right after LOADING them from DB and BEFORE serializing them:

var item = GetItemFromDb(...);// mark appropriate DateTime fields manually as neededitem.OrderDate = DateTime.SpecifyKind(item.OrderDate, DateTimeKind.Utc);// now it will be serialized to "2018-10-17T16:21:23.507Z" with the Z at the end// and javascript will parse it properly and convert to local timezone as needed