解决使用@ControllerAdvice继承ResponseEntityExceptionHandler处理异常时的坑

  • A+
所属分类:SpringBoot

我们知道用@ControllerAdvice注解配合

@ExceptionHandler(XXXException.class)
public ApiResultDto handleBizException(XXXException e) {
    // 获取异常消息
    return ApiResultDtoUtil.error(e.getCode(), e.getMessage());
}

可以处理controller的全局异常,有时我们会继承ResponseEntityExceptionHandler类,这个类里默认帮我们处理了一些spring里自带的异常。但是这里面有坑,一旦继承了这个类,访问接口时,一些默认的异常返回的json内容是空。

比如我的cotroller里有一个接口中

@RequestMapping("/test")
public Object test(@RequestParam String a){
    return a;
}

这时如果我在postman里直接不传参数a来访问localhost:8080/test接口,那么返回的结果会是空

而我们如果不使用全局异常处理的话,它返回的结果应该是

{
    "timestamp": "2020-03-24T04:07:55.786+0000",
    "status": 400,
    "error": "Bad Request",
    "message": "Required String parameter 'a' is not present",
    "path": "/test"
}

为什么会这样呢?我们点开ResponseEntityExceptionHandler类的源码可以看到,它里面是帮我们实现了spring里默认的异常处理,但是最后返回json时body里全部设的是null,所以我们在postman里得到的结果就是空。我们如果想得到上面那样异常信息,则需要重写ResponseEntityExceptionHandler里面的方法,把body设成我们想返回的Json值即可,相当于自定义返回的json数据格式。

当然还有一个最简单的方法就是,如果我们其它的异常不需要自定义json的返回格式,那么我们不继承ResponseEntityExceptionHandler类,这样除了我们自定义的异常的处理@ExceptionHandler外,其它的异常则都会由spring的默认异常处理器DefaultHandlerExceptionResolver来处理,这样也会得到上面的异常信息。

ZPY

发表评论

:?: :razz: :sad: :evil: :!: :smile: :oops: :grin: :eek: :shock: :???: :cool: :lol: :mad: :twisted: :roll: :wink: :idea: :arrow: :neutral: :cry: :mrgreen: