5 Replies Latest reply on Jun 11, 2008 8:28 AM by cash1981

    a4j:support with valueChangeListener question

    cash1981

      Hello.

      I am wondering if anyone knows why the onchange event fires when you hit a commandbutton inside a form. The action of the command button should execute, not the valueChangeListener as it does in my example.

      The find method is not executed if I change the value of selectOneMenu and push commandButton.

      <h:form>
      [snip]....[/snip]
      
      <s:decorate template="/layout/display.xhtml">
       <ui:define name="label">Fylke</ui:define>
       <h:selectOneMenu valueChangeListener="#{searchProeveManager.updateKommune}" immediate="true">
       <s:selectItems value="#{fylkeList.resultList}" var="fylke" label="#{fylke.navn}" noSelectionLabel="Velg fylke"/>
       <a4j:support event="onchange" reRender="kommuneResultat"/>
       <s:convertEntity/>
       </h:selectOneMenu>
      </s:decorate>
      <s:div id="kommuneResultat">
       <s:decorate template="/layout/display.xhtml" rendered="#{searchProeveManager.kommuner.size > 0}">
       <ui:define name="label">Kommune</ui:define>
       <h:selectOneMenu value="#{searchProeveManager.kommune}" border="0">
       <s:selectItems value="#{searchProeveManager.kommuner}" var="kom" label="#{kom.navn}"/>
       </h:selectOneMenu>
       </s:decorate>
      </s:div>
      
      [snip]....[/snip]
      <h:commandButton id="findProeverSoek" value="Search" action="#{searchProeveManager.find}" reRender="searchResults" />
      


        • 1. Re: a4j:support with valueChangeListener question
          ilya_shaikovsky

          put phaseTracker to your web-inf libs and provide its log for request which was processed wrong.

          • 2. Re: a4j:support with valueChangeListener question
            cash1981

            Ok I did.

            This is the following output when you enter the page.

            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RESTORE_VIEW 1
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RESTORE_VIEW 1
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE APPLY_REQUEST_VALUES 2
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER APPLY_REQUEST_VALUES 2
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE PROCESS_VALIDATIONS 3
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER PROCESS_VALIDATIONS 3
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE UPDATE_MODEL_VALUES 4
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER UPDATE_MODEL_VALUES 4
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE INVOKE_APPLICATION 5
            09 Jun 08 16:49:27, DEBUG no.kommuneforlaget.alkohol.register.session.Authenticator:authenticate:23 Trying to authenticate she with password shepwd
            09 Jun 08 16:49:27, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             user0_.user_id as user1_27_,
             user0_.name as name27_,
             user0_.password as password27_,
             user0_.person_id as person4_27_,
             user0_.authentication_artefact_id as authenti5_27_
             from
             kf.user user0_
             where
             user0_.name=?
             and user0_.password=?
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER INVOKE_APPLICATION 5
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RESTORE_VIEW 1
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RESTORE_VIEW 1
            09 Jun 08 16:49:27, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:27 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RENDER_RESPONSE 6
            09 Jun 08 16:49:27, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             fylke0_.fylke_id as fylke1_28_,
             fylke0_.navn as navn28_,
             fylke0_.landkode as landkode28_,
             fylke0_.fylkesnummer as fylkesnu3_28_
             from
             kf.fylke fylke0_ limit ?
            09 Jun 08 16:49:27, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             land0_.landkode as landkode26_0_,
             land0_.navn as navn26_0_
             from
             kf.land land0_
             where
             land0_.landkode=?
            09 Jun 08 16:49:28, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             proevetype0_.proevetype_id as proevetype1_19_,
             proevetype0_.beskrivelse as beskrive2_19_
             from
             kf.proevetype proevetype0_ limit ?
            09 Jun 08 16:49:28, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:49:28 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RENDER_RESPONSE 6
            


            After you select from the first selectOneMenu and then select from the populated new selectOneMenu:
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RESTORE_VIEW 1
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RESTORE_VIEW 1
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE APPLY_REQUEST_VALUES 2
            09 Jun 08 16:52:14, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             fylke0_.fylke_id as fylke1_28_0_,
             fylke0_.navn as navn28_0_,
             fylke0_.landkode as landkode28_0_,
             fylke0_.fylkesnummer as fylkesnu3_28_0_
             from
             kf.fylke fylke0_
             where
             fylke0_.fylke_id=?
            09 Jun 08 16:52:14, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             fylke0_.fylke_id as fylke1_28_,
             fylke0_.navn as navn28_,
             fylke0_.landkode as landkode28_,
             fylke0_.fylkesnummer as fylkesnu3_28_
             from
             kf.fylke fylke0_ limit ?
            09 Jun 08 16:52:14, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:298 ***Comes inside updateKommune***
            09 Jun 08 16:52:14, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:305 State is: Rogaland
            09 Jun 08 16:52:14, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             kommunes0_.fylke_id as fylke4_1_,
             kommunes0_.kommune_id as kommune1_1_,
             kommunes0_.kommune_id as kommune1_9_0_,
             kommunes0_.navn as navn9_0_,
             kommunes0_.fylke_id as fylke4_9_0_,
             kommunes0_.kommunenummer as kommunen3_9_0_
             from
             kf.kommune kommunes0_
             where
             kommunes0_.fylke_id=?
            09 Jun 08 16:52:14, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             land0_.landkode as landkode26_0_,
             land0_.navn as navn26_0_
             from
             kf.land land0_
             where
             land0_.landkode=?
            09 Jun 08 16:52:14, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:310 Size of kommuneList: 26
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER APPLY_REQUEST_VALUES 2
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE PROCESS_VALIDATIONS 3
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER PROCESS_VALIDATIONS 3
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE UPDATE_MODEL_VALUES 4
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER UPDATE_MODEL_VALUES 4
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE INVOKE_APPLICATION 5
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER INVOKE_APPLICATION 5
            09 Jun 08 16:52:14, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:14 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RENDER_RESPONSE 6
            09 Jun 08 16:52:15, ERROR org.richfaces.renderkit.html.HtmlRichMessageRenderer:doEncodeEnd:34 'for' attribute cannot be null
            09 Jun 08 16:52:15, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:52:15 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RENDER_RESPONSE 6


            Finally when you push submit:

            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RESTORE_VIEW 1
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RESTORE_VIEW 1
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE APPLY_REQUEST_VALUES 2
            09 Jun 08 16:54:02, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             fylke0_.fylke_id as fylke1_28_0_,
             fylke0_.navn as navn28_0_,
             fylke0_.landkode as landkode28_0_,
             fylke0_.fylkesnummer as fylkesnu3_28_0_
             from
             kf.fylke fylke0_
             where
             fylke0_.fylke_id=?
            09 Jun 08 16:54:02, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             fylke0_.fylke_id as fylke1_28_,
             fylke0_.navn as navn28_,
             fylke0_.landkode as landkode28_,
             fylke0_.fylkesnummer as fylkesnu3_28_
             from
             kf.fylke fylke0_ limit ?
            09 Jun 08 16:54:02, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:298 ***Kommer inn til updateKommune***
            09 Jun 08 16:54:02, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:305 Fylkenavn er: Rogaland
            09 Jun 08 16:54:02, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             kommunes0_.fylke_id as fylke4_1_,
             kommunes0_.kommune_id as kommune1_1_,
             kommunes0_.kommune_id as kommune1_9_0_,
             kommunes0_.navn as navn9_0_,
             kommunes0_.fylke_id as fylke4_9_0_,
             kommunes0_.kommunenummer as kommunen3_9_0_
             from
             kf.kommune kommunes0_
             where
             kommunes0_.fylke_id=?
            09 Jun 08 16:54:02, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             land0_.landkode as landkode26_0_,
             land0_.navn as navn26_0_
             from
             kf.land land0_
             where
             land0_.landkode=?
            09 Jun 08 16:54:02, DEBUG no.kommuneforlaget.alkohol.register.session.search.SearchProeveManagerAction:updateKommune:310 Puttet alt i kommuneLista og den har size: 26
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER APPLY_REQUEST_VALUES 2
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE PROCESS_VALIDATIONS 3
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER PROCESS_VALIDATIONS 3
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker beforePhase
            INFO: BEFORE RENDER_RESPONSE 6
            09 Jun 08 16:54:02, INFO org.jboss.logging.util.LoggerStream:write:152 Hibernate:
             select
             proevetype0_.proevetype_id as proevetype1_19_,
             proevetype0_.beskrivelse as beskrive2_19_
             from
             kf.proevetype proevetype0_ limit ?
            09 Jun 08 16:54:02, ERROR org.jboss.logging.util.LoggerStream:write:152 Jun 9, 2008 4:54:02 PM org.exadel.jsf.PhaseTracker afterPhase
            INFO: AFTER RENDER_RESPONSE 6


            I don't understand much. But my find method is never executed which it should.

            • 3. Re: a4j:support with valueChangeListener question
              cash1981

              I still have this problem. But here is a update. If I do not change the selectOneMenu then I can hit the command button and it calls the correct method.

              But if I change the value of the selectOneMenu and then hit the commandbutton it will call the valueChangeListener method on the selectOneMenu instead.

              Very strange behaviour.

              Here is the complete xhtml:

              <ui:composition xmlns="http://www.w3.org/1999/xhtml"
               xmlns:s="http://jboss.com/products/seam/taglib"
               xmlns:ui="http://java.sun.com/jsf/facelets"
               xmlns:f="http://java.sun.com/jsf/core"
               xmlns:h="http://java.sun.com/jsf/html"
               xmlns:rich="http://richfaces.org/rich"
               xmlns:a4j="http://richfaces.org/a4j">
              
               <style>
               .tooltip {
               background-color:#{richSkin.generalBackgroundColor};
               border-width:3px;
               padding:10px;
               }
               </style>
              
               <rich:simpleTogglePanel label="Search after tests" switchType="ajax">
               <h:form id="searchCriteria" styleClass="edit">
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Fornavn</ui:define>
               <h:inputText id="searchStringFornavn" value="#{searchProeveManager.searchStringFornavn}" />
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space:nowrap">
               Search on fornavn og mellomavn. * søker på alt.
               </span>
               </rich:toolTip>
               </s:decorate>
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Etternavn</ui:define>
               <h:inputText id="searchStringEtternavn" value="#{searchProeveManager.searchStringEtternavn}" />
               </s:decorate>
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Fødselsnummer</ui:define>
               <h:inputText id="searchStringFodselsnr" value="#{searchProeveManager.searchStringFodselsnr}" />
               </s:decorate>
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Adresse</ui:define>
               <h:inputText id="searchStringAdresse" value="#{searchProeveManager.searchStringAdresse}" />
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space:nowrap">
               Søk på adressen til personen. * søker på alt.
               </span>
               </rich:toolTip>
               </s:decorate>
               <a4j:region>
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Fylke</ui:define>
               <h:selectOneMenu valueChangeListener="#{searchProeveManager.updateKommune}">
               <s:selectItems value="#{fylkeList.resultList}" var="fylke" label="#{fylke.navn}" noSelectionLabel="Velg fylke"/>
               <a4j:support event="onchange" ajaxSingle="true" reRender="kommuneResultat" ignoreDupResponses="true" immediate="false" limitToList="true"/>
               <s:convertEntity/>
               </h:selectOneMenu>
               </s:decorate>
               <s:div id="kommuneResultat">
               <s:decorate template="/layout/display.xhtml" rendered="#{searchProeveManager.kommuner.size > 0}">
               <ui:define name="label">Kommune</ui:define>
               <h:selectOneMenu value="#{searchProeveManager.kommune}" border="0">
               <s:selectItems value="#{searchProeveManager.kommuner}" var="kom" label="#{kom.navn}"/>
               </h:selectOneMenu>
               </s:decorate>
               </s:div>
               </a4j:region>
              
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">År</ui:define>
               <h:inputText id="searchStringAar" value="#{searchProeveManager.searchStringAar}"/>
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space:nowrap">
               Velg året prøven ble avlagt i
               </span>
               </rich:toolTip>
               </s:decorate>
               <s:decorate template="/layout/display.xhtml">
               <ui:define name="label">Inneholder prøvetyper:</ui:define>
               <h:selectManyCheckbox value="#{searchProeveManager.proevetyper}" border="0">
               <s:selectItems value="#{proevetypeList.resultList}" var="proevetype" label="#{proevetype.beskrivelse}"/>
               <s:convertEntity/>
               </h:selectManyCheckbox>
               </s:decorate>
              
               <s:decorate template="/layout/display.xhtml">
               <h:commandButton id="findProeverSoek" value="Søk" action="#{searchProeveManager.find}" reRender="searchResults" />
               </s:decorate>
               </h:form>
              
               </rich:simpleTogglePanel>
              
               <rich:simpleTogglePanel label="Søke resultat" switchType="ajax">
               <div class="searchResults" id="proeveSokList">
               <h:outputText value="Søket resulterte i #{proeveSokList.size} treff" rendered="#{proeveSokList.size > 0}"/>
               <h:form>
               <rich:spacer height="20" rendered="#{proeveSokList.size > 0}" />
               <rich:dataTable id="proeveSokList" var="proeve" value="#{proeveSokList}" rendered="#{proeveSokList.size > 0}" rows="20" sortMode="single">
               <rich:column sortBy="#{proeve.person.etternavn}">
               <f:facet name="header"><h:outputText value="Etternavn"/></f:facet>
               <h:outputText value="#{proeve.person.etternavn}"/>
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space: nowrap">
               <strong>Navn: </strong>#{proeve.person.fornavn} #{proeve.person.mellomnavn} #{proeve.person.etternavn}<br />
               <strong>Fødselsdato: </strong>#{proeve.person.foedselsdato}<br />
               </span>
               </rich:toolTip>
               </rich:column>
               <rich:column sortBy="#{proeve.person.fornavn}">
               <f:facet name="header"><h:outputText value="Fornavn"/></f:facet>
               <h:outputText value="#{proeve.person.fornavn}"/>
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space: nowrap">
               <strong>Navn: </strong>#{proeve.person.fornavn} #{proeve.person.mellomnavn} #{proeve.person.etternavn}<br />
               <strong>Fødselsdato: </strong>#{proeve.person.foedselsdato}<br />
               </span>
               </rich:toolTip>
               </rich:column>
               <rich:column>
               <f:facet name="header"><h:outputText value="Fødselsnummer"/></f:facet>
               <h:outputText value="#{proeve.person.personnummer}"/>
               <rich:toolTip followMouse="false" direction="top-right" styleClass="tooltip">
               <span style="white-space: nowrap">
               <strong>Navn: </strong>#{proeve.person.fornavn} #{proeve.person.mellomnavn} #{proeve.person.etternavn}<br />
               <strong>Fødselsdato: </strong>#{proeve.person.foedselsdato}<br />
               </span>
               </rich:toolTip>
               </rich:column>
               <rich:column sortBy="#{proeve.avlagt}">
               <f:facet name="header"><h:outputText value="Prøve Avlagt"/></f:facet>
               <h:outputText value="#{proeve.avlagt}"/>
               </rich:column>
               <rich:column sortBy="#{proeve.bestaatt}">
               <f:facet name="header"><h:outputText value="Prøve Bestått"/></f:facet>
               <h:outputText value="Ja" rendered="#{proeve.bestaatt}" />
               <h:outputText value="Nei" rendered="#{!proeve.bestaatt}" />
               </rich:column>
               <rich:column sortBy="#{proeve.proevetype.beskrivelse}">
               <f:facet name="header"><h:outputText value="Prøvetype"/></f:facet>
               <h:outputText value="#{proeve.proevetype.beskrivelse}"/>
               </rich:column>
               <rich:column sortBy="#{proeve.proevetypeVersjon.navn}">
               <f:facet name="header"><h:outputText value="Prøvetype versjon"/></f:facet>
               <h:outputText value="#{proeve.proevetypeVersjon.navn}"/>
               </rich:column>
               <rich:column sortBy="#{proeve.kommune.navn}">
               <f:facet name="header"><h:outputText value="Kommune"/></f:facet>
               <h:outputText value="#{proeve.kommune.navn}"/>
               <rich:toolTip showEvent="onclick" followMouse="false" mode="ajax" direction="top-right" styleClass="tooltip">
               <span style="white-space: nowrap">
               Prøven ble avlagt i <strong>#{proeve.kommune.navn}</strong> kommune
               </span>
               </rich:toolTip>
               </rich:column>
               <rich:column>
               <f:facet name="header"><h:outputText value="Rediger"/></f:facet>
               <s:link view="/protected/#{empty from ? 'Proeve' : from}.xhtml" value="Velg"
               id="proeve">
               <f:param name="proeveProeveId" value="#{proeve.proeveId}" />
               </s:link>
               </rich:column>
               </rich:dataTable>
               <rich:datascroller align="left" for="proeveSokList" maxPages="10" rendered="#{proeveSokList.size > 0}" renderIfSinglePage="false"/>
               </h:form>
               </div>
               </rich:simpleTogglePanel>
              </ui:composition>
              


              • 4. Re: a4j:support with valueChangeListener question
                ilya_shaikovsky

                So.. as I (and you for sure :) ) could see from the phaseTraker log - after 3rd phase next phase executed is sixth... That tell us about model wasn't successfully updated. So 5th phase not executed - so no valueChange listener.

                If your searchProeveManager request scoped - you should change it to session use keepAlive fro this bean. And there is nothing about ajax. Just JSF question.

                • 5. Re: a4j:support with valueChangeListener question
                  cash1981

                   

                  "ilya_shaikovsky" wrote:
                  So.. as I (and you for sure :) ) could see from the phaseTraker log - after 3rd phase next phase executed is sixth... That tell us about model wasn't successfully updated. So 5th phase not executed - so no valueChange listener.

                  If your searchProeveManager request scoped - you should change it to session use keepAlive fro this bean. And there is nothing about ajax. Just JSF question.


                  Ok I agree there seems to be something wrong. But thats why I need help :-)
                  If I understand you correctly you say that my searchProeveManager is request scoped, but I have session. The only thing is that the #fylkeList.resultList is not session scope.
                  I also tried to put searchProeveManager in <a4j:keepAlive> but that resultet in exception.

                  Here is my searchProeveManager. Maybe you can spot the problem, because I am blinded by my own code.

                  package no.kommuneforlaget.alkohol.register.session.search;
                  
                  import static javax.persistence.PersistenceContextType.EXTENDED;
                  
                  import java.io.Serializable;
                  import java.util.ArrayList;
                  import java.util.Arrays;
                  import java.util.HashSet;
                  import java.util.List;
                  import java.util.Set;
                  
                  import javax.ejb.Remove;
                  import javax.ejb.Stateful;
                  import javax.faces.event.ValueChangeEvent;
                  import javax.persistence.EntityManager;
                  import javax.persistence.PersistenceContext;
                  
                  import no.kommuneforlaget.alkohol.register.entity.Adresse;
                  import no.kommuneforlaget.alkohol.register.entity.Fylke;
                  import no.kommuneforlaget.alkohol.register.entity.Kommune;
                  import no.kommuneforlaget.alkohol.register.entity.Person;
                  import no.kommuneforlaget.alkohol.register.entity.PersonAdresseAdressetype;
                  import no.kommuneforlaget.alkohol.register.entity.Proeve;
                  import no.kommuneforlaget.alkohol.register.entity.Proevetype;
                  
                  import org.jboss.seam.ScopeType;
                  import org.jboss.seam.annotations.Destroy;
                  import org.jboss.seam.annotations.Factory;
                  import org.jboss.seam.annotations.Logger;
                  import org.jboss.seam.annotations.Name;
                  import org.jboss.seam.annotations.Scope;
                  import org.jboss.seam.annotations.datamodel.DataModel;
                  import org.jboss.seam.faces.FacesMessages;
                  import org.jboss.seam.log.Log;
                  import org.joda.time.DateTime;
                  
                  /**
                   * @author Shervin Asgari <shervin@linpro.no> <br>
                   * This class retrieves Proever which has been taken. <br>
                   * From the ProeverSoek.xhtml you can search on Person, Kommune and
                   * Proevetype.
                   */
                  
                  @Stateful
                  @Name("searchProeveManager")
                  @Scope(ScopeType.SESSION)
                  //@Restrict("#{identity.loggedIn}")
                  public class SearchProeveManagerAction implements SearchProeveManager, Serializable {
                  
                   private static final long serialVersionUID = 7218402377558637175L;
                  
                   @PersistenceContext(type = EXTENDED)
                   private EntityManager em;
                  
                   private String searchStringFornavn;
                   private String searchStringEtternavn;
                   private String searchStringFodselsnr;
                   private String searchStringAdresse;
                   private String searchStringAar;
                  
                   @DataModel
                   private List<Proeve> proeveSokList;
                  
                   private List<Proevetype> proevetyper = new ArrayList<Proevetype>();
                   private List<Kommune> kommuner = new ArrayList<Kommune>();
                  
                   //@In(required=false)
                   //@Out(required=false)
                   private Kommune kommune;
                  
                   //No point in serializing logger
                   @Logger
                   private transient Log log;
                  
                   @Override
                   public void updateKommune(ValueChangeEvent event) {
                   log.debug("***Inside updateKommune***");
                  
                   final Fylke f = (Fylke) event.getNewValue();
                   if(f == null) {
                   kommuner = new ArrayList<Kommune>();
                   return;
                   }
                   log.debug("Fylkenavn is: " + f.getNavn());
                   kommuner = new ArrayList<Kommune>();
                  
                   final Set<Kommune> kommuneTilFylke = f.getKommunes();
                   kommuner.addAll(Arrays.asList(kommuneTilFylke.toArray(new Kommune[kommuneTilFylke.size()])));
                   log.debug("The kommuneList has size: " + kommuner.size());
                   }
                  
                   /**
                   * Creates a factory name patternPersonFornavn so you can call it with the \#{name}
                   * in the query. It will return '%' if it is null and and put '%' in the
                   * beginning and last of the text field and also replace '*' with '%'
                   */
                   @Factory(value = "patternFornavn", scope = ScopeType.EVENT)
                   @Override
                   public String getSearchPatternFornavn() {
                   return searchStringFornavn == null ? "%" : '%' + searchStringFornavn.toLowerCase().replace('*', '%') + '%';
                   }
                  
                   /**
                   * Creates a factory name patternPersonEtternavn so you can call it with the \#{name}
                   * in the query. It will return '%' if it is null and and put '%' in the
                   * beginning and last of the text field and also replace '*' with '%'
                   */
                   @Factory(value = "patternEtternavn", scope = ScopeType.EVENT)
                   @Override
                   public String getSearchPatternEtternavn() {
                   return searchStringEtternavn == null ? "%" : '%' + searchStringEtternavn.toLowerCase().replace('*', '%') + '%';
                   }
                  
                   /**
                   * Creates a factory name patternSted so you can call it with the \#{name}
                   * in the query. It will return '%' if it is null and and put '%' in the
                   * beginning and last of the text field and also replace '*' with '%'
                   */
                   @Factory(value = "patternAdresse", scope = ScopeType.EVENT)
                   @Override
                   public String getSearchPatternAdresse() {
                   return searchStringAdresse == null ? "%" : '%' + searchStringAdresse.toLowerCase().replace('*', '%') + '%';
                   }
                  
                   /**
                   * Creates a factory name patternFodselsdato so you can call it with the \#{name}
                   * in the query. It will return '%' if it is null and and put '%' in the
                   * beginning and last of the text field and also replace '*' with '%'
                   */
                   @Factory(value = "patternFodselsnr", scope = ScopeType.EVENT)
                   @Override
                   public String getSearchPatternFodselsnr() {
                   return searchStringFodselsnr == null ? "%" : '%' + searchStringFodselsnr.toLowerCase().replace('*', '%') + '%';
                   }
                  
                   /**
                   * Creates a factory name patternKommunenavn so you can call it with the \#{name}
                   * in the query. It will return '%' if it is null and and put '%' in the
                   * beginning and last of the text field and also replace '*' with '%'
                   */
                   @Factory(value = "patternKommunenavn", scope = ScopeType.EVENT)
                   @Override
                   public String getSearchPatternKommunenavn() {
                   return kommune == null ? "%" : '%' + kommune.getNavn().toLowerCase().replace('*', '%') + '%';
                   }
                  
                   /**
                   * @return the searchStringFornavn
                   */
                   public String getSearchStringFornavn() {
                   return searchStringFornavn;
                   }
                  
                   /**
                   * @param searchStringFornavn the searchStringFornavn to set
                   */
                   public void setSearchStringFornavn(String searchStringFornavn) {
                   this.searchStringFornavn = searchStringFornavn;
                   }
                  
                   /**
                   * @return the searchStringEtternavn
                   */
                   public String getSearchStringEtternavn() {
                   return searchStringEtternavn;
                   }
                  
                   /**
                   * @param searchStringEtternavn the searchStringEtternavn to set
                   */
                   public void setSearchStringEtternavn(String searchStringEtternavn) {
                   this.searchStringEtternavn = searchStringEtternavn;
                   }
                  
                   /**
                   * @return the searchStringFodselsnr
                   */
                   public String getSearchStringFodselsnr() {
                   return searchStringFodselsnr;
                   }
                  
                   /**
                   * @param searchStringFodselsnr the searchStringFodselsnr to set
                   */
                   public void setSearchStringFodselsnr(String searchStringFodselsnr) {
                   this.searchStringFodselsnr = searchStringFodselsnr;
                   }
                  
                   /**
                   * @return the searchStringAdresse
                   */
                   public String getSearchStringAdresse() {
                   return searchStringAdresse;
                   }
                  
                   /**
                   * @param searchStringAdresse the searchStringAdresse to set
                   */
                   public void setSearchStringAdresse(String searchStringAdresse) {
                   this.searchStringAdresse = searchStringAdresse;
                   }
                  
                   /**
                   * @return the searchStringAar
                   */
                   public String getSearchStringAar() {
                   return searchStringAar;
                   }
                  
                   /**
                   * @param searchStringAar the searchStringAar to set
                   */
                   public void setSearchStringAar(String searchStringAar) {
                   this.searchStringAar = searchStringAar;
                   }
                  
                   public List<Proevetype> getProevetyper() {
                   return proevetyper;
                   }
                  
                   public void setProevetyper(List<Proevetype> proevetyper) {
                   this.proevetyper = proevetyper;
                   }
                  
                   public List<Kommune> getKommuner() {
                   return kommuner;
                   }
                  
                   public void setKommuner(List<Kommune> kommuner) {
                   this.kommuner = kommuner;
                   }
                  
                   public Kommune getKommune() {
                   log.debug("***Calling getKommune");
                   return kommune;
                   }
                  
                   public void setKommune(Kommune kommune) {
                   log.debug("***Calling setKommune");
                   this.kommune = kommune;
                   }
                  
                   @Override
                   public void find() {
                   if(kommune == null) {
                   log.debug("KOMMUNE ER NULL");
                   }
                   findProever();
                   }
                  
                   /**
                   * This method returns the year interval to be search for
                   *
                   * @return - This method returns the year interval to be search for
                   */
                   private String getYearInterval() {
                   if (getSearchStringAar() == null || getSearchStringAar().equals("")) {
                   setSearchStringAar("");
                   return "";
                   }
                   try {
                   Integer.parseInt(getSearchStringAar());
                   } catch (NumberFormatException nfe) {
                   FacesMessages.instance().add("År kan kun inneholde tall. Ignorerer...");
                   setSearchStringAar("");
                   return "";
                   }
                   log.debug("Returnerer: " + ("AND (p.avlagt < '" + getSearchStringAar() + "-12-31' AND p.avlagt > '" + getSearchStringAar() + "-01-01')"));
                   return ("AND (p.avlagt < '" + getSearchStringAar() + "-12-31' AND p.avlagt > '" + getSearchStringAar() + "-01-01')");
                   }
                  
                   /**
                   * Returns the String to be used in the query for retrieving proevetype.
                   *
                   * @return This method checks the proevetyper list size and returns a string
                   * accordingly
                   */
                   private String getProevetypeChosen() {
                   String proevetypeValgt = " (p.proevetypeVersjon.proevetype.beskrivelse like '%') ";
                   for (int i = 0; i < proevetyper.size(); i++) {
                   final Proevetype pt = proevetyper.get(i);
                  
                   if (proevetyper.size() == 1) {
                   proevetypeValgt = " (p.proevetypeVersjon.proevetype.beskrivelse like '" + pt.getBeskrivelse() + "') ";
                   break;
                   // Can also write continue since size is 1 anyways
                   }
                   if (i == 0) {
                   proevetypeValgt = " (p.proevetypeVersjon.proevetype.beskrivelse like '" + pt.getBeskrivelse() + "') ";
                   continue;
                   }
                   proevetypeValgt += " OR (p.proevetypeVersjon.proevetype.beskrivelse like '" + pt.getBeskrivelse() + "') ";
                   }
                  
                   log.debug("PrøvetypeValgt er: " + proevetypeValgt);
                   return proevetypeValgt;
                   }
                  
                   /**
                   * This is the method that fills the proeveSokList that shows the Proeve
                   * result.
                   */
                   @SuppressWarnings("unchecked")
                   private void findProever() {
                   try {
                   log.debug("Searching for prøver with searchfields: #{patternFornavn}, #{patternEtternavn}, #{patternFodselsnr}, #{patternAdresse}" );
                   proeveSokList = em.createQuery(
                   "from " + Proeve.class.getName() + " p "
                   + "where (lower(p.person.fornavn) like #{patternFornavn} OR lower(p.person.mellomnavn) like #{patternFornavn}) "
                   + "AND (lower(p.person.etternavn) like #{patternEtternavn}) "
                   + "AND (lower(p.person.foedselsnummer) like #{patternFodselsnr}) "
                   + "AND (lower(p.kommune.navn) like #{patternKommunenavn}) "
                   + getYearInterval() + "AND (" + getProevetypeChosen() + ") " + "order by p.person.etternavn, p.avlagt desc")
                   .getResultList();
                  
                   // Searching for the persons address
                   log.debug("Det originale søket har size: " + proeveSokList.size());
                   final List<Proeve> proeveFromAdresseList = findProeveFromAdresse();
                   // Adding the result to the Proeve list
                   proeveSokList.addAll(proeveFromAdresseList);
                   // Putting the list in a HashSet so that it removes duplicates
                   final Set<Proeve> proeveUnique = new HashSet<Proeve>(proeveSokList);
                   log.debug("After putting in a set the list has now: " + proeveUnique.size());
                   /*
                   * Creating a temporary array of type Proeve with the size of the
                   * unique hashset. This is done because the toArray() method takes
                   * as argument an array of a type which it returns. Meaning, if you
                   * send in of type T, you get back of type T. And we have to return
                   * a list of type Proeve. Finally, we use Arrays.asList to return
                   * the arrays as a list.
                   */
                   proeveSokList = Arrays.asList(proeveUnique.toArray(new Proeve[proeveUnique.size()]));
                   log.debug("Fant " + proeveSokList.size());
                   } catch (Exception e) {
                   e.printStackTrace();
                   proeveSokList = null;
                   }
                   }
                  
                   /**
                   * This method retrieves a List of type Proeve that matches the search
                   * string.
                   *
                   * @return List<Proeve>
                   */
                   @SuppressWarnings("unchecked")
                   private List<Proeve> findProeveFromAdresse() {
                   final List<Adresse> allAdresseList = findAdresses();
                  
                   List<Proeve> proeveFromAdresseList = new ArrayList<Proeve>();
                  
                   // This block of code retrives the PersonAdresseAdresseTypes for every
                   // address it finds.
                   // Then for all the PersonAdresseAdressetypes it retrieves the Proever
                   // and adds it to the existing list
                   for (Adresse adr : allAdresseList) {
                   final Set<PersonAdresseAdressetype> personAdresseSet = adr.getPersonAdresseAdressetypes();
                   for (PersonAdresseAdressetype paa : personAdresseSet) {
                   Set<Proeve> proeveFromAdresseSet = paa.getPerson().getProeves();
                   /*
                   * Creating a temporary array of type Proeve with the size of
                   * the hashset. This is done because the toArray() method takes
                   * as argument an array of a type which it returns. Meaning, if
                   * you send in of type T, you get back of type T. And we have to
                   * return a list of type Proeve. Then we use Arrays.asList to
                   * return the arrays as a list, and finally we add that list to
                   * the existing proeveFromAdresseList.
                   */
                   proeveFromAdresseList.addAll(Arrays.asList(proeveFromAdresseSet.toArray(new Proeve[proeveFromAdresseSet.size()])));
                   }
                   }
                  
                   // Refine the search if year is chosen
                   if (getSearchStringAar() != null && !getSearchStringAar().equals("")) {
                   log.debug("Refining the search list based on year input");
                   for (int i = 0; i < proeveFromAdresseList.size(); i++) {
                   final Proeve proeve = proeveFromAdresseList.get(i);
                   DateTime dt = new DateTime(proeve.getAvlagt());
                  
                   log.debug("DT er: " + dt);
                  
                   final String year = "" + dt.getYear();
                   if (!year.equals(getSearchStringAar())) {
                   proeveFromAdresseList.remove(i);
                   i--; // The size of the list is now smaller, so you have
                   // to decrease i
                   }
                   }
                   }
                  
                   // This block is a refining of the search in case you also search for
                   // person and address
                   if (getSearchStringFornavn() != null && !getSearchStringFornavn().equals("")
                   || getSearchStringEtternavn() != null && !getSearchStringEtternavn().equals("")
                   || getSearchStringFodselsnr() != null && !getSearchStringFodselsnr().equals("")) {
                   log.debug("Refining the search list based on person. The list has size: " + proeveFromAdresseList.size());
                   final List<Person> personList = findPersons();
                   boolean foundMatch = false;
                   for (int i = 0; i < proeveFromAdresseList.size(); i++) {
                   final Proeve proeve = proeveFromAdresseList.get(i);
                   inner: for (Person person : personList) {
                   foundMatch = false;
                   // TODO: Should maybe fix for future notice
                   // Wanted to use the Object.equals(obj) but that doesn't
                   // seem to work. Therefore, I only check on the Id of person
                   if (proeve.getPerson().getPersonId().equals(person.getPersonId())) {
                   foundMatch = true;
                   break inner;
                   }
                   } // inner
                  
                   if (!foundMatch) {
                   proeveFromAdresseList.remove(i);
                   i--; // The size of the list is now smaller, so you have
                   // to decrease i
                   }
                   }
                   }
                  
                   // Refine the search even more with proevetyper
                   if (proevetyper.size() > 0) {
                   boolean foundProevetype = false;
                   for (int i = 0; i < proeveFromAdresseList.size(); i++) {
                   Proeve proeve = proeveFromAdresseList.get(i);
                   inner: for (Proevetype pt : proevetyper) {
                   foundProevetype = false;
                   // TODO: Should fix for future notice
                   // Wanted to use the Object.equals(obj) but that doesn't
                   // seem to work. Therefore, I only check on the Id of
                   // proevetype
                   if (proeve.getProevetypeVersjon().getProevetype().getProevetypeId().equals(pt.getProevetypeId())) {
                   foundProevetype = true;
                   break inner;
                   }
                   } // inner
                  
                   if (!foundProevetype) {
                   proeveFromAdresseList.remove(i);
                   i--; // The size of the list is now smaller, so you have
                   // to decrease i
                   }
                   }
                   }
                  
                   return proeveFromAdresseList;
                   }
                  
                   /**
                   * Returns a list of the addresses matching #{patternSted}
                   *
                   * @return Returns a list of the addresses matching #{patternSted}
                   */
                   @SuppressWarnings("unchecked")
                   private List<Adresse> findAdresses() {
                   return em.createQuery(
                   "from " + Adresse.class.getName() + " adr "
                   + "where lower(adr.adressefelt1) like #{patternAdresse} or lower(adr.adressefelt2) like #{patternAdresse}").getResultList();
                   }
                  
                   /**
                   * Returns a list of the persons matching the input
                   *
                   * @return Returns a list of the persons matching the input
                   */
                   @SuppressWarnings("unchecked")
                   private List<Person> findPersons() {
                   return em.createQuery(
                   "from " + Person.class.getName() + " p "
                   + "where (lower(p.fornavn) like #{patternFornavn} OR lower(p.mellomnavn) like #{patternFornavn}) "
                   + "AND (lower(p.etternavn) like #{patternEtternavn}) "
                   + "AND (lower(p.foedselsnummer) like #{patternFodselsnr})").getResultList();
                   }
                  
                   @Destroy
                   @Remove
                   public void destroy() {
                   }
                  
                   @Override
                   public void chooseKommune(ValueChangeEvent event) {
                   log.debug("Entering chooseKommune");
                   kommune = (Kommune) event.getNewValue();
                   log.debug("Kommune is: " + kommune.getNavn());
                   }
                  }