Specifying a custom DateTime format when serializing with Json.Net
You are on the right track. Since you said you can't modify the global settings, then the next best thing is to apply the JsonConverter
attribute on an as-needed basis, as you suggested. It turns out Json.Net already has a built-in IsoDateTimeConverter
that lets you specify the date format. Unfortunately, you can't set the format via the JsonConverter
attribute, since the attribute's sole argument is a type. However, there is a simple solution: subclass the IsoDateTimeConverter
, then specify the date format in the constructor of the subclass. Apply the JsonConverter
attribute where needed, specifying your custom converter, and you're ready to go. Here is the entirety of the code needed:
class CustomDateTimeConverter : IsoDateTimeConverter
{
public CustomDateTimeConverter()
{
base.DateTimeFormat = "yyyy-MM-dd";
}
}
If you don't mind having the time in there also, you don't even need to subclass the IsoDateTimeConverter. Its default date format is yyyy'-'MM'-'dd'T'HH':'mm':'ss.FFFFFFFK
(as seen in the source code).
System.Text.Json Custom JsonConverterDateTime .Read() method not being used by .Deserialize()
The reason for this is that the name of the class property and the name of the Json property are different:
"sortDate": "2019-09-20T11:59:59.999"
And
public DateTime sort_date { get; set; }
In order to deserialize that json, you need to either make the names the same, or tell the serializer what to do by adding an attribute to tell what the equivalent name is:
// For NewtonSoft.Json
// [JsonProperty("sortDate")]
// For System.Text.Json
[JsonPropertyName("sortDate")]
public DateTime sort_date { get; set; }
Once that is added your sample code runs correctly:
How to format dd/MM/yyyy to date? c# .NetCore
Finally, I was able to correct it by adding these two lines of code to my Startup:
services.AddControllers().AddNewtonsoftJson(options =>
{
options.SerializerSettings.DateTimeZoneHandling = Newtonsoft.Json.DateTimeZoneHandling.Utc;
options.SerializerSettings.DateFormatString = "dd/MM/yyyy";
});
With that it was solved since within my api there was already a DateTimeConverter.
Thank you very much to all!
asp .net core 6 how to update option for json serialization. Date format in Json serialization
We can try to use builder.Services.Configure<JsonOptions>
to set our Serializer setting in DI container from .net core 6
JsonOptions
let us configure JSON serialization settings, which might instead AddJsonOptions
method.
JsonOptions
might use same as JsonOptions
object from DI in the SourceCode.
using Microsoft.AspNetCore.Http.Json;
builder.Services.Configure<JsonOptions>(options =>
{
options.SerializerOptions.Converters.Add(new DateTimeConverterForCustomStandardFormatR());
});
I think this change is based on Microsoft wanting to introduce minimal web API with ASP.NET Core in .net 6
Minimal APIs are architected to create HTTP APIs with minimal dependencies. They are ideal for microservices and apps that want to include only the minimum files, features, and dependencies in ASP.NET Core.
System.Text.Json.Serialization.JsonConverterDateTime is executed for nullable DateTime properties as well
After adding also a System.Text.Json.Serialization.JsonConverter<DateTime?>
class it seems that the non-nullable version was not hit anymore.
System.FormatException: The JSON value is not in a supported DateTimeOffset format
Implementing custon JSON behaviours with System.Text.Json
is usually done with custom converters. Unfortunately there aren't many provided out the box for different date formats, so if you need to deserialise something not in the default ISO 8601-1:2019
format you need to roll your own.
Forutnately that's not very difficult:
using System.Text.Json;
using System.Text.Json.Serialization;
public class DateTimeOffsetConverterUsingDateTimeParse : JsonConverter<DateTimeOffset >
{
public override DateTimeOffset Read(ref Utf8JsonReader reader, Type typeToConvert, JsonSerializerOptions options)
{
Debug.Assert(typeToConvert == typeof(DateTimeOffset));
return DateTimeOffset .Parse(reader.GetString());
}
public override void Write(Utf8JsonWriter writer, DateTimeOffset value, JsonSerializerOptions options)
{
writer.WriteStringValue(value.ToString());
}
}
This way you'll the same behaviour you do when you use DateTimeOffset.Parse()
.
You can use it like this
public record TestType(DateTimeOffset CreationDate);
public class Program
{
public static void Main(string[] args)
{
JsonSerializerOptions options = new JsonSerializerOptions();
options.Converters.Add(new DateTimeOffsetConverterUsingDateTimeParse());
var testType = JsonSerializer.Deserialize<TestType>(@"{ ""CreationDate"": ""2021-03-17T12:03:14+0000"" }",options);
Console.WriteLine(testType.CreationDate);
}
}
Related Topics
How to Implement "Access-Control-Allow-Origin" Header in ASP.NET
Reasons for Why a Winforms Label Does Not Want to Be Transparent
C#: How to Create an Attribute on a Method Triggering an Event When It Is Invoked
How to Split an Ienumerable<String> into Groups of Ienumerable<String>
C# Getting Value of Params Using Reflection
Reading a Binary File and Using Response.Binarywrite()
Running Async Methods in Parallel
Select Either a File or Folder from the Same Dialog in .Net
Exceptions That Can't Be Caught by Try-Catch Block in Application Code
How to Export a Gridview.Datasource to a Datatable or Dataset
Datagridview Changing Cell Background Color
How to Calculate the Average Rgb Color Values of a Bitmap
How to Secure Passwords Stored Inside Web.Config
Why Doesn't the Xmlserializer Need the Type to Be Marked [Serializable]