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 :

Formulaire, collections et boutons add, remove, etc.


Sujet :

Struts 1 Java

  1. #1
    Modérateur
    Avatar de nouknouk
    Homme Profil pro
    Inscrit en
    Décembre 2006
    Messages
    1 655
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 1 655
    Par défaut Formulaire, collections et boutons add, remove, etc.
    Bonjour,

    faisant suite à ce post (où j'ai finalement dû opter pour l'emploi du javascript, faute d'alternative), j'ai quelques soucis avec mon formulaire composé de collections.

    Un screenshot:

    J'ai une liste d'items (ici composés d'un nom & langue) rangés dans une collection.
    Un unique bouton 'add' permet d'ajouter un nouvel item (des MultiLangStringBean); un bouton 'remove' pour chaque item permet de supprimer l'item correspondant.

    En premier jet, j'avais implémenté une ActionForm contenant une liste d'items:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
     
    public class TestForm  extends ActionForm {
    	public static class MultiLangStringBean implements Serializable {
    		private String lang = "";
    		private String name = "";
    		public get/*...*/
    		public set/*...*/
    	}
     
    	private ArrayList names = new ArrayList();
    	public ArrayList getNames() { return names; }
    	public void setNames(ArrayList names) {this.names = names;}
    La JSP inclut quant à elle des champs 'strutsAction' et 'id'. Ils sont peuplés en javascript lors du clic sur un bouton, et permettent de renseigner quel bouton a été cliqué. La JSP ressemble à ça:
    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
     
    <script language="JavaScript">
    function setAction(action, firstParam, secondParam) {         
    	document.forms[0].strutsAction.value = action;
    	document.forms[0].id.value = firstParam;
    </script>
    <html:form action="/edition/testForm"> 
    	<html:hidden property="strutsAction"/>
    	<html:hidden property="id"/>
    	<html:submit onclick="setAction('addName', '');">
    	      <bean:message key="button.add"/>
    	</html:submit>
           <nested:iterate property="names" indexId="index">
    		<html:submit onclick="setAction('removeName', '${index}');">
    		      <bean:message key="button.remove"/>
    		</html:submit>
    		lang: <nested:text property="lang" size="50"/>
    		name: <nested:text property="name" size="50"/>
    	</nested:iterate>
    	<html:submit onclick="setAction('save', '');">
    		<bean:message key="button.save"/>
    	</html:submit>
    </html:form>
    Voivi le code de l'Action qui est appelé lors du submit (/edition/testForm) et qui fait le bon traitement en fonction de la 'strutsAction' (notamment pour la strutsAction 'addName'):
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
     
    public class TestFormSubmitAction  extends AbstractApplicationAction {
    	public ActionForward execute(/* ...*/) {
    		TestForm testForm = (TestForm)form;
    		/* ... */
    		if (testForm.getStrutsAction().equals("addName")) {
    			testForm.getNames().add(new TestForm.MultiLangStringBean());
    		}
    	}
    Enfin, la définition de l'Action mapping dans le struts-config.xml qui boucle sur la même page (/edition/testForm): lorsque le formulaire est validé l'action renvoie à nouveau vers le formulaire (.edition.testForm) pour continuer l'édition
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
     
    <action path="/edition/testFormSubmit"
    	type="test.TestFormSubmitAction"
    	name="testForm"
    	input=".edition.testForm"
    	validate="true"
    	scope="request">
    	<set-property property="cancellable" value="true"/>
    	<forward name="success" path=".edition.testForm" redirect="true"/>
    </action>
    Problème:
    Ce code ne marche que pour un seul ajout. Si je clique deux fois de suite sur le bouton 'add', le deuxième clic me sort une belle exception:
    Code : Sélectionner tout - Visualiser dans une fenêtre à part
    1
    2
    3
    4
    5
    6
    7
    8
    9
    10
    11
    12
    13
     
    javax.servlet.ServletException: BeanUtils.populate
    org.apache.struts.chain.ComposableRequestProcessor.process(ComposableRequestProcessor.java:286)
    /*...*/
    cause mère:
    javax.servlet.ServletException: BeanUtils.populate
    	org.apache.struts.util.RequestUtils.populate(RequestUtils.java:475)
    /*...*/
    cause mère:
    java.lang.IndexOutOfBoundsException: Index: 1, Size: 1
    	java.util.ArrayList.RangeCheck(Unknown Source)
    	java.util.ArrayList.get(Unknown Source)
    org.apache.commons.beanutils.PropertyUtilsBean.getIndexedProperty(PropertyUtilsBean.java:511)
    Après moults et moults tests dans tous les sens, il semblerait que le formulaire n'arrive pas à gérer son repeuplement lorsque la collection 'names' a changé de taille (ie. lorsque mon code dans TestFormSubmitAction lui a ajouté un item).

    La seule solution actuelle est pour moi de déporter toutes les collections de mon formulaire de la 'form' vers un bean indépendant que je stocke dans la session (request.getSession().setAttribute(monBean)). Ma classe ActionForm ne contenant alors plus qu'une référence vers ce bean externalisé.

    Mais ça ne me paraît vraiment pas propre et ça cause d'autres effets de bord. J'imagine pourtant que ce que j'essaie de faire est loin d'être inhabituel...

    Comment puis-je gérer ce souci ?

    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
    Soit tu mets le scope du form-bean à session dans le mapping des Actions liées à ce form-bean, soit tu utilises les Lazy List.

  3. #3
    Modérateur
    Avatar de nouknouk
    Homme Profil pro
    Inscrit en
    Décembre 2006
    Messages
    1 655
    Détails du profil
    Informations personnelles :
    Sexe : Homme
    Âge : 45
    Localisation : France

    Informations forums :
    Inscription : Décembre 2006
    Messages : 1 655
    Par défaut
    Tout d'abord un immense merci pour ta réponse

    Citation Envoyé par c_nvy Voir le message
    Soit tu mets le scope du form-bean à session dans le mapping des Actions liées à ce form-bean
    J'avais déjà lu ça pendant mes recherches sur le web ; je viens de refaire le test et ça ne change absolument rien chez moi.

    soit tu utilises les Lazy List.
    J'avais également vu ça sur le web et déjà testé ... ou plutôt pensé tester : je viens de faire à nouveau le test en me basant sur les signatures de fonctions données dans ton lien. J'avais visiblement dû mal écrire la signature de mes fonctions (ou en oublier une dans le lot) , car maintenant ça marche du tonnerre.

    EDIT: Peut-être était-ce comme ton lien le précise à cause d'une histoire de bug avec java 1.4 : "but in JDK 1.4 the getter/setter which use the java.util.List are ignored by Bean Utils".

    Quoi qu'il en soit, mille mercis

  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
    De rien.

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

Discussions similaires

  1. Réponses: 4
    Dernier message: 24/11/2005, 09h34
  2. Formulaire avec deux boutons
    Par Oberown dans le forum Langage
    Réponses: 1
    Dernier message: 12/09/2005, 17h06
  3. [FLASH MX2004] Formulaire et le bouton de validation
    Par liam81150 dans le forum Flash
    Réponses: 2
    Dernier message: 22/07/2005, 10h38
  4. Réponses: 2
    Dernier message: 03/02/2005, 08h59
  5. Réponses: 10
    Dernier message: 10/06/2004, 16h20

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