IdentifiantMot de passe
Loading...
Mot de passe oublié ?Je m'inscris ! (gratuit)
Navigation

Inscrivez-vous gratuitement
pour pouvoir participer, suivre les réponses en temps réel, voter pour les messages, poser vos propres questions et recevoir la newsletter

Struts 1 Java Discussion :

code jsp associé à un form-property de type String[] (ou Collection)


Sujet :

Struts 1 Java

  1. #1
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut code jsp associé à un form-property de type String[] (ou Collection)
    Bonjour.

    Lors du submit d'un formulaire, je souhaite récupérer une liste de String dont le nombre peut varier.

    j'ai vu qu'il était possible d'utiliser des propriété de formulaire de type String[] ou Collection :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
     
    <form-bean name="RemplirQuestion" type="blabla.RemplirQuestion">
       <form-property name="reponses" type="java.lang.String[]" />
    </form-bean>
    côté jsp, j'arrive déjà à afficher cette liste à l'aide d'un <c:forEach très classique
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    <c:forEach var="beanReponse" items="${beanQuestion.reponses}">
     <tr>
       <td>${beanReponse.rang}</td>
       <td><input type="text" name="intituleReponse" value="${beanReponse.value}" /></td>
     </tr>
    </c:forEach>

    Mon problème:
    Comment faire en sorte que toutes les réponses soient englobées dans un même attribut de type String[] (ou Collection).

    Merci d'avance!

  2. #2
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    Tu peux ajouter l'attribut varStatus dans le tag c:forEach pour pouvoir utiliser l'index de l'objet courant dans le tag text :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    <c:forEach var="beanReponse" items="${beanQuestion.reponses}" varStatus="status">
     <tr>
       <td>${beanReponse.rang}</td>
       <td><html:text property="reponses[${status.index}]" value="${beanReponse.value}"/></td>
     </tr>
    </c:forEach>

  3. #3
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut
    Bonjour.

    ça me paraît pas mal ce que tu me présentes seulement je sais pas encore si ça marche car après avoir implémenté cette fonctionnalité j'ai des erreur que je n'arrive pas à localiser :'(


    Juste par curiosité, pour les Collection ça marcherait comment?

  4. #4
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    Avec une collection, le fonctionnement est identique.
    Il est d'ailleurs plus pratique d'utiliser une collection plutôt qu'un tableau de String parce que pour un tableau de String, on est obligé de fixer sa longueur, ce qui n'est pas le cas pour une collection.

    Si tu as des erreurs, poste-les.

    Sinon, tu as aussi une solution qui consiste à modifier directement la collection d'objets plutôt que de mettre les champs saisis dans une collection ou un tableau de String à part.

    Avec par exemple les tags nested, si beanQuestion est une propriété de l'ActionForm et si reponses est une collection, propriété de beanQuestion :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    <nested:form action="pathAction">
       <nested:nest property="beanQuestion">
          <nested:iterate property="reponses">
          <tr>
             <td><nested:write property="rang"/></td>
             <td><nested:text property="value"/></td>
          </tr>
          </nested:iterate>
       </nested:nest>
    </nested:form>

  5. #5
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut
    Quand tu dis que c'est identique, c'est qu'à la place d'avoir
    property="reponses[${status.index}]" on se retrouve avec
    property="reponses(${status.index})" ? Sinon je vois pas comment écrire ça



    Si je ne mets pas les erreurs ici c'est que je n'en ai aucune qui apparaît
    Je suis simplement redirigé vers ma page d'erreur générale après avoir enregistré les réponses.
    Avec du débugging j'ai pu cibler le problème:quand mon actionForm est initialisé, je ne sais pas pourquoi la méthode getReponses de mon actionForm est appelé je ne sais comment. étant donné qu'il n'a pas encore été initialisé, j'ai un NullPointerException. Je ne sais pas du tout pourquoi cette méthode est appelée

  6. #6
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    Citation Envoyé par HozakaN Voir le message
    Quand tu dis que c'est identique, c'est qu'à la place d'avoir
    property="reponses[${status.index}]" on se retrouve avec
    property="reponses(${status.index})" ? Sinon je vois pas comment écrire ça
    Il faut l'écrire de la même façon, soit :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    property="reponses[${status.index}]"

    Citation Envoyé par HozakaN Voir le message
    Si je ne mets pas les erreurs ici c'est que je n'en ai aucune qui apparaît
    Je suis simplement redirigé vers ma page d'erreur générale après avoir enregistré les réponses.
    Avec du débugging j'ai pu cibler le problème:quand mon actionForm est initialisé, je ne sais pas pourquoi la méthode getReponses de mon actionForm est appelé je ne sais comment. étant donné qu'il n'a pas encore été initialisé, j'ai un NullPointerException. Je ne sais pas du tout pourquoi cette méthode est appelée
    Utilises-tu toujours une ActionForm dynamique ?
    Avec une ActionForm normale, pour éviter le NullPointerException, il faut initialiser la propriété reponses :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    private String[] reponses=new String[0] ;
    ou
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    private List reponses=new ArrayList() ;

  7. #7
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut
    Il s'agit d'une actionForm normale, mais l'attribut réponse est initialisé.

    J'ai refait quelques tours de debugg en utilisant une Collection à la place d'un tableau de String et j'ai trouvé que c'est la méthode populate(Object, String, HttpServletRequest) de la classe RequestUtils qui entraîne une servletException lorsque l'appel à la méthode getReponses de mon actionForm est faite.

    Dans un ultime espoir voici le code correspondant:

    struts-config form-bean:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    <form-bean name="ModificationQuestion" type="projet.formulaires.PollQuestionModification">
    		<form-property name="intitule" type="java.lang.String" />
    		<form-property name="type" type="java.lang.String" />
    		<form-property name="ordonne" type="java.lang.String" />
    		<form-property initial="*" name="cardMin" type="java.lang.String" />
    		<form-property initial="*" name="cardMax" type="java.lang.String" />
    		<form-property name="reponses" type="java.util.Collection" />
    </form-bean>
    struts-config action-mapping :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    <action path="/ModificationQuestion"
    		name="ModificationQuestion" 
    		type="projet.actions.PollQuestionModificationAction"
    		input="/WEB-INF/jsp/modifierQuestion.jsp"
    		validate="true"
    		scope="request" >
    	<forward name="success"
    			path="/WEB-INF/jsp/modifierSondage.jsp" />
    	<forward name="fail"
    			path="/WEB-INF/jsp/modifierQuestion.jsp" />
    </action>
    actionForm:

    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
    14
    15
    16
    17
    18
    19
    20
    21
    22
    23
    24
    25
     
     private String type;
     private String ordonne;
     private String cardMax;
     private Collection reponses = new ArrayList();
     
      public Collection getReponses() {
        System.out.println("PollModificationQuestion getReponses");
        return reponses;
      }
     
      public void setReponses(Collection reponses) {
        System.out.println("PollModificationQuestion set réponse");
        this.reponses = reponses;
      }
     
      public void setType(String type) {
        System.out.println("PollModificationQuestion setType");
        this.type = type;
      }
     
      public void setCardMax(String cardMax) {
        System.out.println("PollModificationQuestion setCardMax");
        this.cardMax = cardMax;
      }
    jsp:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
     
    <c:forEach var="beanReponse" items="${beanQuestion.reponses}" varStatus="status">
      <tr>
        <td>${beanReponse.rang}</td>
        <td><html:text property="reponses[${status.index}]" value="${beanReponse.value}" /></td>
      </tr>
    </c:forEach>
    Les System.out me permettent de voir que 4 méthodes sont appelées: setType, setIntitule, setCardMax, getReponses.
    Au debugging, la valeur de la première réponse est récupérée, l'attribut reponses de mon actionForm est bien initialisé.


    Si quelqu'un voit quelque chose de pas normal...
    En tout cas j'apprécie énormément l'aide déjà apportée

  8. #8
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    Tu dis utiliser une ActionForm normale et tu déclares quand même les propriétés de l'ActionForm dans le struts-config.xml.
    Je ne vois pas bien l'intérêt.

    Sinon, après réflexion, dans ce cas précis, il vaut mieux utiliser un tableau de String.
    Et pour ne plus avoir d'exception, il faudrait initialiser la taille de ce tableau de String avec la taille de la collection reponses du bean beanQuestion dans l'Action qui s'exécute avant l'affichage du formulaire.
    Cela t'oblige à lier cette Action au form-bean ModificationQuestion et à passer le scope du form-bean à session dans le mapping des Actions liées à ce form-bean.

    Et pour initialiser le tableau de String avec la bonne taille :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    PollQuestionModification modificationQuestion  = (PollQuestionModification) form ;
    modificationQuestion.setReponses(new String[reponses.size()]);

  9. #9
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut
    Citation Envoyé par c_nvy Voir le message
    Tu dis utiliser une ActionForm normale et tu déclares quand même les propriétés de l'ActionForm dans le struts-config.xml.
    Je ne vois pas bien l'intérêt.
    Bah c'est struts qui se charge de faire appel aux setteurs de l'actionForm et d'appeler la méthode validate(). Si je ne déclare pas les propriétés de l'actionForm dans struts, il ne peut pas faire appel aux setteurs non?

  10. #10
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    Soit tu utilises une ActionForm dynamique (DynaActionForm) et dans ce cas, tu définis les propriétés dans les balises form-property dans le struts-config.xml et dans ce cas, tu n'as pas besoin de créer une classe qui hérite d'ActionForm.
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    <form-bean name="maForm" type="org.apache.struts.action.DynaActionForm">
       <form-property name="propriete1" type="java.lang.String"/>
    </form-bean>
    Soit tu utilises une ActionForm normale et dans ce cas, tu crées une classe qui hérite d'ActionForm et tu y définis les propriétés avec leurs getters et setters.

    A partir du moment où tu veux faire une validation via la méthode validate, tu dois créer une ActionForm.
    Dans ce cas, tu n'as aucune raison de définir les propriétés dans les balises form-property du struts-config.xml.
    C'est d'ailleurs source d'erreur de définir les propriétés à la fois dans l'ActionForm et dans les balises form-property. Dans le cas où tu renommes une propriété, il faut penser à la modifier dans les 2.

  11. #11
    Membre confirmé
    Profil pro
    Inscrit en
    Mai 2009
    Messages
    104
    Détails du profil
    Informations personnelles :
    Localisation : France, Puy de Dôme (Auvergne)

    Informations forums :
    Inscription : Mai 2009
    Messages : 104
    Par défaut
    J'ai enfin réussi à faire marcher tout ça!

    Avec l'aide apportée il y a eu pas mal de changement.
    Au final, c'est en changeant la property des input text dans la boucle jsp que j'ai réussi: pour tous mes input, la property reste la même

    On a donc à la place de
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    property="reponses[${status.index}]"
    Les différents fichiers ressemblent donc maintenant à ça

    form-bean de struts-config.xml :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
     
    <form-bean name="ModificationQuestion" type="org.apache.struts.action.DynaActionForm">
    	<form-property name="intitule" type="java.lang.String" />
    	<form-property name="reponses" type="java.lang.String[]" />
    </form-bean>
    action-mapping de struts-config.xml :
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    <action path="/ModificationQuestion"
    				name="ModificationQuestion" 
    				type="blabla.PollQuestionModificationAction"
    				input="/WEB-INF/jsp/modifierQuestion.jsp"
    				validate="false"
    				scope="request" >
    			<forward name="success"
    					 path="/WEB-INF/jsp/modifierSondage.jsp" />
    			<forward name="fail"
    					 path="/WEB-INF/jsp/modifierQuestion.jsp" />
    		</action>
    l'actionForm a disparu

    je récupère les valeurs du sondage directement dans l'action de la manière suivante:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    DynaActionForm dform = (DynaActionForm) form;
    String[] reponses = (String[]) dform.get("reponses");
    J'ai créé une méthode validate dans l'action afin de remplacer celle disparue de l'actionForm disparu.
    Selon qu'il y ait des erreurs retournées ou non j'effectue un forward vers "success" ou "fail"


    Merci pour l'aide apportée

  12. #12
    Expert confirmé

    Femme Profil pro
    Inscrit en
    Juillet 2005
    Messages
    5 793
    Détails du profil
    Informations personnelles :
    Sexe : Femme
    Localisation : France

    Informations forums :
    Inscription : Juillet 2005
    Messages : 5 793
    Par défaut
    C'est cool que ça fonctionne enfin.

    A ta place, j'aurais plutôt utilisé une ActionForm normale et sa méthode validate, ou bien une DynaValidatorForm, si toutefois les cas de validation sont simples, à la place d'une DynaActionForm et la validation dans l'Action.

