jgeerts
jgeerts

Reputation: 671

Spring jackson deserialization and exception handling

I'm building a REST api in Spring and I have problems with my exception handling. I want to validate the full request and give information about the payload in one go.

Suppose my object is

public class StubJson {
    private BigDecimal bigDecimalField;
    @NotEmpty
    private String stringField;

    public void setBigDecimalField(BigDecimal bigDecimalField) { this.bigDecimalField = bigDecimalField; }
    public String setStringField(String stringField) { this.stringField = stringField; }
}

And my controller is

@RestController
public class StubController {
    @RequestMapping(value = "/stub", method = POST)
    public void stub(@Valid @RequestBody StubJson stubJson) {}
}

The validation on this object is in a @ControllerAdvice that translates FieldError objects into translated errors for the end user.

@ResponseStatus(BAD_REQUEST)
@ResponseBody
@ExceptionHandler(value = MethodArgumentNotValidException.class)
public List<ErrorJson> processValidationError(MethodArgumentNotValidException ex) {}

If I pass in this json

{"bigDecimalField": "text", "stringField": ""}

I want a response like this

[
  {
    "field": "stringField",
    "message": "Cannot be empty."
  },
  {
    "field": "bigDecimalField",
    "message": "Not a number."
  }
]

If I do this I get a

com.fasterxml.jackson.databind.exc.InvalidFormatException

on the BigDecimalField which only contains information about only one field. The only option I see is passing it in as a String or writing custom validation annotations. Is there an easier way of achieving this?

Upvotes: 4

Views: 6055

Answers (1)

Umair Zahid
Umair Zahid

Reputation: 143

You can use controller advice for this purpose. Declare a controller advice in your application, catch you expected exception, transform to you required response and return. Just remember controller advice will be applied to all of your controller.

@ControllerAdvice
public class ExceptionHandlerController {

@ExceptionHandler(InvalidFormatException.class)
    @ResponseBody public String typeMismatchException(HttpServletRequest request, HttpServletResponse servletResponse, InvalidFormatException e ) {

        String yourResponse = "";
        return yourResponse;
    }

}

Upvotes: 0

Related Questions