如何为同一属性节点添加多个约束违规?

问题描述 投票:0回答:1

我有一个自定义的ConstraintValidator。我想做的是为同一属性节点,同一条消息和不同的动态有效负载添加多个约束违例。这可能吗?

自定义注释:

@Target(ElementType.FIELD)
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = CustomFieldConstraintValidator.class)
public @interface CustomFieldConstraint {
    String message() default "message";

    Class<?>[] groups() default {};

    Class<? extends Payload>[] payload() default {};
}

自定义约束验证器:

public class CustomFieldConstraintValidator implements ConstraintValidator<CustomFieldConstraint, Integer> {
    @Override
    public boolean isValid(Integer value, ConstraintValidatorContext context) {
        var valid = true;
        var hibernateConstraintValidatorContext = context.unwrap(HibernateConstraintValidatorContext.class);
        hibernateConstraintValidatorContext.disableDefaultConstraintViolation();

        if (value > 0) {
            valid = false;

            hibernateConstraintValidatorContext.withDynamicPayload(Map.of("must_be_less_than", 0))
                .buildConstraintViolationWithTemplate(context.getDefaultConstraintMessageTemplate())
                .addPropertyNode("field")
                .addConstraintViolation();
        }

        if (value > 5) {
            valid = false;

            hibernateConstraintValidatorContext.withDynamicPayload(Map.of("must_be_less_than", 5))
                .buildConstraintViolationWithTemplate(context.getDefaultConstraintMessageTemplate())
                .addPropertyNode("field")
                .addConstraintViolation();
        }

        return valid;
    }
}

验证程序测试:

public class HibernateValidatorTest {
    private final Validator validator = Validation.buildDefaultValidatorFactory().getValidator();

    @Test
    void multipleFailuresForSameField() {
        var foo = new Foo(10);

        var constraintViolations = validator.validate(foo);

        assertEquals(2, constraintViolations.size());
    }

    public static class Foo {
        @CustomFieldConstraint
        private int field;

        public Foo(int field) {
            this.field = field;
        }
    }
}

测试失败,并显示expected: <2> but was: <1>

java hibernate-validator
1个回答
0
投票

您有这个问题,因为ConstraintViolation作为一个集合返回,并且根据设计,动态有效载荷不包含在equals()方法中。参见https://github.com/hibernate/hibernate-validator/blob/master/engine/src/main/java/org/hibernate/validator/internal/engine/ConstraintViolationImpl.java#L251

因此,您的2个约束在Set级别上相等。

您需要更改处理方式,并同时使用两种信息来丰富有效负载。

© www.soinside.com 2019 - 2024. All rights reserved.