两个日期字段之间的Spring验证?

scyqe7ek  于 5个月前  发布在  Spring
关注(0)|答案(4)|浏览(47)

在我的Spring应用程序中,我使用Hibernate Validator进行验证。
当我做简单的验证,如@NotEmpty@Email ..我很容易工作
但是当进入日期字段时,给出问题.
问题是,在我的JSP页面,我得到的值类型为字符串,然后我将字符串转换为日期。
听是我的榜样……

@NotEmpty(message = "Write Some Description")
private String description;

private String fromDateMonth;

private String fromDateYear;

private String toDateMonth;

private String toDateYear;

字符串
我在我的Controller类中将fromDateMonthfromDateYear转换为Date。
那么他们是否有可能在Controller类中添加Validator Annotation呢?
其他明智的我应该做什么听到?给予我的建议.

gcmastyq

gcmastyq1#

如果你想验证fromDate在toDate之前,你可以写一个自定义的验证器来执行这个多字段验证。你写一个自定义的验证器,你还定义了一个自定义的annotation,它被放置在被验证的bean上。
有关详细信息,请参阅以下答案。

mtb9vblg

mtb9vblg2#

根据问题显示的次数,我得出结论,很多人仍然在这里寻找一个日期范围的验证器。
假设我们有一个DTO包含另一个DTO(或带有@Embeddable注解的类),其中两个字段带有LocalDate(或其他日期表示,这只是示例)。

class MyDto {

    @ValidDateRange // <-- target annotation
    private DateRange dateRange;
    
    // getters, setters, etc.
}

个字符
现在,我们可以声明自己的@ValidDateRange注解:

@Documented
@Constraint(validatedBy = DateRangeValidator.class)
@Target({ElementType.FIELD})
@Retention(RetentionPolicy.RUNTIME)
@interface ValidDateRange {

    String message() default "Start date must be before end date";

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

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


编写验证器本身也可以归结为几行代码:

class DateRangeValidator implements ConstraintValidator<ValidDateRange, DateRange> {
    @Override
    public boolean isValid(DateRange value, ConstraintValidatorContext context) {
        return value.getStartOfRange().isBefore(value.getEndOfRange());
    }
}

2guxujil

2guxujil3#

为了确保您可以在控制器中使用Bean验证,只需像在模型中那样在属性上添加一个注解。但最好的方法是在模型中使用Date类型而不是string。

3qpi33ja

3qpi33ja4#

参考:https://blog.tericcabrel.com/write-custom-validator-for-body-request-in-spring-boot/
创建DateRange标注

@Constraint(validatedBy = DateRangeValidator.class)
@Target({ElementType.TYPE, ElementType.FIELD, ElementType.ANNOTATION_TYPE})
@Retention(RetentionPolicy.RUNTIME)
@Documented

public @interface DateRange {
    String message() default "{mob.concept.admin.models.constraint.DateRange.message}";

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

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

    String before();

    String after();
}

字符串

创建验证器约束

public class DateRangeValidator implements ConstraintValidator<DateRange, Object> {
    private String beforeFieldName;
    private String afterFieldName;

    @Override
    public void initialize(DateRange constraintAnnotation) {
        beforeFieldName = constraintAnnotation.before();
        afterFieldName = constraintAnnotation.after();
    }

    @Override
    public boolean isValid(final Object value, ConstraintValidatorContext context) {
        try {
            final Field beforeDateField = value.getClass().getDeclaredField(beforeFieldName);
            beforeDateField.setAccessible(true);

            final Field afterDateField = value.getClass().getDeclaredField(afterFieldName);
            afterDateField.setAccessible(true);

            final LocalDate beforeDate = (LocalDate) beforeDateField.get(value);
            final LocalDate afterDate = (LocalDate) afterDateField.get(value);
            return beforeDate.isEqual(afterDate) || beforeDate.isBefore(afterDate);

        } catch (NoSuchFieldException | IllegalAccessException ignored) {
            return false;
        }
    }
}

示例

@DateRange(before = "startDate", after = "endDate", message = "Start date should be less than end date")
public class OfferDto {
    @NotNull(message = "offer title required")
    @Size(max = 20, min = 8, message = "Offer title must be between 8 and 20 characters")
    private String offerTitle;
    @Size(max = 100, min = 8, message = "Offer title must be between 8 and 100 characters")
    @NotNull(message = "offer description required")
    private String description;
    @NotNull(message = "start date is required")
    private LocalDate startDate;
    @NotNull(message = "end date is required")
    private LocalDate endDate;
    @NotNull(message = "discount is required")
    private Float discount;
    @NotNull(message = "offer type is required")
    @EnumValidation(enumsClass = OfferType.class)
    private String offerType;
}

相关问题