+ Répondre à la discussion
Cette discussion est résolue.

Discussions similaires

  1. Réponses: 0
    Dernier message: 12/03/2014, 09h38
  2. Tuto MVVM : dans le source, une property de type string retourne un booléen ?!
    Par zax-tfh dans le forum Windows Presentation Foundation
    Réponses: 5
    Dernier message: 23/03/2009, 08h35
  3. [VB.NET;C#) Associer du code C#.NET à un form VB.NET ?
    Par beegees dans le forum Windows Forms
    Réponses: 4
    Dernier message: 23/06/2006, 10h06
  4. [STRUTS][JSP] html:file et property value
    Par Wavyx dans le forum Struts 1
    Réponses: 3
    Dernier message: 21/10/2005, 16h34
  5. [Debutant(e)]Générer du code JSP dynamiquement
    Par Gibier dans le forum Servlets/JSP
    Réponses: 6
    Dernier message: 16/01/2004, 11h54

Partager

Partager
  • Envoyer la discussion sur Viadeo
  • Envoyer la discussion sur Twitter
  • Envoyer la discussion sur Google
  • Envoyer la discussion sur Facebook
  • Envoyer la discussion sur Digg
  • Envoyer la discussion sur Delicious
  • Envoyer la discussion sur MySpace
  • Envoyer la discussion sur Yahoo