JSF action not called OR selectbox value is null - jsf

i have another strange JSF problem here... I don´t really know why, but what ever i try to do, i have one out of two problems. Either the action method inside my popupPanel is not (means never) called or it is called, but the value from my selectBox is (always) null. Can´t figure out, what the problem is, but it seems to me, like it´s a XHTML property problem.
Already tried to put the popupPanel outside my h:form (helped me at some other locations...), i also tried to put it outside and put another form into my popup. Beyond that i was trying to change the attachment to parent/form and i changed the execute of the commandButton inside my popup to form/form-id/popuppanel-id and i guess there were some more things i did... but nothing helped.
The Bean is session scoped and i am using Richface 4.0 Final if it does matter at all.
What ever, the XHTML looks like this:
<rich:popupPanel
header="#{label['edit.title']} #{mandateAction.ccService.mandateList[mandateAction.currentIndex].id}"
id="addExternalSystem"
onmaskclick="#{rich:component('addExternalSystem')}.hide()"
domElementAttachment="form" autosized="true" layout="block">
<h:panelGrid columns="2">
<h:outputText value="#{label['login.username']}" />
<h:inputText
value="#{mandateAction.newExternalSystem.username}" />
<h:outputText value="#{label['login.password']}" />
<h:inputSecret
value="#{mandateAction.newExternalSystem.password}" />
<h:outputText value="#{label['mandate.externalSystem']}" />
<h:selectOneMenu
value="#{mandateAction.newExternalSystem.externalSystem}">
<f:selectItems
value="#{creditcardConfigurationService.externalSystems}"
itemLabel="#{system.name}" itemValue="#{system}"
var="system" />
<f:converter binding="#{externalSystemConverter}" />
</h:selectOneMenu>
....
<a4j:commandButton value="#{label['insert.save']}"
action="#{mandateAction.insertNewSystem}"
render="mandate_table" execute="#form"
oncomplete="if (#{facesContext.maximumSeverity==null}) {#{rich:component('addExternalSystem')}.hide();}" />

If your page have any of the required fields kept as empty the submit from the popup panel will not work. In that case include the popup panel inside a form and domElementAttachment="form" , and perform the submit.

Related

why composite compoment does not invoke in the <h:datatable/>

I have a compoment which has a method-signature attribute. It can be activated, but if I put it in a <h:datatable> <h:column/> and trigger this component, it does not work.
When I just refresh this page again or when I put it in another place it can invoked successfully. I would be grateful if somebody can tell me why!
this is my code
<h:column>
<f:facet name="header">op:</f:facet>
<h:commandLink value="alter" action="#{userSession.alterAction}"
rendered="#{userSession.user.power.powerID == 1}">
<f:param name="beanId" value="#{book.bookID}" />
<f:param name="class" value="#{BookBean}" />
</h:commandLink>
<h:commandLink action="#{userSession.detailAction}" value="detail"
rendered="#{userSession.user != null}">
<f:param name="beanId" value="#{book.bookID}" />
<f:param name="class" value="#{BookBean}" />
</h:commandLink>
<h:commandLink action="#{bookAction.bookDelAction}"
onclick="return confirm('are you sure?')" value="delete"
rendered="#{userSession.user.power.powerID == 1}">
<f:param name="beanId" value="#{book.bookID}" />
</h:commandLink>
</h:column>
this manageredBean #{bookAction} is requestScope when i click one of this operation,just like delete ,it doesnot work at all. but if i put the 'delete' commandlink out of <h:datatabel/> .it can invoke backing method successfully. it is so upset!
who can tell me whether <h:datatable/> can Shielding the .i found if i put these code in a <h:form/> .it can invoke too! cound you can tell me the reason!
You need to preserve exactly the same data model (i.e. the one which you have referenced by the value attribute of the <h:dataTable>) in during the request of the form submit as it was during the request of displaying the initial form. The symptoms indicate that you're using a request scoped bean and that the loading of the data model is based on some request parameter which is missing during the form submit and/or the loading is not being done during bean's (post)construction.
Putting the bean in the view scope and/or rearranging the data loading logic should fix it.

ValueChangeListener problem

