当前位置:   article > 正文

详解java参数校验之:顺序校验、自定义校验、分组校验(@Validated @GroupSequence)_java 非空校验分组

java 非空校验分组

当使用 @Validated、@GroupSequence 和自定义校验规则时,可以实现对实体类属性的分组校验
首先,定义验证分组的接口:

public interface Group1 {}
public interface Group2 {}

@GroupSequence({Group1.class, Group2.class})
public interface MyValidationGroupSequence {}
  • 1
  • 2
  • 3
  • 4
  • 5

然后,创建一个实体类,并应用验证分组的约束和自定义校验规则:

public class User {
    @NotBlank(groups = Group1.class)
    private String username;

    @Size(min = 6, max = 20, groups = Group2.class)
    @CustomValidation(groups = Group2.class)
    private String password;

    // 省略构造函数、getter 和 setter 方法
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

在上述示例中,User 类应用了不同分组的约束。username 字段在 Group1 分组中不能为空白(@NotBlank),password 字段在 Group2 分组中必须是长度在 6 到 20 之间的字符串,并通过 @CustomValidation 标记了自定义校验规则。

接下来,定义一个自定义校验注解和校验器:

@Target({ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = CustomValidator.class)
public @interface CustomValidation {
    String message() default "Invalid value";
    Class<?>[] groups() default {};
    Class<? extends Payload>[] payload() default {};
}

public class CustomValidator implements ConstraintValidator<CustomValidation, String> {
    public boolean isValid(String value, ConstraintValidatorContext context) {
        return value.matches("[A-Za-z0-9]+");
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13
  • 14

在上述示例中,定义了一个名为 CustomValidation 的自定义校验注解,并将它应用在 password 字段上。同时,实现了 CustomValidator 类,对属性值进行自定义校验。

最后,创建一个服务类,并在方法参数上应用 @Validated 和验证分组注解进行校验:

@Service
@Validated
public class UserService {
    public void createUser(@Validated(MyValidationGroupSequence.class) User user) {
        // 创建用户的业务逻辑
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

在上述示例中,createUser 方法使用了 @Validated 注解来启用方法参数校验,并通过 @Validated(MyValidationGroupSequence.class) 指定了要验证的分组。

使用该服务类进行方法调用时,会按照 @GroupSequence 中指定的顺序依次对分组进行校验,并执行自定义校验规则。

注意,为了使自定义校验规则生效,需要在 Spring 配置文件(如配置类)中配置自定义校验器,当然springboot环境已经自动注入了:

@Configuration
public class AppConfig {
    @Bean
    public MethodValidationPostProcessor methodValidationPostProcessor() {
        return new MethodValidationPostProcessor();
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

以上展示了结合 @Validated、@GroupSequence 和自定义校验规则的用法,以实现分组校验和自定义校验逻辑。具体的验证逻辑和业务约束根据实际需求进行定义和实现。

MethodValidationPostProcessor作用

MethodValidationPostProcessor 是 Spring 提供的一个后置处理器,用于在方法调用时对方法参数进行校验。

当将 MethodValidationPostProcessor 添加到 Spring 容器中时,它会自动拦截标注了 @Validated 注解的方法,并在方法调用之前执行参数校验操作。如果方法参数不满足验证约束,则抛出 MethodArgumentNotValidException 异常或 ConstraintViolationException 异常。

使用 MethodValidationPostProcessor 可以方便地在方法级别上实现参数校验,而无需显式调用 Validator 对象进行验证。

在示例中,通过在配置类中定义 MethodValidationPostProcessor 的 bean,将其添加到 Spring 容器中:

@Configuration
public class AppConfig {
    @Bean
    public MethodValidationPostProcessor methodValidationPostProcessor() {
        return new MethodValidationPostProcessor();
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

这样,在使用 @Validated 注解标注的方法中,就可以触发方法参数的校验。例如,在 UserService 中的 createUser 方法上使用 @Validated 注解:

@Service
@Validated
public class UserService {
    public void createUser(@Validated(MyValidationGroupSequence.class) User user) {
        // 创建用户的业务逻辑
    }
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6

}
当调用 createUser 方法时,MethodValidationPostProcessor 会拦截该方法的调用,根据 @Validated 注解和指定的验证分组(MyValidationGroupSequence.class),对 User 对象的属性进行校验。如果校验失败,则会抛出相应的异常。

总而言之,MethodValidationPostProcessor 是一个后置处理器,用于实现方法参数的校验。它简化了在方法层面进行验证的操作,提供了方便的验证机制。

显示调用

如果你不想使用 MethodValidationPostProcessor,而是显式调用 Validator 对象进行验证,可以按照以下步骤进行编写:

首先,需要注入一个 Validator 对象到你的类中。可以使用 LocalValidatorFactoryBean 或者 Validator 接口的其他实现类。

@Autowired
private Validator validator;
  • 1
  • 2

接下来,在方法中手动调用 validator.validate() 方法进行参数校验。假设你的方法名为 createUser,接收 User 对象作为参数。

public void createUser(User user) {
    Set<ConstraintViolation<User>> violations = validator.validate(user, MyValidationGroupSequence.class);
    if (!violations.isEmpty()) {
        // 处理校验失败的情况
        for (ConstraintViolation<User> violation : violations) {
            System.out.println(violation.getMessage());
        }
    }
    // 创建业务逻辑
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10

上述示例中,validator.validate() 方法接受两个参数:要校验的对象 user 和验证分组 MyValidationGroupSequence.class。它会返回一个包含所有校验失败信息的 Set<ConstraintViolation> 集合。

如果集合不为空,说明存在校验失败的情况。可以通过遍历集合中的 ConstraintViolation 对象,获取具体的校验错误信息进行处理。

注意,在使用显式调用 Validator 对象进行验证时,需要自己处理校验失败的情况,并根据实际需求进行后续操作。

最后,确保你已经在 Spring 配置文件(如配置类)中配置了 Validator 的 bean。

@Bean
public Validator validator() {
    LocalValidatorFactoryBean factoryBean = new LocalValidatorFactoryBean();
    factoryBean.setProviderClass(HibernateValidator.class);
    factoryBean.afterPropertiesSet();
    return factoryBean.getValidator();
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7

当然也可以直接使用工厂模式的对象进项校验:

public class Main {
    public static void main(String[] args) {
        ValidatorFactory factory = Validation.buildDefaultValidatorFactory();
        Validator validator = factory.getValidator();

        User user = new User();
        Set<ConstraintViolation<User>> violations = validator.validate(user, MyValidationGroupSequence.class);

        for (ConstraintViolation<User> violation : violations) {
            System.out.println(violation.getMessage());
        }
    }
}
  • 1
  • 2
  • 3
  • 4
  • 5
  • 6
  • 7
  • 8
  • 9
  • 10
  • 11
  • 12
  • 13

以上就是使用显式调用 Validator 对象进行参数验证的方法。通过手动调用 validator.validate() 方法,可以实现对对象的参数校验,并且可以通过检查 ConstraintViolation 集合来处理校验失败的情况。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/不正经/article/detail/310803?site
推荐阅读
相关标签
  

闽ICP备14008679号