0

I'm trying to get automatic data validation working in an ApiController but when the user sends incorrect/missing data a JSON deserialization failed error message is returned instead of the custom ErrorMessage.

ProfilesController.cs

using ClassLibrary.Models;
using ClassLibrary.Services;
using Microsoft.AspNetCore.Mvc;
using Swashbuckle.AspNetCore.Annotations;
using ClassLibrary.Models.API.Responses.Profiles;
using ClassLibrary.Models.API.Requests;
using Microsoft.AspNetCore.Authorization;

namespace API.Controllers
{
    [ApiController]
    [Route("v1/[controller]")]
    public class ProfilesController : Controller
    {
        private IProfileManager _profileManager;

        public ProfilesController(IProfileManager profileManager)
        {
            _profileManager = profileManager;
        }

        [Authorize]
        [HttpPatch("about")]
        public async Task<IActionResult> UpdateAbout([FromBody] UpdateAboutPayload payload)
        {
            await _profileManager.UpdateAboutAsync(payload.About);

            return Ok();
        }
    }
}

UpdateAboutPayload.cs

using System.ComponentModel.DataAnnotations;

namespace ClassLibrary.Models.API.Requests
{
    public class UpdateAboutPayload
    {
        [Required(ErrorMessage = "About is required")]
        [StringLength(500, ErrorMessage = "About must be between 0 and 500 characters long")]
        public required string About { get; set; }
    }
}

When I send the following data

{}

I get this error

{
  "type": "https://tools.ietf.org/html/rfc9110#section-15.5.1",
  "title": "One or more validation errors occurred.",
  "status": 400,
  "errors": {
    "$": [
      "JSON deserialization for type 'ClassLibrary.Models.API.Requests.UpdateAboutPayload' was missing required properties, including the following: about"
    ],
    "payload": [
      "The payload field is required."
    ]
  },
  "traceId": "00-402c938fa2cb172de6a89b521f8fcae1-88ebfe9d6c674e35-00"
}

instead of the error message configured in the [Required] attribute

2 Answers 2

1

The issue was caused by the required modifier on the About property, removing it solved the error.

Sign up to request clarification or add additional context in comments.

2 Comments

This doesn't solves your issue, it just hides it.
How doesn't it solve my issue? The value is still required but it's set as such by the [Required] attribute instead of the required modifier.
0

That is the correct behavior, you are not sending the whole object, hence you are getting the exception that payload field is required, If you only want "About is required" message, you need to send blank payload, something like this

{ 
   payload: {} 
}

3 Comments

About is a string, not an object and even if I set it to an empty object i still get the same error message.
Does this mean that [FromBody] is trying to extract a child property with the key payload from inside your top-level body JSON object, instead of treating the entire body JSON object as an UpdateAboutPayload object itself? Maybe removing [FromBody] will parse the entire body as that class? (Case 6 in Binding Precedence)
The issue still happens even without the [FromBody] attribute

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.