Reputation: 1070
I have a .NET minimal API project, as described here. One of the endpoints accepts JSON in the request body, and this is deserialized automatically. The code looks something like this:
app.MapPost("/myendpoint", async (MyInputFromBody input) => { ... });
This works in general, but I would like to specify options for deserialization. For instance, the JSON has some date fields such as "myDate": "2021-04-01T06:00:00"
, which can be converted to a DateTime, but an empty date value "myDate": ""
throws an exception (System.FormatException: The JSON value is not in a supported DateTime format.).
I found a suggestion to write my own DateTime converter and use this:
builder.Services.AddControllers()
.AddJsonOptions(options => options.JsonSerializerOptions.Converters.Add(new JsonDateTimeConverter()));
but this doesn't seem to do anything. A breakpoint in my converter is never hit, and I get the same exception as before.
Is there a way to specify JSON options, or should I use a string parameter, as in [FromBody] string body
, and parse that myself?
Upvotes: 9
Views: 6460
Reputation: 1140
From documentation
By default, minimal API apps use Web defaults options during JSON serialization and deserialization.
You can find how to adjust this configuration using builder.Services.ConfigureHttpJsonOptions
You can use also :
builder.Services.Configure<Microsoft.AspNetCore.Http.Json.JsonOptions>(options =>
{
options.SerializerOptions
});
Note that
JsonOptions
should come from Microsoft.AspNetCore.Http.Json
and not from Mvc
... otherwise not for minimal APIMicrosoft.AspNetCore.Http.Json
uses System.Text.Json
AddJsonOptions
for IMvcBuilder
using System.Text.Json
not for minimal APIAddNewtonsoftJson
for IMvcBuilder
using Newtonsoft.Json
not for minimal APIAddControllers
returns IMvcBuilder
.Upvotes: 9
Reputation: 320
In my .NET 8 minimal API, JsonOptions
wasn't installed by default, so I couldn't call services.Configure<JsonOptions>(x => ...)
.
For anyone else having this problem, installing Microsoft.AspNetCore.Http.Extensions
resolved it for me. I could then call services.Configure<JsonOptions>(x => ...)
in the normal way, as described above.
Upvotes: 0
Reputation: 8830
I put these in my Program.cs ignore the actual configs they may not be for you.
Minimal APIs .net 8 - do not use AddNewtonsoftJson
builder.Services.Configure<JsonOptions>(options =>
{
//options.SerializerOptions.Converters.Add(new TimeSpanConverter());
//options.SerializerOptions.Converters.Add(new JsonDateTimeConverter());
options.SerializerOptions.ReferenceHandler = ReferenceHandler.Preserve;
options.SerializerOptions.MaxDepth = 1000;
});
NewtonsoftJson Options non Minimal APIs
builder.Services.AddControllersWithViews().AddNewtonsoftJson(options =>
{
options.SerializerSettings.ReferenceLoopHandling = ReferenceLoopHandling.Ignore;
}
);
MicrosoftJson Options non Minimal API
builder.Services.AddControllers().AddJsonOptions(options =>
{
options.JsonSerializerOptions.ReferenceHandler = ReferenceHandler.IgnoreCycles;
options.JsonSerializerOptions.MaxDepth = 100;
options.JsonSerializerOptions.IgnoreNullValues = true;
options.JsonSerializerOptions.Converters.Add(new TimeSpanConverter());
}
);
Upvotes: 1
Reputation: 1850
AddControllers().AddJsonOptions
is configuring for your controllers, To configure for Minimal api
all you have to do is:
builder.Services.Configure<JsonOptions>(options => options.SerializerOptions.Converters.Add(new JsonDateTimeConverter()));
ASP.NET Core supports two approaches to creating APIs: a controller-based approach and minimal APIs. Controllers in an API project are classes that derive from ControllerBase. Minimal APIs define endpoints with logical handlers in lambdas or methods. This article points out differences between the two approaches.
Upvotes: 6