什么是@RestControllerAdvice:
@RestControllerAdvice是一个组合注解,由@ControllerAdvice,@ResponseBody组成,@ControllerAdvice又继承了@Component,因此@RestControllerAdvice本质上是个Component,用于定义@ExceptionHandler,@InitBinder和@ModelAttribute方法,适用于所有使用@RequestMapping方法.
@ExceptionHandler:用于指定异常处理方法。当与@RestControllerAdvice配合使用时,用于全局处理控制器里的异常
@InitBinder:用来设置WebDataBinder,用于自动绑定前台请求参数到Model中
@ModelAttribute:本来作用是绑定键值对到Model中,当与@ControllerAdvice配合使用时,可以让全局的@RequestMapping都能获得在此处设置的键值对
用法:
-
通过@ControllerAdvice注解可以将对于控制器的全局配置放在同一个位置
-
注解了@RestControllerAdvice的类的方法可以使用@ExceptionHandler、@InitBinder、@ModelAttribute注解到方法上
-
@RestControllerAdvice注解将作用在所有注解了@RequestMapping的控制器的方法上
代码示例:
此处省略了统一返回类
/**
* 全局异常处理类
*/
@RestControllerAdvice
public class GlobalExceptionHandler {
@ExceptionHandler({MissingServletRequestParameterException.class})
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(MissingServletRequestParameterException e) {
String message = String.format("缺少必要的请求参数: %s", e.getParameterName());
return R.fail(HttpStatus.BAD_REQUEST, message);
}
@ExceptionHandler({MethodArgumentTypeMismatchException.class})
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(MethodArgumentTypeMismatchException e) {
String message = String.format("请求参数格式错误: %s", e.getName());
return R.fail(HttpStatus.BAD_REQUEST, message);
}
@ExceptionHandler({MethodArgumentNotValidException.class})
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(MethodArgumentNotValidException e) {
return this.handleError(e.getBindingResult());
}
@ExceptionHandler({BindException.class})
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(BindException e) {
return this.handleError(e.getBindingResult());
}
private R handleError(BindingResult result) {
FieldError error = result.getFieldError();
String message = String.format("%s:%s", error.getField(), error.getDefaultMessage());
return R.fail(HttpStatus.BAD_REQUEST, HttpStatus.BAD_REQUEST.getReasonPhrase()+" "+message);
}
@ExceptionHandler(ConstraintViolationException.class)
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(ConstraintViolationException e) {
Set<ConstraintViolation<?>> violations = e.getConstraintViolations();
ConstraintViolation<?> violation = violations.iterator().next();
String path = ((PathImpl) violation.getPropertyPath()).getLeafNode().getName();
String message = String.format("%s:%s", path, violation.getMessage());
return R.fail(HttpStatus.BAD_REQUEST, message);
}
@ExceptionHandler(NoHandlerFoundException.class)
@ResponseStatus(HttpStatus.NOT_FOUND)
public R handleError(NoHandlerFoundException e) {
return R.fail(HttpStatus.NOT_FOUND, e.getMessage());
}
@ExceptionHandler(HttpMessageNotReadableException.class)
@ResponseStatus(HttpStatus.BAD_REQUEST)
public R handleError(HttpMessageNotReadableException e) {
return R.fail(HttpStatus.BAD_REQUEST, e.getMessage());
}
@ExceptionHandler(HttpRequestMethodNotSupportedException.class)
@ResponseStatus(HttpStatus.METHOD_NOT_ALLOWED)
public R handleError(HttpRequestMethodNotSupportedException e) {
return R.fail(HttpStatus.METHOD_NOT_ALLOWED, e.getMessage());
}
@ExceptionHandler(HttpMediaTypeNotSupportedException.class)
@ResponseStatus(HttpStatus.UNSUPPORTED_MEDIA_TYPE)
public R handleError(HttpMediaTypeNotSupportedException e) {
return R.fail(HttpStatus.UNSUPPORTED_MEDIA_TYPE, e.getMessage());
}
}