forked from ddrilling/AsbCloudServer
SubsystemOperationTimeRequest implements IValidatableObject;
Add Controller.ValidationBadRequest(..)
This commit is contained in:
parent
ab166487fb
commit
772360cb6e
@ -1,4 +1,4 @@
|
|||||||
using AsbCloudApp.ValidationAttributes;
|
using AsbCloudApp.Validation;
|
||||||
using System;
|
using System;
|
||||||
using System.ComponentModel.DataAnnotations;
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
|
||||||
|
@ -22,25 +22,5 @@ namespace AsbCloudApp.Exceptions
|
|||||||
{
|
{
|
||||||
ParamName = paramName;
|
ParamName = paramName;
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// преобразование в объект валидации
|
|
||||||
/// </summary>
|
|
||||||
/// <returns></returns>
|
|
||||||
public object ToValidationErrorObject()
|
|
||||||
=> MakeValidationError(ParamName, Message);
|
|
||||||
|
|
||||||
/// <summary>
|
|
||||||
/// фабрика объекта валидации
|
|
||||||
/// </summary>
|
|
||||||
/// <param name="paramName"></param>
|
|
||||||
/// <param name="errors"></param>
|
|
||||||
/// <returns></returns>
|
|
||||||
public static object MakeValidationError(string paramName, params string[] errors)
|
|
||||||
=> new
|
|
||||||
{
|
|
||||||
name = paramName,
|
|
||||||
errors,
|
|
||||||
};
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using AsbCloudApp.ValidationAttributes;
|
using AsbCloudApp.Validation;
|
||||||
using System;
|
using System;
|
||||||
|
|
||||||
namespace AsbCloudApp.Requests;
|
namespace AsbCloudApp.Requests;
|
||||||
|
@ -1,23 +1,27 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.Collections.Generic;
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel.DataAnnotations;
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
using System.Linq;
|
||||||
|
|
||||||
namespace AsbCloudApp.Requests
|
namespace AsbCloudApp.Requests
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// класс с фильтрами для запроса
|
/// класс с фильтрами для запроса
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public class SubsystemOperationTimeRequest: RequestBase
|
public class SubsystemOperationTimeRequest: RequestBase, IValidatableObject
|
||||||
{
|
{
|
||||||
|
private static readonly DateTime validationMinDate = new DateTime(2020,01,01,0,0,0,DateTimeKind.Utc);
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// идентификатор скважины
|
/// идентификатор скважины
|
||||||
/// </summary>
|
/// </summary>
|
||||||
[Required]
|
[Required]
|
||||||
public int IdWell { get; set; }
|
public int IdWell { get; set; }
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// идентификатор подсистемы
|
/// идентификатор подсистемы
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public IEnumerable<int>? IdsSubsystems { get; set; }
|
public IEnumerable<int> IdsSubsystems { get; set; } = Enumerable.Empty<int>();
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Больше или равно дате
|
/// Больше или равно дате
|
||||||
@ -58,5 +62,32 @@ namespace AsbCloudApp.Requests
|
|||||||
/// Режим выборки элементов
|
/// Режим выборки элементов
|
||||||
/// </summary>
|
/// </summary>
|
||||||
public int SelectMode { get; set; } = SelectModeOuter;
|
public int SelectMode { get; set; } = SelectModeOuter;
|
||||||
|
|
||||||
|
/// <inheritdoc/>
|
||||||
|
public IEnumerable<ValidationResult> Validate(ValidationContext validationContext)
|
||||||
|
{
|
||||||
|
if (GtDate.HasValue && GtDate < validationMinDate)
|
||||||
|
yield return new ValidationResult(
|
||||||
|
$"Должно быть больше {validationMinDate:O})",
|
||||||
|
new[] { nameof(GtDate) });
|
||||||
|
|
||||||
|
if (LtDate.HasValue && GtDate.HasValue)
|
||||||
|
{
|
||||||
|
if (LtDate < GtDate)
|
||||||
|
yield return new ValidationResult(
|
||||||
|
$"{nameof(LtDate)} должно быть больше {nameof(GtDate)}. ({LtDate:O} < {GtDate:O})",
|
||||||
|
new[] { nameof(LtDate), nameof(GtDate) });
|
||||||
|
}
|
||||||
|
|
||||||
|
if (LtDepth.HasValue && GtDepth.HasValue)
|
||||||
|
{
|
||||||
|
if (LtDepth < GtDepth)
|
||||||
|
yield return new ValidationResult(
|
||||||
|
$"{nameof(LtDepth)} должно быть больше {nameof(GtDepth)}. ({LtDepth:O} < {GtDepth:O})",
|
||||||
|
new[] { nameof(LtDepth), nameof(GtDepth) });
|
||||||
|
}
|
||||||
|
|
||||||
|
yield break;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,7 +1,7 @@
|
|||||||
using System;
|
using System;
|
||||||
using System.ComponentModel.DataAnnotations;
|
using System.ComponentModel.DataAnnotations;
|
||||||
|
|
||||||
namespace AsbCloudApp.ValidationAttributes
|
namespace AsbCloudApp.Validation
|
||||||
{
|
{
|
||||||
/// <summary>
|
/// <summary>
|
||||||
/// Атрибут валидации даты-времени
|
/// Атрибут валидации даты-времени
|
@ -345,7 +345,7 @@ namespace AsbCloudInfrastructure.Services.Subsystems
|
|||||||
.Where(o => o.IdTelemetry == well.IdTelemetry)
|
.Where(o => o.IdTelemetry == well.IdTelemetry)
|
||||||
.AsNoTracking();
|
.AsNoTracking();
|
||||||
|
|
||||||
if (request.IdsSubsystems?.Any() == true)
|
if (request.IdsSubsystems.Any())
|
||||||
query = query.Where(o => request.IdsSubsystems.Contains(o.IdSubsystem));
|
query = query.Where(o => request.IdsSubsystems.Contains(o.IdSubsystem));
|
||||||
|
|
||||||
// # Dates range condition
|
// # Dates range condition
|
||||||
|
@ -1,4 +1,4 @@
|
|||||||
using AsbCloudApp.ValidationAttributes;
|
using AsbCloudApp.Validation;
|
||||||
using System;
|
using System;
|
||||||
using Xunit;
|
using Xunit;
|
||||||
|
|
||||||
|
@ -119,10 +119,10 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
return Forbid();
|
return Forbid();
|
||||||
|
|
||||||
if (files.Count > 1)
|
if (files.Count > 1)
|
||||||
return BadRequest(ArgumentInvalidException.MakeValidationError(nameof(files), "only 1 file can be uploaded"));
|
throw new ArgumentInvalidException("only 1 file can be uploaded", nameof(files));
|
||||||
|
|
||||||
if (files.Count == 0)
|
if (files.Count == 0)
|
||||||
return BadRequest(ArgumentInvalidException.MakeValidationError(nameof(files), "at list 1 file should be uploaded"));
|
throw new ArgumentInvalidException("at list 1 file should be uploaded", nameof(files));
|
||||||
|
|
||||||
var fileName = files[0].FileName;
|
var fileName = files[0].FileName;
|
||||||
|
|
||||||
|
@ -83,18 +83,14 @@ public class NotificationController : ControllerBase
|
|||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
[HttpGet("{idNotification}")]
|
[HttpGet("{idNotification}")]
|
||||||
[ProducesResponseType(typeof(NotificationDto), (int)System.Net.HttpStatusCode.OK)]
|
[ProducesResponseType(typeof(NotificationDto), (int)System.Net.HttpStatusCode.OK)]
|
||||||
public async Task<IActionResult> GetAsync([Required] int idNotification,
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
|
public async Task<IActionResult> GetAsync([Required] int idNotification,
|
||||||
CancellationToken cancellationToken)
|
CancellationToken cancellationToken)
|
||||||
{
|
{
|
||||||
var notification = await notificationRepository.GetOrDefaultAsync(idNotification, cancellationToken);
|
var notification = await notificationRepository.GetOrDefaultAsync(idNotification, cancellationToken)
|
||||||
|
?? throw new ArgumentInvalidException("Уведомление не найдено", nameof(idNotification));
|
||||||
|
|
||||||
if (notification is null)
|
return Ok(notification);
|
||||||
{
|
|
||||||
return BadRequest(ArgumentInvalidException.MakeValidationError(nameof(idNotification),
|
|
||||||
"Уведомление не найдено"));
|
|
||||||
}
|
|
||||||
|
|
||||||
return Ok(notification);
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/// <summary>
|
/// <summary>
|
||||||
|
@ -128,7 +128,7 @@ namespace AsbCloudWebApi.Controllers.SAUB
|
|||||||
public async Task<IActionResult> ExportAsync(int? idWell, int? idCluster, CancellationToken token)
|
public async Task<IActionResult> ExportAsync(int? idWell, int? idCluster, CancellationToken token)
|
||||||
{
|
{
|
||||||
if (idCluster is null && idWell is null)
|
if (idCluster is null && idWell is null)
|
||||||
return this.MakeBadRequest(nameof(idWell), $"One of {nameof(idWell)} or {nameof(idCluster)} mast be set.");
|
return this.ValidationBadRequest(nameof(idWell), $"One of {nameof(idWell)} or {nameof(idCluster)} mast be set.");
|
||||||
|
|
||||||
int? idCompany = User.GetCompanyId();
|
int? idCompany = User.GetCompanyId();
|
||||||
|
|
||||||
|
@ -1,5 +1,6 @@
|
|||||||
using AsbCloudApp.Data;
|
using AsbCloudApp.Data;
|
||||||
using AsbCloudApp.Data.Subsystems;
|
using AsbCloudApp.Data.Subsystems;
|
||||||
|
using AsbCloudApp.Exceptions;
|
||||||
using AsbCloudApp.Requests;
|
using AsbCloudApp.Requests;
|
||||||
using AsbCloudApp.Services;
|
using AsbCloudApp.Services;
|
||||||
using AsbCloudApp.Services.Subsystems;
|
using AsbCloudApp.Services.Subsystems;
|
||||||
@ -50,12 +51,12 @@ namespace AsbCloudWebApi.Controllers.Subsystems
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
[HttpGet("stat")]
|
[HttpGet("stat")]
|
||||||
[ProducesResponseType(typeof(IEnumerable<SubsystemStatDto>), (int)System.Net.HttpStatusCode.OK)]
|
[ProducesResponseType(typeof(IEnumerable<SubsystemStatDto>), (int)System.Net.HttpStatusCode.OK)]
|
||||||
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
public async Task<IActionResult> GetStatAsync([FromQuery] SubsystemOperationTimeRequest request, CancellationToken token)
|
public async Task<IActionResult> GetStatAsync([FromQuery] SubsystemOperationTimeRequest request, CancellationToken token)
|
||||||
{
|
{
|
||||||
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
||||||
return Forbid();
|
return Forbid();
|
||||||
if (!await IsValidRequest(request, token))
|
await CustomValidate(request, token);
|
||||||
return BadRequest("Запрашиваемый диапазон должен заканчиваться за 2 часа до текущего времени(после приведения к UTC).");
|
|
||||||
var subsystemResult = await subsystemOperationTimeService.GetStatAsync(request, token);
|
var subsystemResult = await subsystemOperationTimeService.GetStatAsync(request, token);
|
||||||
return Ok(subsystemResult);
|
return Ok(subsystemResult);
|
||||||
}
|
}
|
||||||
@ -125,15 +126,14 @@ namespace AsbCloudWebApi.Controllers.Subsystems
|
|||||||
/// </summary>
|
/// </summary>
|
||||||
[HttpGet("operationTime")]
|
[HttpGet("operationTime")]
|
||||||
[ProducesResponseType(typeof(IEnumerable<SubsystemOperationTimeDto>), (int)System.Net.HttpStatusCode.OK)]
|
[ProducesResponseType(typeof(IEnumerable<SubsystemOperationTimeDto>), (int)System.Net.HttpStatusCode.OK)]
|
||||||
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
public async Task<IActionResult> GetOperationTimeAsync(
|
public async Task<IActionResult> GetOperationTimeAsync(
|
||||||
[FromQuery] SubsystemOperationTimeRequest request,
|
[FromQuery] SubsystemOperationTimeRequest request,
|
||||||
CancellationToken token)
|
CancellationToken token)
|
||||||
{
|
{
|
||||||
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
||||||
return Forbid();
|
return Forbid();
|
||||||
if (!await IsValidRequest(request, token))
|
await CustomValidate(request, token);
|
||||||
return BadRequest("Запрашиваемый диапазон должен заканчиваться за 2 часа до текущего времени(после приведения к UTC).");
|
|
||||||
|
|
||||||
var result = await subsystemOperationTimeService.GetOperationTimeAsync(request, token);
|
var result = await subsystemOperationTimeService.GetOperationTimeAsync(request, token);
|
||||||
return Ok(result);
|
return Ok(result);
|
||||||
@ -148,14 +148,14 @@ namespace AsbCloudWebApi.Controllers.Subsystems
|
|||||||
[HttpDelete]
|
[HttpDelete]
|
||||||
[Permission]
|
[Permission]
|
||||||
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
|
[ProducesResponseType(typeof(int), (int)System.Net.HttpStatusCode.OK)]
|
||||||
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
public async Task<IActionResult> DeleteAsync(
|
public async Task<IActionResult> DeleteAsync(
|
||||||
[FromQuery] SubsystemOperationTimeRequest request,
|
[FromQuery] SubsystemOperationTimeRequest request,
|
||||||
CancellationToken token)
|
CancellationToken token)
|
||||||
{
|
{
|
||||||
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
if (!await UserHasAccesToWellAsync(request.IdWell, token))
|
||||||
return Forbid();
|
return Forbid();
|
||||||
if (!await IsValidRequest(request, token))
|
await CustomValidate(request, token);
|
||||||
return BadRequest("Запрашиваемый диапазон должен заканчиваться за 2 часа до текущего времени(после приведения к UTC).");
|
|
||||||
var result = await subsystemOperationTimeService.DeleteAsync(request, token);
|
var result = await subsystemOperationTimeService.DeleteAsync(request, token);
|
||||||
return Ok(result);
|
return Ok(result);
|
||||||
}
|
}
|
||||||
@ -180,20 +180,24 @@ namespace AsbCloudWebApi.Controllers.Subsystems
|
|||||||
return true;
|
return true;
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
protected async Task<bool> IsValidRequest(SubsystemOperationTimeRequest request, CancellationToken token)
|
|
||||||
|
/// <summary>
|
||||||
|
/// Валидирует запрос и бросает исключение ArgumentInvalidException
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="request"></param>
|
||||||
|
/// <param name="token"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
/// <exception cref="ArgumentException"></exception>
|
||||||
|
private async Task CustomValidate(SubsystemOperationTimeRequest request, CancellationToken token)
|
||||||
{
|
{
|
||||||
var well = await wellService.GetOrDefaultAsync(request.IdWell, token);
|
var well = await wellService.GetOrDefaultAsync(request.IdWell, token);
|
||||||
if (well is not null && request.LtDate.HasValue)
|
if (well is not null && request.LtDate.HasValue)
|
||||||
{
|
{
|
||||||
var ltDate = (DateTimeOffset)request.LtDate;
|
var ltDate = request.LtDate.Value;
|
||||||
var utcDateRequest = ltDate.ToRemoteDateTime(well.Timezone.Hours);
|
var utcDateRequest = ltDate.ToUtcDateTimeOffset(well.Timezone.Hours);
|
||||||
|
|
||||||
if (utcDateRequest.AddHours(2) > DateTime.UtcNow)
|
if (utcDateRequest.AddHours(2) > DateTime.UtcNow)
|
||||||
{
|
throw new ArgumentInvalidException("Запрашиваемый диапазон должен заканчиваться за 2 часа до текущего времени", nameof(request.LtDate));
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
return true;
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -55,6 +55,7 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
/// <param name="token"></param>
|
/// <param name="token"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
[HttpPut("{key}")]
|
[HttpPut("{key}")]
|
||||||
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
public virtual async Task<ActionResult<int>> UpsertAsync(string key, [FromBody] System.Text.Json.JsonDocument value, CancellationToken token)
|
public virtual async Task<ActionResult<int>> UpsertAsync(string key, [FromBody] System.Text.Json.JsonDocument value, CancellationToken token)
|
||||||
{
|
{
|
||||||
var userId = User.GetUserId();
|
var userId = User.GetUserId();
|
||||||
@ -63,7 +64,7 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
|
|
||||||
var result = await service.UpsertAsync((int)userId, key, value, token).ConfigureAwait(false);
|
var result = await service.UpsertAsync((int)userId, key, value, token).ConfigureAwait(false);
|
||||||
if (result < 0)
|
if (result < 0)
|
||||||
return BadRequest(ArgumentInvalidException.MakeValidationError(nameof(key), "not found"));
|
throw new ArgumentInvalidException("not found", nameof(key));
|
||||||
return Ok(result);
|
return Ok(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -74,6 +75,7 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
/// <param name="token"></param>
|
/// <param name="token"></param>
|
||||||
/// <returns></returns>
|
/// <returns></returns>
|
||||||
[HttpDelete("{key}")]
|
[HttpDelete("{key}")]
|
||||||
|
[ProducesResponseType(typeof(ValidationProblemDetails), (int)System.Net.HttpStatusCode.BadRequest)]
|
||||||
public virtual async Task<ActionResult<int>> DeleteAsync(string key, CancellationToken token)
|
public virtual async Task<ActionResult<int>> DeleteAsync(string key, CancellationToken token)
|
||||||
{
|
{
|
||||||
var userId = User.GetUserId();
|
var userId = User.GetUserId();
|
||||||
@ -82,7 +84,7 @@ namespace AsbCloudWebApi.Controllers
|
|||||||
|
|
||||||
var result = await service.DeleteAsync((int)userId, key, token).ConfigureAwait(false);
|
var result = await service.DeleteAsync((int)userId, key, token).ConfigureAwait(false);
|
||||||
if (result < 0)
|
if (result < 0)
|
||||||
return BadRequest(ArgumentInvalidException.MakeValidationError(nameof(key), "not found"));
|
throw new ArgumentInvalidException("not found", nameof(key));
|
||||||
return Ok(result);
|
return Ok(result);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
using AsbCloudApp.Data.User;
|
using AsbCloudApp.Data.User;
|
||||||
using AsbCloudWebApi.Converters;
|
using AsbCloudWebApi.Converters;
|
||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.ComponentModel;
|
using System.ComponentModel;
|
||||||
using System.Security.Claims;
|
using System.Security.Claims;
|
||||||
|
|
||||||
@ -30,13 +31,26 @@ namespace Microsoft.AspNetCore.Mvc
|
|||||||
: null;
|
: null;
|
||||||
}
|
}
|
||||||
|
|
||||||
public static IActionResult MakeBadRequest(this ControllerBase controller, string paramName, params string[] errors)
|
/// <summary>
|
||||||
|
/// <para>
|
||||||
|
/// Returns BadRequest with ValidationProblemDetails as body
|
||||||
|
/// </para>
|
||||||
|
/// <para>
|
||||||
|
/// Используйте этот метод только если валидацию нельзя сделать через
|
||||||
|
/// атрибуты валидации или IValidatableObject модели.
|
||||||
|
/// </para>
|
||||||
|
/// </summary>
|
||||||
|
/// <param name="controller"></param>
|
||||||
|
/// <param name="paramName"></param>
|
||||||
|
/// <param name="error"></param>
|
||||||
|
/// <returns></returns>
|
||||||
|
public static BadRequestObjectResult ValidationBadRequest(this ControllerBase controller, string paramName, string error)
|
||||||
{
|
{
|
||||||
return controller.BadRequest(new
|
var errors = new Dictionary<string, string[]> {
|
||||||
{
|
{ paramName, new[]{ error } }
|
||||||
name = paramName,
|
};
|
||||||
errors,
|
var problem = new ValidationProblemDetails(errors);
|
||||||
});
|
return controller.BadRequest(problem);
|
||||||
}
|
}
|
||||||
|
|
||||||
public static MvcOptions UseDateOnlyTimeOnlyStringConverters(this MvcOptions options)
|
public static MvcOptions UseDateOnlyTimeOnlyStringConverters(this MvcOptions options)
|
||||||
|
@ -1,8 +1,9 @@
|
|||||||
// Ignore Spelling: Middlewares
|
// Ignore Spelling: Middlewares
|
||||||
|
|
||||||
using AsbCloudApp.Exceptions;
|
using AsbCloudApp.Exceptions;
|
||||||
using Microsoft.AspNetCore.Http;
|
using Microsoft.AspNetCore.Http;
|
||||||
|
using Microsoft.AspNetCore.Mvc;
|
||||||
using System;
|
using System;
|
||||||
|
using System.Collections.Generic;
|
||||||
using System.Threading.Tasks;
|
using System.Threading.Tasks;
|
||||||
|
|
||||||
namespace AsbCloudWebApi.Middlewares
|
namespace AsbCloudWebApi.Middlewares
|
||||||
@ -55,8 +56,11 @@ namespace AsbCloudWebApi.Middlewares
|
|||||||
|
|
||||||
private static string MakeJsonBody(ArgumentInvalidException ex)
|
private static string MakeJsonBody(ArgumentInvalidException ex)
|
||||||
{
|
{
|
||||||
object error = ex.ToValidationErrorObject();
|
var errors = new Dictionary<string, string[]> {
|
||||||
var buffer = System.Text.Json.JsonSerializer.Serialize(error);
|
{ ex.ParamName, new[]{ ex.Message } }
|
||||||
|
};
|
||||||
|
var problem = new ValidationProblemDetails(errors);
|
||||||
|
var buffer = System.Text.Json.JsonSerializer.Serialize(problem);
|
||||||
return buffer;
|
return buffer;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
Loading…
Reference in New Issue
Block a user