Spring Boot+Hibernate服务404异常无法通过@ControllerAdvice捕获问题求助
为啥你的@ControllerAdvice抓不到404异常?
嘿,我来帮你捋清楚这个问题:在Spring Boot里,当你访问一个不存在的路径时,DispatcherServlet找不到对应的控制器方法,默认不会抛出异常,而是直接生成404响应返回。而你的@ControllerAdvice只能捕获控制器层主动抛出的异常,自然就抓不到这种情况啦。
下面给你两种解决办法,按需选就行:
方法1:开启抛出NoHandlerFoundException,让全局处理器能抓到
首先在配置文件里加两行配置,让Spring Boot在找不到Handler时抛出NoHandlerFoundException:
如果你用application.properties:
spring.mvc.throw-exception-if-no-handler-found=true spring.web.resources.add-mappings=false
如果你用application.yml:
spring: mvc: throw-exception-if-no-handler-found: true web: resources: add-mappings: false
小贴士:
spring.web.resources.add-mappings=false是为了让静态资源的404也触发异常,如果不需要管静态资源的404,可以去掉,但一般建议加上,确保所有路径的404都能被捕获。
然后修改你的全局异常处理器,新增对NoHandlerFoundException的处理:
@ControllerAdvice public class GlobalExceptionHandlerController { // 你原来的NullPointerException处理 @ResponseStatus(value = HttpStatus.INTERNAL_SERVER_ERROR) @ExceptionHandler(value = NullPointerException.class) @ResponseBody public String handleNullPointerException(NullPointerException ex) { return "发生空指针异常:" + ex.getMessage(); } // 新增404异常处理 @ResponseStatus(value = HttpStatus.NOT_FOUND) @ExceptionHandler(value = NoHandlerFoundException.class) @ResponseBody public String handleNoHandlerFoundException(NoHandlerFoundException ex) { return "请求的路径不存在:" + ex.getRequestURL(); } }
方法2:自定义ErrorController,更灵活处理所有错误
如果不想开启异常抛出,也可以通过实现ErrorController接口来接管所有错误响应,这种方式能处理容器级别的所有错误(包括404、500等):
@RestController public class CustomErrorController implements ErrorController { @RequestMapping("/error") public ResponseEntity<String> handleError(HttpServletRequest request) { Object status = request.getAttribute(RequestDispatcher.ERROR_STATUS_CODE); if (status != null) { Integer statusCode = Integer.valueOf(status.toString()); if (statusCode == HttpStatus.NOT_FOUND.value()) { return new ResponseEntity<>("抱歉,您访问的页面不存在", HttpStatus.NOT_FOUND); } else if (statusCode == HttpStatus.INTERNAL_SERVER_ERROR.value()) { return new ResponseEntity<>("服务器内部错误", HttpStatus.INTERNAL_SERVER_ERROR); } } return new ResponseEntity<>("未知错误", HttpStatus.INTERNAL_SERVER_ERROR); } // 注意:Spring Boot 2.3及以上版本不需要重写getErrorPath(),默认就是"/error" }
两种方法各有特点:方法1能和你现有的异常处理器统一管理,方法2更灵活,能覆盖所有错误场景,你可以根据自己的需求来选~
内容的提问来源于stack exchange,提问作者Hitrene
相关产品推荐
相关产品推荐