While calling the ValueChangeListener in JSF based on value change in dropdown, it is calling all the ValueChangeListner that are on that page.
There are two valueChangeListener in DataTable, while changing value in one dropdwon the 2nd one also executing.
<t:column id="avlId" styleClass="coltextcenteralign">
<f:facet name="header">
<h:panelGroup>
<h:outputText value="#{bundle['travelLocalAccommodation.title.availability']}" />
<h:outputText value="*" style="color:red" />
</h:panelGroup>
</f:facet>
<t:selectOneMenu value="#{accomDtls.availability}" immediate="true"
valueChangeListener="#{TravelProcessingBB.localAccommodationBB.setAvailableFlag}" forceid="true" id="avl"
onchange="return availabilityAlert('#{accomDtls.prepopulatedFlag}','avl[#{table_count}]')"
styleClass="dropDownStyle" style="width:50">
<f:selectItem itemValue="Y" itemLabel="Yes" />
<f:selectItem itemValue="N" itemLabel="No" />
</t:selectOneMenu>
</t:column>
The value change alone won't automatically call the valueChangeListener. You need to submit the form as well. A commonly used "hack" is to call form.submit() using JavaScript during the onchange event. This will however submit the entire form. Truly the valueChangeListener will be triggered for all changed fields of the form.
To fix this in JSF 1.x, you need to hassle somewhat with the immediate attribute to skip all other form components from validating and with component binding so that you can properly get/set the other component's value. Long story short, I ever wrote an article about that: populate child menus in JSF 1.2.
In JSF 2.0, this is however easier to achieve with help of <f:ajax> tag. If you're really using JSF 2.0 (your current question doesn't indicate that), then let me know if you need an example.

Trying to understand why h:commandLink submits through validation and a4j:commandLink doesn't

First of all, i'm using Jsf 1.2...
I have a problem with submitting some values in a form to validation.
Specifically this code segement:
<h:panelGrid columns="4" id="StatusPanel">
<h:outputText value="#{msg.Phone_number_to_send_SMS_to}" />
<h:inputText id="phoneNumber" value="#{general.smsPhoneNumber}" required="true"
requiredMessage="Please enter a valid phone number." />
<a4j:commandLink value="#{msg.Submit_Button}"
reRender="pinCodeDeliveryMsgText, pinCodeDeliveryMsg, pinCodeDeliveryFailedMsg, pinCodeDeliveryMainPanel, LastPinCodeMsg, SendingSMSMSG"
action="#{general.submit}" />
<h:message for="phoneNumber" fatalClass="mandatoryFieldMissing" errorClass="mandatoryFieldMissing" tooltip="true" />
</h:panelGrid>
Which looks like this in the html page:
Whenever I press the submit link, the page doesn't really go through validation, it seems to go with the last successull values instead. The result being that, if the phone number field is left empty, it does nothing and doesn't even render the <h:message> tag.
Actually, I have a workaround fix that looks like this:
<h:commandLink value="#{msg.Submit_Button}">
<a4j:support event="onclick" reRender="pinCodeDeliveryMsgText, pinCodeDeliveryMsg, pinCodeDeliveryFailedMsg, pinCodeDeliveryMainPanel, LastPinCodeMsg, SendingSMSMSG"
action="#{general.submit}"/>
</h:commandLink>
But i'm really curious to know what's the difference between a4j:commandLink and h:commandLink that makes one woirk and the other not.
TnX
Have you tried to set the process attribute of a4j:commandLink to the id of the inputText? Looks like you are just triggering rerendering of some components, so no model update is performed at all.

How to do client side updates in JSF 2.0

I'd like to do client side component updates. Example: disable a button when a checkbox is clicked:
<h:selectBooleanCheckbox value="true" onchange="button.disabled=true" />
<h:commandButton id="button" value="Save" />
The above doesn't work. Is there a way to do this declaratively in JSF?
It doesn't work because the JSF component ID is not necessarily the same as the generated HTML ID. JSF composes the HTML element ID and form element name based on the ID's of all UINamingContainer components in the tree -if any. The UIForm component is one of them. Rightclick the page in webbrowser and choose View Source. See and learn.
There are two ways to solve this problem:
Set prependId attribtue of <h:form> to false.
<h:form prependId="false">
<h:selectBooleanCheckbox value="true" onclick="button.disabled=true" />
<h:commandButton id="button" value="Save" />
</h:form>
Note that I'd rather use onclick="button.disabled=!checked" instead. The onchange is only fired when the input element loses focus and that is non-intuitive in case of checkboxes and radiobuttons. Also, you'd like to turn it back on when the checkbox is checked again, right?
Give the <h:form> a fixed ID so that you know how the generated form element name look like:
<h:form id="form">
<h:selectBooleanCheckbox value="true" onclick="form['form:button'].disabled=true" />
<h:commandButton id="button" value="Save" />
</h:form>
The brace notation is mandatory because the : is an illegal identifier character and just onclick="form:button.disabled=true" won't work. Also here, I'd rather use onclick="form['form:button'].disabled=!checked instead.
The same problem applies on document.getElementById() as well. So simply replacing button by document.getElementById('button') alone won't fix the problem.
simply use javascript
document.getElementById("buttonId").disabled="true";
Check this

