7 Replies Latest reply on Apr 18, 2008 8:08 AM by Paata Lominadze

    Seam,A4J,Selectonemenus and Validation(Rich:Message)

    Paata Lominadze Newbie

      hello,


      i have two selectonemenu, first is parent and second is child, both of them must be required.


      i use jboss seam(2.0) framework with richfaces (3.4.1).


      my task is create ajax wizard (i found example about it into richfaces examples), on first page i have two selectonemenus, which i described above.
      everything works fine except messaging for requirement.
      my code snippets :



      <table>
      <tr>
      <td> 
      <h:selectOneMenu id="dbType" styleClass="LoginLangCombo" value="#{dbparams.dbVendor}">
           <s:selectItems value="#{dbVendors.resultList}" var="vendor" label="#{vendor.dbvendorname}" />
           <s:convertEntity />
           <a4j:support event="onchange" reRender="dbType,dbDriverid" bypassUpdates="false"/>
      </h:selectOneMenu>
      </tr>
      <tr>
      <td>
      <h:selectOneMenu id="dbDriverid" styleClass="LoginLangCombo" value="#{dbparams.dbDriver}">
           <s:selectItems value="#{dbDrivers.resultList}" var="driver" label="#{driver.dbDriverName}"/>
           <s:convertEntity />
           <f:validator validatorId="SelectValidator"/>
      </h:selectOneMenu>
      <rich:message for="dbDriverid"
           ajaxRendered="true"
           tooltip="true" 
           showDetail="false" 
           showSummary="true" 
           passedLabel="No Error"
           errorLabelClass="errorLabel"
           fatalLabelClass="warnLabel"
           infoLabelClass="infoLabel"
           warnLabelClass="fatalLabel"
           title="this is tooltip">                                                        
           <f:facet name="errorMarker">
                <h:graphicImage url="/img/error.gif"/>
           </f:facet>                            
           <f:facet name="fatalMarker">
                <h:graphicImage url="/img/fatal.gif"/>
           </f:facet>                            
           <f:facet name="infoMarker">
                <h:graphicImage url="/img/info.gif"/>
           </f:facet>                            
           <f:facet name="warnMarker">
                <h:graphicImage url="/img/warn.gif"/>
           </f:facet>                            
           <f:facet name="passedMarker">
                <h:graphicImage url="/img/passed.gif"/>
           </f:facet>
      </rich:message>
      </td>
      </tr>
      </table>
      


      2.Selectonemenu Validator


      public class SelectValidator implements Validator {
      
          public SelectValidator() {
          }
      
          public void validate(FacesContext context, UIComponent component, Object value) throws Validator
      Exception {
              System.out.println("SelectValidator.validate()");
      
              DbDriver dbDriver = (DbDriver) value;
              String clientId = component.getClientId(context);
              int componentNum = componentNum(component.getId());
              System.out.println("selectedValue = " + dbDriver);
              System.out.println("clientId = " + clientId);
              System.out.println("componentNum = " + componentNum);
              
              if (dbDriver == null) {
                  FacesMessage message = new FacesMessage();
                  message.setSummary("warning SUMMARY for: " + componentNum + " input");
                  message.setDetail("warning DETAIL for: " + componentNum + " input");
                  message.setSeverity(FacesMessage.SEVERITY_WARN);
                  context.addMessage(clientId, message);
              }
          }
      
          public int componentNum(String baseId) {
      
              if (baseId.endsWith("1")) {
                  return 1;
              } else if (baseId.endsWith("2")) {
                  return 2;
              } else if (baseId.endsWith("3")) {
                  return 3;
              } else if (baseId.endsWith("4")) {
                  return 4;
              }
              return -1;
          }
      }
      


      3.components.xml


      <framework:entity-home name="dbVendorHome" entity-class="com.magticom.billing.jbossmonitor.beans.entity.jits.DbVendor"/>
         <factory name="dbVendor" value="#{dbVendorHome.instance}"/>
         <framework:entity-query name="dbVendors" ejbql="select v from DbVendor v" order="v.id"/>
         
         <framework:entity-home name="dbDriverHome" entity-class="com.magticom.billing.jbossmonitor.beans.entity.jits.DbDriver"/>
         <factory name="dbDriver" value="#{dbDriverHome.instance}"/>
         <framework:entity-query name="dbDrivers" ejbql="select v from DbDriver v">
             <framework:restrictions>           
                 <value>v.dbVendor = #{dbparams.dbVendor}</value>
             </framework:restrictions>
         </framework:entity-query>
      



      1.Validation is not working is second menu is empty.


      2.I tried to add required attribute for second menu, but after this filtering is not working.
      second menu filled every second time ignoring what i choose from first menu, every first time is empty.



      any idea will be appreciated.



      ______________________


      Regards.


      Paata Lominadze


      Magticom LTD.

        • 1. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
          Damian Harvey Apprentice

          So #1 will not work without #2 and #2 won't work because when a4j submits the form for the dbVendor it requires dbDriver.


          What you need to do is either:



          1. Surround just dbVendor with an a4j:region; or

          2. add the ajaxSingle="true" attribute to dbVendor.



          Using one (or both) of these will ensure that only the dbVendor is sent to the server by the a4j:support. This will allow you to use dbDriver with required="true". When you submit the form (I can't see an h:commandButton or similar but I assume it's there) then the dbDriver validation will be fired.


          Cheers,


          Damian.

          • 2. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
            Paata Lominadze Newbie

            hi Damian.


            Great Thanks for your quick reply.
            i did everything what you told me. (i change a4j region, i had it for both menus,i just Surround dbVendor with an a4j:region)
            but i got strange error, on first time of choosing dbVendor it works but on second time i got this error :


            java.lang.IllegalStateException: begin() called from long-running conversation, try join=true
                    at org.jboss.seam.core.Conversation.begin(Conversation.java:255)
                    at org.jboss.seam.navigation.ConversationControl.beginOrEndConversation(ConversationControl.java:62)
                    at org.jboss.seam.navigation.Page.preRender(Page.java:242)
                    at org.jboss.seam.navigation.Pages.preRender(Pages.java:309)
                    at org.jboss.seam.jsf.SeamPhaseListener.preRenderPage(SeamPhaseListener.java:544)
                    at org.jboss.seam.jsf.SeamPhaseListener.beforeRenderResponse(SeamPhaseListener.java:455)
                    at org.jboss.seam.jsf.SeamPhaseListener.beforeServletPhase(SeamPhaseListener.java:146)
                    at org.jboss.seam.jsf.SeamPhaseListener.beforePhase(SeamPhaseListener.java:116)
            
            



            where i should insert this :

            join=true



            ______________


            Regards,


            Paata Lomindadze


            Magticom LTD

            • 3. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
              Paata Lominadze Newbie

              i did it.
              i have not join into my conversation



              <begin-conversation  flush-mode="manual" join="true"/>
              



              Great Thanks Damian for help.

              • 4. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
                Paata Lominadze Newbie

                i have another question.


                everything works fine, ajax onchange event works.


                but, when page loaded on first time, second selectonemenu is not filtered by first one, how i can do it?


                i need that when page loaded second menu must be filtered by first.



                ______________


                Regards,


                Paata Lomindadze


                Magticom LTD

                • 5. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
                  Paata Lominadze Newbie

                  or is it possible to do load order ?
                  i think that second selectonemenu is loaded before first one setting bean veriable.



                  • 6. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
                    Damian Harvey Apprentice

                    You've probably figured this out already, but how can the second menu be filtered if dbVendor doesn't yet have a value? That is what your filter is based on. Maybe you should look into how you can set a default value for dbVendor?


                    Cheers,


                    Damian.

                    • 7. Re: Seam,A4J,Selectonemenus and Validation(Rich:Message)
                      Paata Lominadze Newbie

                      Hi Damian,


                      i understand you.


                      I'll try to explain my problem.


                      i have 10 database vendor into my dbVendor table, two of them has child elements - Driver, for example oracle and db2.


                      onchange event works fine. if i choose oracle or db2, driver menu will be filled, otherwise driver menu is empty, but ..
                      when page loaded and into dbdriver selected item is Oracle, into second dvDriver menu shows all available drivers. i tried to look my sql queries and i found :


                      1.First Page Load Time :


                      10:00:32,272 INFO  [STDOUT] Constructor Initialization
                      10:00:32,272 INFO  [STDOUT] Constructor Initialization
                      10:00:32,439 INFO  [STDOUT] Hibernate:
                          select
                              dbvendor0_.ID as ID183_,
                              dbvendor0_.DBVENDORNAME as DBVENDOR2_183_
                          from
                              JITS.DB_VENDOR dbvendor0_
                          order by
                              dbvendor0_.ID
                      10:00:32,449 INFO  [STDOUT] Getter : null
                      10:00:32,452 INFO  [STDOUT] Getter : null
                      10:00:32,454 INFO  [STDOUT] Getter : null
                      10:00:32,456 INFO  [STDOUT] Getter : null
                      10:00:32,460 INFO  [STDOUT] Getter : null
                      10:00:32,464 INFO  [STDOUT] Getter : null
                      10:00:32,467 INFO  [STDOUT] Getter : null
                      10:00:32,470 INFO  [STDOUT] Getter : null
                      10:00:32,472 INFO  [STDOUT] Getter : null
                      10:00:32,475 INFO  [STDOUT] Getter : null
                      10:00:32,505 INFO  [STDOUT] Hibernate:
                          select
                              dbdriver0_.ID as ID182_,
                              dbdriver0_.DB_DRIVER_NAME as DB2_182_,
                              dbdriver0_.DB_VENDOR_ID as DB3_182_
                          from
                              JITS.DB_DRIVER dbdriver0_
                      10:00:32,509 INFO  [STDOUT] Getter : null
                      
                      


                      second query for driver is without where clause.


                      2. Second ocChange Event (For example when i choose Oracle) :


                      10:17:49,209 INFO  [STDOUT] Hibernate:
                          select
                              dbvendor0_.ID as ID183_,
                              dbvendor0_.DBVENDORNAME as DBVENDOR2_183_
                          from
                              JITS.DB_VENDOR dbvendor0_
                          order by
                              dbvendor0_.ID
                      10:17:49,216 INFO  [STDOUT] Getter : testpac.DbVendor[id=1]
                      10:17:49,221 INFO  [STDOUT] Setter : testpac.DbVendor[id=13]
                      10:17:49,245 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,247 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,250 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,252 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,254 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,256 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,258 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,261 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      10:17:49,293 INFO  [STDOUT] Hibernate:
                          select
                              dbdriver0_.ID as ID182_,
                              dbdriver0_.DB_DRIVER_NAME as DB2_182_,
                              dbdriver0_.DB_VENDOR_ID as DB3_182_
                          from
                              JITS.DB_DRIVER dbdriver0_
                          where
                              dbdriver0_.DB_VENDOR_ID=?
                      10:17:49,297 INFO  [STDOUT] Getter : testpac.DbVendor[id=13]
                      
                      



                      here is defined where clause.
                      because of i wand to do ajax wizard, i tried to do conversation seam component dbParams, which looks like:


                      @Name("dbparams")
                      @Scope(ScopeType.CONVERSATION)
                      public class DBParams {
                          
                          
                          @In
                          private FacesMessages facesMessages;
                      
                          public DBParams(){
                              System.out.println("Constructor Initialization");
                          }
                          
                          private String dbName;
                          private DbDriver dbDriver;
                          private DbVendor dbVendor;
                      
                          public DbVendor getDbVendor() {
                              System.out.println("Getter : "+dbVendor);
                              return dbVendor;
                          }
                      
                          public void setDbVendor(DbVendor dbVendor) {
                              System.out.println("Setter : "+dbVendor);
                              this.dbVendor = dbVendor;
                          }
                      
                          public String getDbName() {
                              return dbName;
                          }
                      
                          public void setDbName(String dbName) {
                              this.dbName = dbName;
                          }
                      
                          public DbDriver getDbDriver() {
                              return dbDriver;
                          }
                      
                          public void setDbDriver(DbDriver dbDriver) {
                              this.dbDriver = dbDriver;
                          }
                      
                          @Override
                          public String toString() {
                              return super.toString();
                          }
                      
                          @Override
                          public int hashCode() {
                              return super.hashCode();
                          }
                      
                          @Override
                          public boolean equals(Object obj) {
                              return super.equals(obj);
                          }
                      }
                      


                      and second problem - firefox remembers previous selected item from selectonemenu.




                      __________________


                      Regards


                      Paata Lominadze


                      Magticom LTD