Is there an implementation of (or third-party implementation for) cross field validation in Hibernate Validator 4.x? If not, what is the cleanest way to implement a cross fi
Very nice solution bradhouse. Is there any way to apply the @Matches annotation to more than one field?
EDIT: Here's the solution I came up with to answer this question, I modified the Constraint to accept an array instead of a single value:
@Matches(fields={"password", "email"}, verifyFields={"confirmPassword", "confirmEmail"})
public class UserRegistrationForm {
@NotNull
@Size(min=8, max=25)
private String password;
@NotNull
@Size(min=8, max=25)
private String confirmPassword;
@NotNull
@Email
private String email;
@NotNull
@Email
private String confirmEmail;
}
The code for the annotation:
package springapp.util.constraints;
import static java.lang.annotation.ElementType.*;
import static java.lang.annotation.RetentionPolicy.*;
import java.lang.annotation.Documented;
import java.lang.annotation.Retention;
import java.lang.annotation.Target;
import javax.validation.Constraint;
import javax.validation.Payload;
@Target({TYPE, ANNOTATION_TYPE})
@Retention(RUNTIME)
@Constraint(validatedBy = MatchesValidator.class)
@Documented
public @interface Matches {
String message() default "{springapp.util.constraints.matches}";
Class>[] groups() default {};
Class extends Payload>[] payload() default {};
String[] fields();
String[] verifyFields();
}
And the implementation:
package springapp.util.constraints;
import javax.validation.ConstraintValidator;
import javax.validation.ConstraintValidatorContext;
import org.apache.commons.beanutils.BeanUtils;
public class MatchesValidator implements ConstraintValidator {
private String[] fields;
private String[] verifyFields;
public void initialize(Matches constraintAnnotation) {
fields = constraintAnnotation.fields();
verifyFields = constraintAnnotation.verifyFields();
}
public boolean isValid(Object value, ConstraintValidatorContext context) {
boolean matches = true;
for (int i=0; i