在 Spring Boot 中处理异常确实有多个方式,比如使用 @ControllerAdvice
、 BasicErrorController
、HandlerExceptionResolver
等。不同方式适合不同的场景,下面是对这些方式的分析以及如何选择的建议:
🧩 1. @ControllerAdvice + @ExceptionHandler(推荐使用)
适用场景:
• 适合全局或局部地处理控制器抛出的异常。
• 适合为 REST 接口返回统一的异常结构(如 JSON)。
优点:
• 使用简单,语义明确。
• 可细粒度控制不同异常的处理逻辑。
• 与 Spring MVC 集成紧密,配合@ResponseStatus
等注解效果更好。
示例:
@ControllerAdvice
public class GlobalExceptionHandler {@ExceptionHandler(ResourceNotFoundException.class)@ResponseStatus(HttpStatus.NOT_FOUND)public ErrorResponse handleNotFound(ResourceNotFoundException ex) {return new ErrorResponse("NOT_FOUND", ex.getMessage());}@ExceptionHandler(Exception.class)@ResponseStatus(HttpStatus.INTERNAL_SERVER_ERROR)public ErrorResponse handleException(Exception ex) {return new ErrorResponse("INTERNAL_ERROR", "Unexpected error occurred");}
}
🧩 2. 自定义 BasicErrorController
适用场景:
• 需要完全控制 Spring Boot 默认错误响应行为时。
• 通常用于构建统一错误页面(HTML)或更底层的 JSON 错误处理逻辑。
优点:
• 可以替换 Spring Boot 默认的 /error 映射逻辑。
• 对 WebMvc + REST + WebFlux 一致性要求高时有用。
缺点:
• 实现复杂,通常不建议自定义它,除非你确实不满意 Spring Boot 提供的默认行为。
备注:
• Spring Boot 默认的错误信息来自 DefaultErrorAttributes 和 BasicErrorController。
🧩 3. HandlerExceptionResolver(低级机制)
适用场景:
• 需要低级别控制异常解析过程,比如处理过滤器/拦截器中抛出的异常。
• 不推荐用于日常业务异常处理。
优点:
• 可用于特殊场景,如非 MVC 层的异常处理。
缺点:
• 更底层、侵入性大、可维护性差。
✅ 选择建议总结
使用方式 | 场景适合 | 是否推荐 |
---|---|---|
@ControllerAdvice | 统一处理控制器异常(REST 风格),前后端分离 | ✅ 推荐 |
BasicErrorController | 自定义 Spring Boot 错误响应入口,有HTML页面需求 | ⚠️ 特殊需求时使用 |
HandlerExceptionResolver | 全局底层异常控制 | ❌ 不推荐常规使用 |
总得来说,如果是前后端分离的项目则选择@ControllerAdvice
,如果是需要返回HTML错误页面选择BasicErrorController
,除非有更底层的异常处理就选择HandlerExceptionResolver
,但一般不建议使用。