2009-07-24 9 views
4

J'ai un validateur JSF qui vérifie si une chaîne de numéro de conteneur est conforme à la spécification ISO-6346.JSF: Accès au bean à partir du validateur via le champ

Cela fonctionne très bien, mais j'ai besoin d'ajouter un traitement conditionnel basé sur d'autres valeurs dans le bean d'où provient le numéro de conteneur. Ce haricot peut être de plusieurs types différents.

Y a-t-il un moyen d'accéder au Bean dans le validateur et d'y effectuer des opérations? Idéalement, j'aimerais le garder en tant que validateur, mais s'il n'y a pas de solution, je devrai implémenter la logique dans le Bean avant de persister.

Je pense quelque chose le long des lignes de:

public class ContainerNumberValidator implements javax.faces.validator.Validator { 
    public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException { 

     Object bean = UIComponent.getMyBeanSomehowThroughAMagicMethod(); 
     if(bean instanceof BeanA) { 
     //do this 
     } else if(bean instanceof BeanB) { 
     //do that 
     } 
} 

MISE À JOUR: À bien des égards est un problème similaire à la validation de plusieurs champs en même temps. This code par BalusC est utile.

Très apprécié.

D.

Répondre

5

Utilisation du < f:attribute> vous pouvez passer un Bean au validateur et le récupérer à partir du composant comme une expression de valeur.

Donc, mon entrée est comme celui-ci (elle doit utiliser <f:validator> et non l'attribut validateur sur le <h:inputText>):

<h:inputText id="containerNum" size="20" maxlength="20" value="#{containerStockAction.containerStock.containerNumber}"> 
    <f:validator validatorId="containerNumberValidator" /> 
    <f:attribute name="containerBean" value="#{containerStockAction.containerStock}"/> 
</h:inputText> 

Et ma classe de validateur:

public void validate(FacesContext context, UIComponent component, Object value) throws ValidatorException { 
    String containerNumber = (String)value; 
    Object containerBean = component.getValueExpression("containerBean").getValue(context.getELContext()); 

    if(containerBean instanceof BeanA) { 
    //do this 
    } 
+0

Une alternative consiste à obtenir la carte d'attributs directement à partir du composant. Combinez-le avec une interface pour vos affaires et il pourrait être aussi simple que cela ... ISOBean bean = (ISOBean) component.getAttribute ("containerBean"); bean.doStuff(); – Drew

2

Vous pouvez utiliser ce qui suit pour obtenez n'importe quel vieux haricot que vous aimez en utilisant le FacesContext. Très similaire à la solution que vous avez trouvée.

public void validate(FacesContext context, UIComponent component, Object value) 
{ 
    Application app = context.getApplication(); 

    ValueExpression expression = app.getExpressionFactory().createValueExpression(context.getELContext(), 
      "#{thingoBean}", Object.class); 

    ThingoBean thingoBean = (ThingoBean) expression.getValue(context.getELContext()); 
} 
+0

Merci. Si vous utilisez Seam, vous pouvez faire la même chose avec ThingoBean thingoBean = (ThingoBean) Component.getInstance ("thingoBean"); Cependant, en utilisant cette approche, je ne peux pas réutiliser le validateur pour différents beans. – Damo

Questions connexes