Reputation: 946
i want to validate my username using a select. if the username already is present in the database, validation fails.
i found some annotations for primefaces like this for example:
@Size(min=2,max=5)
private String name;
i didnt found a annotation solution for something like this:
try {
dao.findUserByUserName(userName);
message = new FacesMessage ("Invalid username!", "Username Validation Error");
message.setDetail("Username already exists!");
message.setSeverity(FacesMessage.SEVERITY_ERROR);
throw new ValidatorException(message);
} catch (NoSuchUserException e) {}
Do i have to use a custom validator or are there annotations for it?
Upvotes: 1
Views: 2303
Reputation: 1109532
Do i have to use a custom validator or are there annotations for it?
It can be done both ways.
In case of a custom JSF validator, you only need to understand that an EJB cannot be injected in a @FacesValidator
. You've basically 3 options:
@ManagedBean
instead of @FacesValidator
@EJB
and @Inject
in @FacesValidator
Ultimately, you can end up like this, assuming that you went for the @ManagedBean
approach:
@ManagedBean
@RequestScoped
public class UsernameValidator implements Validator {
@EJB
private UserService service;
public void validate(FacesContext context, UIComponent component, Object submittedValue) throws ValidatorException {
if (submittedValue == null) {
return; // Let required="true" handle.
}
String username = (String) submittedValue;
if (service.exist(username) {
throw new ValidatorException(new FacesMessage("Username already in use, choose another"));
}
}
}
Which is used as follows:
<h:inputText ... validator="#{usernameValidator}" />
In case of JSR303 bean validation, you'd need to create a custom @Constraint
annotation along with a custom ConstraintValidator
. You need to make sure that you're using at least CDI 1.1, otherwise you can't inject an EJB in a ConstraintValidator
and you'd need to resort to manually grabbing it from JNDI in initialize()
method. You can't solve it by making it a managed bean and even OmniFaces hasn't any magic for this.
E.g.
@Constraint(validatedBy = UsernameValidator.class)
@Documented
@Retention(RetentionPolicy.RUNTIME)
@Target({ElementType.FIELD, ElementType.METHOD, ElementType.ANNOTATION_TYPE})
public @interface Username {
String message() default "Username already in use, choose another";
Class<?>[] groups() default {};
Class<? extends Payload>[] payload() default {};
}
with
public class UsernameValidator implements ConstraintValidator<Username, String> {
@EJB
private UserService service;
@Override
public void initialize(Username constraintAnnotation) {
// If not on CDI 1.1 yet, then you need to manually grab EJB from JNDI here.
}
Override
public boolean isValid(String username, ConstraintValidatorContext context) {
return !service.exist(username);
}
}
and in model
@Username
private String username;
Upvotes: 6