MethodArgumentNotValidException需用@ControllerAdvice+@ExceptionHandler统一捕获并返回400响应;提取BindingResult中的FieldError,结合messageSource实现国际化错误消息,构造含code、message、details的JSON格式响应。

在 Spring Boot 中,MethodArgumentNotValidException 是当使用 @Valid 或 @Validated 注解校验控制器方法参数(如 @RequestBody 对象)失败时自动抛出的异常。它本身不带用户友好的错误信息,需统一捕获并转换为标准响应格式。
全局异常处理器捕获并格式化响应
推荐使用 @ControllerAdvice + @ExceptionHandler 统一处理该异常,避免每个接口重复写校验逻辑。
- 创建一个全局异常处理器类,添加
@ControllerAdvice注解 - 用
@ExceptionHandler(MethodArgumentNotValidException.class)方法接收异常 - 从异常中提取
BindingResult,遍历所有FieldError获取字段名和默认错误消息(如NotNull.user.name)或自定义提示(配合@NotBlank(message = "用户名不能为空")) - 构造统一的 JSON 响应体(如包含 code、message、details 字段),返回
ResponseEntity或直接返回对象(由@ResponseBody自动序列化)
确保校验注解生效
异常能被抛出的前提是校验真正触发:
-
@RequestBody参数必须显式加@Valid(或@Validated),仅加校验注解(如@NotBlank)不够 - 不要在 DTO 类上只加
@Valid,而忘了在控制器方法参数上也加——后者才是触发点 - 若用
@Validated配合分组校验,需确保分组类型与注解声明一致
自定义错误消息与国际化支持
提升用户体验的关键细节:
- 在
resources/messages.properties中定义如NotBlank.user.username=用户名不能为空,并在注解中引用:@NotBlank(message = "{NotBlank.user.username}") - 配置
MessageSourceBean(Spring Boot 默认已配好ResourceBundleMessageSource),支持根据请求头Accept-Language返回对应语言提示 - 在异常处理器中调用
messageSource.getMessage(error, LocaleContextHolder.getLocale())获取本地化消息
区分客户端错误与服务端异常
校验失败属于明确的客户端输入问题,应返回 HTTP 400 Bad Request,而非 500:
- 在
@ExceptionHandler方法中,用ResponseEntity.status(HttpStatus.BAD_REQUEST).body(...)显式设状态码 - 避免和
RuntimeException等未预期异常共用同一错误码,便于前端区分处理(例如表单高亮 vs 弹系统错误提示) - 可将校验失败响应结构设计为含
"code": "VALIDATION_FAILED",方便前端做统一拦截和字段映射
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南