Form value not passed to Seam bean after a4j reRender

I'm making a webapp in Seam but ran into a problem I can't seem to fix.
I have a JSF form where the customer can select a reservation type through a combobox. Based on the selected value, other form components gets rendered.
For example: the customer selects Hours as reservation type, a panelGroup gets rendered where the customer can select a start- and an end hour. But if the customer would select 'part of the day' as reservation type, a selectOneMenu gets rendered where the customer can select a part of the day (morning, afternoon, evening)
The rerendering well but the values of the components with a rendered conditional won't get passed to the bean. They stay null values.
This is the code i'm talking about:
<s:div id="spot"
rendered="#{selectedProduct.productType.name eq 'Flex Spot'}">
<h:panelGrid columns="2">
<h:outputText value="Reservation Type" />
<h:selectOneMenu value="#{selectedPeriodPart}">
<s:selectItems
value="#{productManager.getAvailableDayPartsSpot()}"
var="daypart"
label="#{daypart.label}"></s:selectItems>
<s:convertEnum />
<a4j:support ajaxSingle="true"
event="onchange"
action="#"
reRender="spot">
</a4j:support>
</h:selectOneMenu>
<h:outputText id="date_spot" value="Date" />
<a4j:outputPanel id="calendar_spot" layout="block">
<rich:calendar value="#{reservation.reservationPeriod.startDate}"
locale="en" cellWidth="24px"
cellHeight="22px"
style="width:200px" />
</a4j:outputPanel>
<h:outputText rendered="#{selectedPeriodPart eq 'DAY_PART'}"
value="Daypart" />
<h:selectOneMenu value="#{selectedDaypart}"
rendered="#{selectedPeriodPart eq 'DAY_PART'}">
<f:selectItem id="si_morning" itemLabel="Morning (6:00 - 12:00)"
itemValue="morning" />
<f:selectItem id="si_afternoon"
itemLabel="Afternoon (12:00 - 18:00)" itemValue="afternoon" />
<f:selectItem id="si_evening" itemLabel="Evening (18:00 - 00:00)"
itemValue="evening" />
</h:selectOneMenu>
<h:outputText rendered="#{selectedPeriodPart eq 'HOURS'}"
value="Hours" />
<h:panelGroup id="hours_spot"
rendered="#{selectedPeriodPart eq 'HOURS'}">
<ui:include src="/includes/reservation/select_hours.xhtml" />
</h:panelGroup>
</h:panelGrid>
</s:div>
Note: The calendar value do get passed back to the bean but the value of this piece of code doesn't (it does if you remove the rendered conditional):
selectOneMenu value="#{selectedDaypart}" rendered="#{selectedPeriodPart eq 'DAY_PART'}"
You need to ensure that the conditionals responsible for the outcome of the rendered attribute are also the same in the subsequent request of the form submit. Because when a component isn't rendered, JSF won't apply the request values them.
In a nutshell, the property behind #{selectedPeriodPart} needs to be the same in the subsequent request. There are several solutions:
Put bean in session scope. Easiest solution, but bad for server memory and client experience (updates would be reflected in multiple tabs/windows in same session).
Pass it through using <h:inputHidden>. Not sure though how this fits in the Ajax/Richfaces picture. Better use <a4j:keepAlive> here.
Use a conversation scope. Seam offers facilities for this.
I fixed it -.- Nothing was wrong with the code I posted.
Because I wasn't able to solve this issue I continued on an other page in the same conversation. I noticed some more strange behaviour: outjection of a variable didn't work etc.
I figured the mistake was in some other part of the code which, after corrected, fixed the whole problem.
Thx for answering guys!

Resources