Reputation: 21
I want to validate date as request parameter.
My endpoint url is like
http://localhost:8080/api/get/getCurrencyRate?date=02-20-2017
Controller:
@RequestMapping(value = "/getCurrencyRate", produces={"application/json"},
method = RequestMethod.GET)
public CurrenctRate getCurrencyrate(@RequestHeader ("Authorization") String
authorization, @RequestParam(value="date") @DateTimeFormat(pattern="MM-dd-
yyyy") @Valid Date date) throws Exception {
For the above input (02-20-2017) service is working fine. I want to validate the request param send appropiate response to the user. How can I do that.
e.g. if the request is like
http://localhost:8080/api/get/getCurrencyRate?date=02/20/2017
response should be "Please enter date in "MM-DD-YYYY" format"
whereas now I am getting
Error code **400**
<b>JBWEB000069: description</b>
<u>JBWEB000120:
- The request sent by the client was syntactically incorrect.
</u>
Please advice.
Upvotes: 2
Views: 18419
Reputation: 21
I created custom exception handler extending ResponseEntityExceptionHandler with @ControllerAdvice. where I override handleTypeMismatch(TypeMismatchException ex, HttpHeaders headers, HttpStatus status, WebRequest request). This way I created handled the exception and created my own response.
Please refer below:
@Override
protected ResponseEntity<Object> handleTypeMismatch(TypeMismatchException ex, HttpHeaders headers, HttpStatus status, WebRequest request) {
char quotes='"';
String error ="Invalid date "+ quotes+ ex.getValue()+quotes +".. Please enter date in MM/dd/YYYY.";
err (error);
CustomException customExcepton = new CustomException (HttpStatus.BAD_REQUEST, "101", ex.getLocalizedMessage(), error);
return new ResponseEntity <Object> (customExcepton, new HttpHeaders(), customExcepton.getStatus());
}
My CustomException class is:
@JsonInclude(Include.NON_NULL) public class CustomException implements Serializable {
private static final long serialVersionUID = -6839345326601547899L;
private HttpStatus status;
private String exceptionCode;
private String exceptionMessage;
private List <String> errors = null;
public CustomException() {
// Default
}
public CustomException (HttpStatus status, String exceptionCode, String exceptionMessage, String error) {
super();
this.status = status;
this.exceptionCode = exceptionCode;
this.exceptionMessage = exceptionMessage;
this.errors = Arrays.asList (error);
}
//getters and setters
Upvotes: 0
Reputation: 6818
You have to use @ControllerAdvice
, create exception handler for MethodArgumentTypeMismatchException
exception type and also create class for your proper exception class which you need to send as a response to the client. For instance,
I have @ControllerAdvice
class RestErrorHandler
with below exceptionhandler for HttpMessageNotReadableException
exception.
@ExceptionHandler(HttpMessageNotReadableException.class)
@ResponseStatus(HttpStatus.BAD_REQUEST)
@ResponseBody
public ResponseEntity<ValidationErrorDTO> processValidationIllegalError(HttpMessageNotReadableException ex,
HandlerMethod handlerMethod, WebRequest webRequest) {
Throwable throwable = ex.getMostSpecificCause();
ValidationErrorDTO errorDTO = new ValidationErrorDTO();
if (throwable instanceof EnumValidationException) {
EnumValidationException exception = (EnumValidationException) ex.getMostSpecificCause();
errorDTO.setEnumName(exception.getEnumName());
errorDTO.setEnumValue(exception.getEnumValue());
errorDTO.setErrorMessage(exception.getEnumValue() + " is an invalid " + exception.getEnumName());
}
return new ResponseEntity<ValidationErrorDTO>(errorDTO, HttpStatus.BAD_REQUEST);
}
ValidationErrorDTO
is the class having few setter/getters and when HttpMessageNotReadableException
exception occurs then send ValidationErrorDTO
in the response with the message which I want the client to see.
Upvotes: 0
Reputation: 89169
The best solution I can think of is to have methods for all types of date format BUT formation the path, or use path parameters, like so:
//Using Path
@RequestMapping(value = "/getCurrencyRate/{date}", produces={"application/json"}, method = RequestMethod.GET)
public CurrenctRate getCurrencyRateOfDate(@RequestHeader ("Authorization") String authorization, @PathVariable("date") @DateTimeFormat(pattern="MM/dd/yyyy") @Valid Date date) throws Exception {
OR, with request parameter
//Using Request Parameter
@RequestMapping(value = "/getCurrencyRate", produces={"application/json"}, method = RequestMethod.GET)
public CurrenctRate getCurrencyrate(@RequestHeader ("Authorization") String authorization, @RequestParam(value="date") @DateTimeFormat(pattern="MM/dd/yyyy") @Valid Date date) throws Exception {
That way, Spring REST can match your request to your API call.
Upvotes: 2