There does not seem to be any annotation to specify constraints like a key must exist in a Map.
This can be solved by implementing a custom constraint:
@Target({ METHOD, FIELD, ANNOTATION_TYPE, CONSTRUCTOR, PARAMETER })
@Retention(RUNTIME)
@Documented
@Constraint(validatedBy = { ContainsKeyValidator.class })
public @interface ContainsKeys {
String message() default "{com.acme.ContainsKey.message}";
Class<?>[] groups() default { };
Class<? extends Payload>[] payload() default { };
String[] value() default {};
}
And a validator like this:
public class ContainsKeysValidator implements ConstraintValidator<ContainsKeys, Map<?, ?>> {
String[] requiredKeys;
@Override
public void initialize(ContainsKeys constraintAnnotation) {
requiredKeys = constraintAnnotation.values();
}
@Override
public boolean isValid(Map<?, ?> value, ConstraintValidatorContext context) {
if( value == null ) {
return true;
}
for( String requiredKey : requiredKeys ) {
if( value.containsKey( requiredKey ) ) {
return false;
}
}
return true;
}
}
My use case is that some map keys are required to have valid values only if some other property of the bean is set to true.
For this requirement you could implement a class-level constraint, which allows to access the complete bean with all its attributes in the validator implementation.