Java 303/349 开始日期早于结束日期验证

标签 java validation bean-validation

与按以下方式编写类级别 ConstraintValidator 相比,是否有更好的方法来编写 Java validator 来确保开始日期早于结束日期:

// VALIDATOR IMPLEMENTATION

    public class StartBeforeEndDateValidator implements ConstraintValidator<StartBeforeEndDateValid, Object> {

        // cannot use LocalDate here...
        private String start;
        private String end;

        @Override
        public void initialize(final StartBeforeEndDateValid annotation) {
            start = annotation.start();
            end = annotation.end();

        }

        @Override
        public boolean isValid(final Object bean, final ConstraintValidatorContext context) {
            try {
                final String startDateStr = BeanUtils.getProperty(bean, start);
                final String endDateStr = BeanUtils.getProperty(bean, end);

                final LocalDate startDate = new LocalDate(startDateStr);
                final LocalDate endDate = new LocalDate(endDateStr);

                return !startDate.isAfter(endDate);
            } catch (final Exception e) {
                return false;
            }
        }
    }


// USAGE
    @StartBeforeEndDateValid(start = "startDate", end = "endDate")
    @Entity
    public class MyBean {

        @NotNull
        @Type(type = "org.jadira.usertype.dateandtime.joda.PersistentLocalDate")
        private LocalDate startDate;

        @Type(type = "org.jadira.usertype.dateandtime.joda.PersistentLocalDate")
        private LocalDate endDate;

        ... 
    }

我真的不喜欢这样的事实:我必须使用反射从 bean 中提取 2 个日期对象。不幸的是,据我所知,验证规范没有指定仅设置您想要从 bean 验证的值的方法。

最佳答案

一种方法是向 MyBean 添加接口(interface)

public interface StartEndDateable {
   public LocalDate getStartDate();
   public LocalDate getEndDate();
}

public class MyBean implements StartEndDatable {
...

然后您可以将 ConstraintValidator 上的泛型类型设置为新接口(interface)而不是 Object。

public class StartBeforeEndDateValidator implements ConstraintValidator<StartBeforeEndDateValid, StartEndDatable> {

    @Override
    public void initialize(StartBeforeEndDateValid annotation) {
    }

    @Override
    public boolean isValid(StartEndDatable bean, ConstraintValidatorContext context) {
        final LocalDate startDate = bean.getStartDate();
        final LocalDate endDate = bean.getEndDate();

        return !startDate.isAfter(endDate);
    }
}

显然,您想要验证开始和结束日期的任何类都必须实现 StartEndDateable (我知道,这不是最好的名称,但我相信您可以想出更好的方法)并定义 getStartDategetEndDate 方法。

关于Java 303/349 开始日期早于结束日期验证,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/33873163/

相关文章:

javascript - Angularjs 字段仅在其值大于零时有效

java - 复杂对象的验证

java - 如何在DAO中并发使用Spring Validation Annotation(Bean Validation Specification)

java - 字符串 replaceAll 方法 (Java)

java - 谷歌 Guava 嵌套木工

html - 是否可以嵌套 HTML 注释?

java - 在 Spring MVC 中使用 JSR-303 注释进行条件验证

java - Android 2.2 应用程序的 OnPreferenceChangeListener.onPreferenceChange 方法中 @Override 的不同行为取决于源代码级别

java - 使用 java 流将包含标题和行的 csv 文件转换为 hashmap 数组

java - 如何从 ConstraintValidator.isValid 方法访问叶或根 bean?