I have an endpoint that returns an IAsyncEnumerable
[HttpPost("GetByDates")]
[ProducesResponseType(typeof(IAsyncEnumerable<DayModel>), StatusCodes.Status200OK)]
public async IAsyncEnumerable<DayModel> GetByDates([FromBody] DayModelGetByDatesRequest request)
{
await foreach (var dayModel in _dayService.GetAsync(request.channelGuid, request.dates.ToArray(), request.onlyPublished, request.IncludeDiscardedScheduledItems))
{
yield return dayModel;
};
}
The generated .json schema looks like this:
"/Private/Days/GetByDates": {
"post": {
"tags": [
"Days"
],
"operationId": "Days_GetByDates",
"requestBody": {
"x-name": "request",
"content": {
"application/json": {
"schema": {
"$ref": "#/components/schemas/DayModelGetByDatesRequest"
}
}
},
"required": true,
"x-position": 1
},
"responses": {
"200": {
"description": "",
"content": {
"application/json": {
"schema": {
"type": "array",
"items": {
"$ref": "#/components/schemas/Day"
}
}
}
}
}
}
}
}
and the Nswag is configured like this:
services.AddOpenApiDocument(configure =>
{
configure.Title = "MyAppName (Private)";
configure.DocumentName = "private";
configure.SchemaType = SchemaType.OpenApi3;
configure.SchemaNameGenerator = new CustomNameGenerator();
configure.AddOperationFilter(new RequireUserHeaderParameterFilter().Process);
configure.AddSecurity("Bearer", new OpenApiSecurityScheme()
{
In = OpenApiSecurityApiKeyLocation.Header,
Description = "Please enter the word \"Bearer\" followed by space and token",
Name = "Authorization",
Type = OpenApiSecuritySchemeType.ApiKey,
});
configure.ApiGroupNames = new string[] { "Private" };
});
And another project uses the .json schema to genereate a client of its own that seems to use Newtonsoft Json instead of System.Text.Json
[System.CodeDom.Compiler.GeneratedCode("NSwag", "13.18.0.0 (NJsonSchema v10.8.0.0 (Newtonsoft.Json v13.0.0.0))")]
public partial class TablaApiClient
{
private string _baseUrl = "https://localhost:5102";
private System.Net.Http.HttpClient _httpClient;
private System.Lazy<Newtonsoft.Json.JsonSerializerSettings> _settings;
public TablaApiClient(System.Net.Http.HttpClient httpClient)
{
_httpClient = httpClient;
_settings = new System.Lazy<Newtonsoft.Json.JsonSerializerSettings>(CreateSerializerSettings);
}
private Newtonsoft.Json.JsonSerializerSettings CreateSerializerSettings()
{
var settings = new Newtonsoft.Json.JsonSerializerSettings();
UpdateJsonSerializerSettings(settings);
return settings;
}
public string BaseUrl
{
get { return _baseUrl; }
set { _baseUrl = value; }
}
protected Newtonsoft.Json.JsonSerializerSettings JsonSerializerSettings { get { return _settings.Value; } }
partial void UpdateJsonSerializerSettings(Newtonsoft.Json.JsonSerializerSettings settings);
The endpoint doesn't serialize the IAsyncEnumerable and return an ICollection instead:
The Swagger is configured like so:
services.AddOpenApiDocument(configure =>
{
configure.Title = "My App";
configure.SchemaType = NJsonSchema.SchemaType.OpenApi3;
configure.AddSecurity("AzureAsIdentityProvider", new OpenApiSecurityScheme
{
Type = OpenApiSecuritySchemeType.OAuth2,
Flows = new OpenApiOAuthFlows
{
AuthorizationCode = new OpenApiOAuthFlow
{
AuthorizationUrl = $"{settings.Instance}/{settings.TenantId}/oauth2/v2.0/authorize",
TokenUrl = $"{settings.Instance}/{settings.TenantId}/oauth2/v2.0/token",
}
}
});
configure.OperationProcessors.Add(new AspNetCoreOperationSecurityScopeProcessor("AzureAsIdentityProvider"));
});
Is there a way for the generated client to properly serialize and understand it is working towards an IAsyncEnumerable endpoint so that I can work with the stream instead of fully buffered collection?
I read that System.Text.Json serializes IAsyncEnumerable out of the box. Is there a way to get Swagger to use that instead of Newtonsoft?