Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Validation on enum in spring request

I have a request WorkerRequest in which there is an enum which has FULL_TIME, MANAGER and so on.

In WorkerRequest how can I apply the length validation on this enum?

Example: enum type should not be greater than 8 characters.

FULL_TIME valid (8 characters)

PERMANENT invalid (9 characters)

Currently if I put javax.validation.constraints.Size

  @Size(min = 0, max = 8, message = "Allowed length for workerType is 8.")
  @Enumerated(EnumType.STRING)
  private WorkerType workerType;

it throws an error :

HV000030: No validator could be found for constraint 'javax.validation.constraints.Size' validating type 'com.XX.XX.XX.WorkerType'. Check configuration for 'workerType'

like image 608
Mehraj Malik Avatar asked Oct 17 '22 13:10

Mehraj Malik


1 Answers

As described in Difference between @Size, @Length and @Column(length=value)

@Size is a Bean Validation annotation that validates that the associated String has a value whose length is bounded by the minimum and maximum values.

You can only specify the the maximum required length for persisting enum value in your db. For example, if you define @Column(length = 8) instead of @Size you will see workerType VARCHAR(8) in your db definition correspondingly.

But there is a workaround for it: suppose you have

 public enum WorkerType {PERMANENT , FULL_TIME, ...}; 
  1. Define a custom validation annotation:

    @Target(ElementType.FIELD)
    @Retention(RetentionPolicy.RUNTIME)
    @Constraint(validatedBy = EnumSizeLimit.class)
    public @interface EnumSizeLimit {
        String message() default "{com.example.app.EnumSizeLimit.message}";
        Class<?>[] groups() default {};
        Class<? extends Payload>[] payload() default {};
        Class<? extends Enum<?>> targetClassType();
    }
    
  2. Implement a Validator:

    public class EnumSizeLimitValidator implements ConstraintValidator < EnumSizeLimit , String > {
         private Set < String > allowedValues;
    
         @SuppressWarnings({
             "unchecked",
             "rawtypes"
         })
        @Override
        public void initialize(EnumSizeLimit targetEnum) {
        Class << ? extends Enum > enumSelected = targetEnum.targetClassType();
        allowedValues = (Set < String > ) EnumSet.allOf(enumSelected).stream().map(e - > ((Enum << ? extends Enum << ? >> ) e).name())
            .collect(Collectors.toSet());
        }
    
        @Override
        public boolean isValid(String value, ConstraintValidatorContext context) {
            return value == null || (value.length>=0 && value.length<=8)) ? true : false;
        }
    }
    
  3. Define Field:

    @EnumSizeLimit (targetClassType = WorkerType.class, message = "your message" 
    private String workerType; 
    
like image 59
MohammadReza Alagheband Avatar answered Nov 15 '22 07:11

MohammadReza Alagheband