Java 使用 Validated 捕获 MethodArgumentNotValidException

1. 简介

在Java开发中,我们经常需要对输入的数据进行校验。Spring框架提供了一种简单而强大的方法来实现数据校验,即使用 Validated 注解结合 MethodArgumentNotValidException 异常来捕获校验失败的情况。本文将详细介绍如何在Java中使用 Validated 注解来捕获 MethodArgumentNotValidException 异常。

2. 整体流程

下表展示了整个过程的步骤:

步骤 描述
1 定义需要校验的实体类
2 在Controller层添加校验逻辑
3 定义全局异常处理类
4 在全局异常处理类中捕获并处理 MethodArgumentNotValidException 异常
5 返回校验失败的结果

下面我们将逐步介绍每个步骤的具体实现。

3. 实现步骤

步骤 1:定义需要校验的实体类

首先,我们需要定义一个实体类,该实体类包含需要进行校验的字段。例如,我们定义一个 User 类,包含一个 name 字段和一个 age 字段。

public class User {
    @NotBlank(message = "姓名不能为空")
    private String name;

    @Min(value = 18, message = "年龄必须大于等于18")
    private int age;

    // 省略 getter 和 setter 方法
}

在上述代码中,我们使用了 NotBlank 注解来标识 name 字段不能为空,使用了 Min 注解来标识 age 字段必须大于等于18。

步骤 2:在Controller层添加校验逻辑

接下来,在Controller层中添加校验逻辑。我们可以通过在方法参数中添加 @Validated 注解来启用校验功能。在方法体内,如果校验失败,将会抛出 MethodArgumentNotValidException 异常。

@RestController
public class UserController {

    @PostMapping("/users")
    public String createUser(@Validated @RequestBody User user) {
        // 处理创建用户的逻辑
        return "创建用户成功";
    }
}

在上述代码中,我们在 createUser 方法的参数中添加了 @Validated 注解来启用校验功能,同时使用 @RequestBody 注解将请求的JSON转换为 User 对象。如果校验失败,将会抛出 MethodArgumentNotValidException 异常。

步骤 3:定义全局异常处理类

为了捕获并处理 MethodArgumentNotValidException 异常,我们需要定义一个全局异常处理类。该类需要实现 @ControllerAdvice 注解,并定义一个异常处理方法。

@ControllerAdvice
public class GlobalExceptionHandler {

    @ExceptionHandler(MethodArgumentNotValidException.class)
    @ResponseBody
    public ResponseEntity<String> handleMethodArgumentNotValidException(MethodArgumentNotValidException e) {
        // 处理校验失败的逻辑
        return ResponseEntity.status(HttpStatus.BAD_REQUEST).body(e.getMessage());
    }
}

在上述代码中,我们使用 @ExceptionHandler 注解来标识异常处理方法,该方法的参数为 MethodArgumentNotValidException 类型,即用于处理校验失败的异常。在该方法中,我们可以自定义处理校验失败的逻辑,例如返回一个错误信息。

步骤 4:在全局异常处理类中捕获并处理 MethodArgumentNotValidException 异常

接下来,我们需要在全局异常处理类中捕获并处理 MethodArgumentNotValidException 异常。在处理方法中,我们可以通过 BindingResult 对象获取校验失败的详细信息。

public ResponseEntity<String> handleMethodArgumentNotValidException(MethodArgumentNotValidException e) {
    BindingResult bindingResult = e.getBindingResult();
    StringBuilder stringBuilder = new StringBuilder();
    for (FieldError fieldError : bindingResult.getFieldErrors()) {
        stringBuilder.append(fieldError.getDefaultMessage()).append("\n");
    }
    return ResponseEntity.status(HttpStatus.BAD_REQUEST).body(stringBuilder.toString());
}

在上述代码中,我们通过 e.getBindingResult() 方法获取 `BindingResult