/// <summary> /// Produces a <see cref="StatusCodes.Status400BadRequest"/> response /// with a <see cref="HttpValidationProblemDetails"/> value. /// </summary> /// <param name="errors">One or more validation errors.</param> /// <param name="detail">The value for <see cref="ProblemDetails.Detail" />.</param> /// <param name="instance">The value for <see cref="ProblemDetails.Instance" />.</param> /// <param name="statusCode">The status code.</param> /// <param name="title">The value for <see cref="ProblemDetails.Title" />. Defaults to "One or more validation errors occurred."</param> /// <param name="type">The value for <see cref="ProblemDetails.Type" />.</param> /// <param name="extensions">The value for <see cref="ProblemDetails.Extensions" />.</param> /// <returns>The created <see cref="IResult"/> for the response.</returns> public static IResult ValidationProblem( IDictionary <string, string[]> errors, string?detail = null, string?instance = null, int?statusCode = null, string?title = null, string?type = null, IDictionary <string, object?>?extensions = null) { var problemDetails = new HttpValidationProblemDetails(errors) { Detail = detail, Instance = instance, Type = type, Status = statusCode, }; problemDetails.Title = title ?? problemDetails.Title; if (extensions is not null) { foreach (var extension in extensions) { problemDetails.Extensions.Add(extension); } } return(new ObjectResult(problemDetails) { ContentType = "application/problem+json", }); }
public async Task ExecuteAsync_UsesDefaults_ForProblemDetails() { // Arrange var details = new HttpValidationProblemDetails(); var result = new ValidationProblem(details); var stream = new MemoryStream(); var httpContext = new DefaultHttpContext { RequestServices = CreateServices(), Response = { Body = stream, }, }; // Act await result.ExecuteAsync(httpContext); // Assert Assert.Equal(StatusCodes.Status400BadRequest, httpContext.Response.StatusCode); Assert.Equal(details, result.ProblemDetails); stream.Position = 0; var responseDetails = JsonSerializer.Deserialize <ProblemDetails>(stream); Assert.Equal("https://tools.ietf.org/html/rfc7231#section-6.5.1", responseDetails.Type); Assert.Equal("One or more validation errors occurred.", responseDetails.Title); Assert.Equal(StatusCodes.Status400BadRequest, responseDetails.Status); }
/// <summary> /// Produces a <see cref="StatusCodes.Status400BadRequest"/> response /// with a <see cref="HttpValidationProblemDetails"/> value. /// </summary> /// <param name="errors">One or more validation errors.</param> /// <param name="detail">The value for <see cref="ProblemDetails.Detail" />.</param> /// <param name="instance">The value for <see cref="ProblemDetails.Instance" />.</param> /// <param name="statusCode">The status code.</param> /// <param name="title">The value for <see cref="ProblemDetails.Title" />. Defaults to "One or more validation errors occurred."</param> /// <param name="type">The value for <see cref="ProblemDetails.Type" />.</param> /// <param name="extensions">The value for <see cref="ProblemDetails.Extensions" />.</param> /// <returns>The created <see cref="IResult"/> for the response.</returns> public static IResult ValidationProblem( IDictionary <string, string[]> errors, string?detail = null, string?instance = null, int?statusCode = null, string?title = null, string?type = null, IDictionary <string, object?>?extensions = null) { // TypedResults.ValidationProblem() does not allow setting the statusCode so we do this manually here var problemDetails = new HttpValidationProblemDetails(errors) { Detail = detail, Instance = instance, Type = type, Status = statusCode, }; problemDetails.Title = title ?? problemDetails.Title; if (extensions is not null) { foreach (var extension in extensions) { problemDetails.Extensions.Add(extension); } } return(TypedResults.Problem(problemDetails)); }
public async Task ExecuteAsync_IncludeErrors_ForValidationProblemDetails() { // Arrange var details = new HttpValidationProblemDetails(new Dictionary <string, string[]> { { "testError", new string[] { "message" } } }); var result = new ProblemHttpResult(details); var stream = new MemoryStream(); var httpContext = new DefaultHttpContext() { RequestServices = CreateServices(), Response = { Body = stream, }, }; // Act await result.ExecuteAsync(httpContext); // Assert Assert.Equal(StatusCodes.Status400BadRequest, httpContext.Response.StatusCode); stream.Position = 0; var responseDetails = JsonSerializer.Deserialize <HttpValidationProblemDetails>(stream); Assert.Equal(StatusCodes.Status400BadRequest, responseDetails.Status); var error = Assert.Single(responseDetails.Errors); Assert.Equal("testError", error.Key); }
public void ValidationProblemResult_Implements_IValueHttpResultOfT_Correctly() { // Arrange var value = new HttpValidationProblemDetails(); // Act & Assert var result = Assert.IsAssignableFrom <IValueHttpResult <HttpValidationProblemDetails> >(new ValidationProblem(value)); Assert.IsType <HttpValidationProblemDetails>(result.Value); Assert.Equal(value, result.Value); }
public void NotFoundObjectResult_ProblemDetails_SetsStatusCodeAndValue() { // Arrange & Act var obj = new HttpValidationProblemDetails(); var result = new NotFound <HttpValidationProblemDetails>(obj); // Assert Assert.Equal(StatusCodes.Status404NotFound, result.StatusCode); Assert.Equal(StatusCodes.Status404NotFound, obj.Status); Assert.Equal(obj, result.Value); }
public void CreatedResult_ProblemDetails_SetsStatusCodeAndValue() { // Arrange & Act var expectedUrl = "testAction"; var obj = new HttpValidationProblemDetails(); var result = new Created <HttpValidationProblemDetails>(expectedUrl, obj); // Assert Assert.Equal(StatusCodes.Status201Created, result.StatusCode); Assert.Equal(StatusCodes.Status201Created, obj.Status); Assert.Equal(obj, result.Value); }
public void AcceptedAtRouteResult_ProblemDetails_SetsStatusCodeAndValue() { // Arrange & Act var routeValues = new RouteValueDictionary(new Dictionary <string, string>() { { "test", "case" }, { "sample", "route" } }); var obj = new HttpValidationProblemDetails(); var result = new AcceptedAtRoute <HttpValidationProblemDetails>(routeValues, obj); // Assert Assert.Equal(StatusCodes.Status202Accepted, result.StatusCode); Assert.Equal(StatusCodes.Status202Accepted, obj.Status); Assert.Equal(obj, result.Value); }
public void Problem_WithValidationProblemArg_ResultHasCorrectValues() { // Arrange var problem = new HttpValidationProblemDetails { Title = "Test title" }; // Act var result = TypedResults.Problem(problem); // Assert Assert.Equal(problem, result.ProblemDetails); Assert.Equal("Test title", result.ProblemDetails.Title); Assert.Equal("application/problem+json", result.ContentType); Assert.Equal(StatusCodes.Status400BadRequest, result.StatusCode); }
public async Task ExecuteAsync_SetsProblemDetailsStatus_ForValidationProblemDetails() { // Arrange var details = new HttpValidationProblemDetails(); var result = new ObjectResult(details, StatusCodes.Status422UnprocessableEntity); var httpContext = new DefaultHttpContext() { RequestServices = CreateServices(), }; // Act await result.ExecuteAsync(httpContext); // Assert Assert.Equal(StatusCodes.Status422UnprocessableEntity, details.Status.Value); }
internal ValidationProblem(HttpValidationProblemDetails problemDetails) { ArgumentNullException.ThrowIfNull(problemDetails); if (problemDetails is { Status : not null and not StatusCodes.Status400BadRequest })