Bonjour à tous,
J'utilise un formulaire à pages multiples. Ma première page contient des listes déroulantes alimentées par Hibernate. Par exemple, une liste d'"initiatives" et de "satisfactions". La valeur du select est un identifiant (retourné en string dans le request) et je dois récupérer un objet de type Initiative et un objet de type Satisfaction.
J'arrive au résultat désiré en utilisant "PropertyEditorSupport".
Ne peut-on pas utiliser le binding comme pour une page simple ? Cela implique d'écrire des propertyEditorSupport pour chaque champs de type select..
Voici la méthode testée avec le Binder :
Un morceau de mon controller :
Voici l'erreur :
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
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42 @Override protected void initBinder(HttpServletRequest request, ServletRequestDataBinder binder) throws Exception { Rapport rap = (Rapport)binder.getTarget(); DateFormat df = new SimpleDateFormat("dd/MM/yyyy"); df.setLenient(false); binder.registerCustomEditor(Date.class, new CustomDateEditor(df, true)); try { long initId = Long.parseLong(request.getParameter("initiative")); if(initId > 0) { Initiative init = this.initiativManager.getObjById(initId); rap.setInitiative(init); } }catch(Exception e){System.out.println(e.getMessage());} } @Override protected Map referenceData(HttpServletRequest request, Object command, Errors errors, int page) throws Exception { Map<Object, Object> dataMap = new HashMap<Object, Object>(); initiativManager.loadClass(Initiative.class); dataMap.put("initiList",this.initiativManager.getList()); return dataMap; } protected void validatePage(Object command, Errors errors, int page){ Rapport rap = (Rapport) command; System.out.println("nb erreurs : " + errors.getErrorCount()); if(page == 0){ if(rap.getSubject()==""){ errors.rejectValue("subject", "error.too-high", null, "Le sujet ne peut être vide."); } if(rap.getInitiative() == null){ errors.rejectValue("initiative", "error.too-high", null, "Vous devez choisir une option."); } } }
Pourtant dans le validatePage, grâce à l'initBinder que j'ai réécrit, je n'ai pas l'erreur "Vous devez choisir une option", lorsque j'interroge rap.getInitiative().getName() , j'ai bien la bonne valeur issue du formulaire...
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2 Failed to convert property value of type [java.lang.String] to required type [pjx.bean.Initiative] for property initiative; nested exception is java.lang.IllegalArgumentException: Cannot convert value of type [java.lang.String] to required type [pjx.bean.Initiative] for property initiative: no matching editors or conversion strategy found
J'ai tenté aussi de faire le bind dans la méthode onBindAndValidate, mais même chose..
Maintenant, la méthode utilisant le PropertyEditorSupport :
Avec ceci :
Code : Sélectionner tout - Visualiser dans une fenêtre à part
1
2
3
4
5
6
7
8
9
10
11
12
13
14 @Override protected void initBinder(HttpServletRequest request, ServletRequestDataBinder binder) throws Exception { Rapport rap = (Rapport)binder.getTarget(); DateFormat df = new SimpleDateFormat("dd/MM/yyyy"); df.setLenient(false); binder.registerCustomEditor(Date.class, new CustomDateEditor(df, true)); InitiativeTypePropertyEditor initTpe = new InitiativeTypePropertyEditor(); initTpe.setInitiativManager(initiativManager); binder.registerCustomEditor(Initiative.class,initTpe); }
Plus d'erreur, mais lorsque mon formulaire est de nouveau appelé (erreur sur un autre champs ou autre raison), la valeur du select est perdue, il se repositionne sur "Choisissez une option" plutôt que l'option elle même déjà enregistrée.
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 public class InitiativeTypePropertyEditor extends PropertyEditorSupport{ private CommonManager<Initiative> initiativManager; public CommonManager<Initiative> getInitiativManager(){ return initiativManager; } public void setInitiativManager(CommonManager<Initiative> manag){ initiativManager = manag; } public void setAsTest(String text) { } @Override public void setAsText(String arg0) throws IllegalArgumentException { Initiative init = initiativManager.getObjById(Long.parseLong(arg0)); this.setValue(init); } }
Pourriez-vous me dire quel est le meilleur procédé ?
Merci d'avance
Partager