问题
I have created a bean validator that I apply to my bean setter method. Instead of getting a JSF validation error, I get an exception raised. Is there a way to make this work, or I should go with a traditional JSF validator?
//Bean Method
public void setGuestPrimaryEmail(@ValidEmail String email){
guest.getEmails().get(0).setValue(email);
}
//Validator interface
@Target({ElementType.FIELD,ElementType.PARAMETER})
@Retention(RetentionPolicy.RUNTIME)
@Constraint(validatedBy = EmailValidator.class)
public @interface ValidEmail {
String message() default "{invalid}";
Class<? extends Payload>[] payload() default {};
Class<?>[] groups() default {};
}
//Validator impl
public class EmailValidator implements ConstraintValidator<ValidEmail, String> {
private Pattern p;
@Override
public void initialize(ValidEmail constraintAnnotation) {
p = java.util.regex.Pattern
.compile("[a-z0-9!#$%&'*+/=?^_`{|}~-]+(?:\\.[a-z0-9!#$%&'*+/=?^_`{|}~-]+)*@(?:[a-z0-9](?:[a-z0-9-]*[a-z0-9])?\\.)+[a-z0-9](?:[a-z0-9-]*[a-z0-9])?");
}
@Override
public boolean isValid(String value, ConstraintValidatorContext context) {
if (DothatUtils.isEmpty(value)) {
return true;
}
boolean invalid = !p.matcher(value).matches();
if (invalid)
return false;
return true;
}
}
Exception:
2013-11-30T20:58:41.747+0000|SEVERE: javax.faces.component.UpdateModelException:
javax.el.ELException: /index.xhtml @144,86 value="....":
javax.validation.ConstraintViolationException: 1 constraint violation(s) occurred during method validation.
Note: I am using GF4 with JSF 2.2.4. If I place my custom annotation on the field, it works as expected.
回答1:
ElementType.PARAMETER
is not recognized by the default JSR303 bean validation provider.
From JSR303 1.0 specification:
2.1 Constraint annotation
...
Constraint annotations can target any of the following
ElementType
s:
FIELD
for constrained attributesMETHOD
for constrained gettersTYPE
for constrained beansANNOTATION_TYPE
for constraints composing other constraintsWhile other
ElementType
s are not forbidden, the provider does not have to recognize and process constraints placed on such types. Built-in types do supportPARAMETER
andCONSTRUCTOR
to allow Bean Validation provider specific extensions. It is considered good practice to follow the same approach for custom annotations.
You really have to put the constraint annotation on the property (identified by ElementType.FIELD
) or on the getter (identified by ElementType.METHOD
). Note that a constrained setter is not supported!
来源:https://stackoverflow.com/questions/20305680/how-can-i-use-method-parameter-level-validation-with-jsf-2-2