0

Using PrimeFaces 5.3 running in WebSphere 8.5.5

I have a form with two required fields, a inputText and a selectOneMenu. I select a valid value (e.g. Stateless) in the menu but leave the text field blank causing an error. I then correct the text field but the user also presses the "S" key on the menu - intending to select "Stateless" again but instead the result is "Select Country" which means nothing selected - another validation error.

When the user presses ENTER they get another error message for the selectOneMenu and the field itself is highlighted as being in error but a valid value of "Stateless" appears - which is confusing to me imagine how users are going to react!

Is there a way to always preserve the user entered values?

I am attaching sanitized code that demonstrates the problem. I have menus that list all countries (as well as US states, Mexican states, Canadian provinces) so it is impossible to assign a letter for the default value that is not also applicable to a valid value.

XHTML

<!DOCTYPE html>
<html   xmlns="http://www.w3.org/1999/xhtml"
        xmlns:h="http://java.sun.com/jsf/html"
        xmlns:ui="http://java.sun.com/jsf/facelets"
        xmlns:f="http://java.sun.com/jsf/core"
        xmlns:p="http://primefaces.org/ui">
    <h:head>
        <!-- IE standards mode override *must* appear first - use resource ordering facet to force this. -->
        <f:facet name="first">
            <meta http-equiv="x-ua-compatible" content="IE=edge" />
            <!-- 
                <meta http-equiv="x-ua-compatible" content="IE=edge" /> 
                ^ Prevents IE from reverting to 'IE7 Standards Mode' when accessing via non-localhost hostname.
                Must appear immediately after <title> element. Note that setting this at the server level (ie: in websphere)
                is considered preferable. See: http://stackoverflow.com/questions/6156639/x-ua-compatible-is-set-to-ie-edge-but-it-still-doesnt-stop-compatibility-mode
            -->
        </f:facet>
    </h:head>
    <h:body>
        <br/>
        <h:form id="dataForm">
            <p:outputLabel for="note" value="Note"/>:
            <p:inputText id="note" size="30" maxlength="50" value="#{Test.note}" required="true" />
            <br />
            <p:outputLabel for="citizenship" value="Citizenship:"/>
            <p:selectOneMenu id="citizenship" value="#{Test.citizenship}" required="true">
                <f:selectItem itemLabel="Select Country..."/>
                <f:selectItem itemValue="1" itemLabel="Canada"/>
                <f:selectItem itemValue="2" itemLabel="United States"/>
                <f:selectItem itemValue="3" itemLabel="Mexico"/>
                <f:selectItem itemValue="-1" itemLabel="Stateless"/>
            </p:selectOneMenu>
            <br />
            <p:commandButton value="Save" type="submit" action="#{Test.save}" ajax="false" />
        </h:form>
    </h:body>
</html>

Java

import javax.inject.Named;

@Named ("Test")
public class Test 
{
    private String note;
    private Integer citizenship;

    public Integer getCitizenship() 
    {
        return citizenship;
    }

    public String getNote() 
    {
        return note;
    }

    public void setNote(String note) 
    {
        this.note = note;
    }

    public void setCitizenship(Integer citizenship) 
    {
        this.citizenship = citizenship;
    }

    public String save()
    {
        System.out.println("Citizenship=" + this.citizenship);

        return "test";
    }
}

EDIT

Applied following modification but it had no effect at all. When I pressed "S" it would still select the "Select Country..." option and if I clicked on the control I could still see and select the "Select Country..." option.

<p:selectOneMenu id="citizenship" value="#{Test.citizenship}" required="true" hideNoSelectionOption="true">
                <f:selectItem itemValue="#{null}" itemLabel="Select Country..." noSelectionOption="true"/>

Something else I noticed while studying this in detail in my browser debugger. The selected value of the HTML option element does not change when I select a different option - rather a label does. The actual HTML select element is inside a DIV with the class "ui-helper-hidden-accessible". I am wondering if this is might mean something...

BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
BigMac66
  • 1,528
  • 5
  • 19
  • 35
  • I have found a hack that sorta works. If I add a space in front of the default country it prevents the default value from being selected by a letter. E.g. replace "Select Country..." with " Select Country...". But if the user does intentionally select the default value the odd behaviour where the field gets the last valid value but is still marked as being in error returns. – BigMac66 Jun 10 '16 at 17:50
  • Isn't http://stackoverflow.com/questions/13478663/noselectionoption-attribute part of your problem? – Kukeltje Jun 10 '16 at 18:22

2 Answers2

0

So it's specified that "Input components keep their local values at state when validation fails." This leads me to believe you're problem here is that the select country option is missing the itemLabel tag. I usually assign it itemLabel = "" or null. There is also a noSelectionOption option for the f:selectItem that may help.

This answer helped me with a similar problem a while back: Best way to add a "nothing selected" option to a selectOneMenu in JSF

Community
  • 1
  • 1
ezPaint
  • 152
  • 1
  • 8
0

OK I found a way to fix it - essentially I switch from the PrimeFaces version to plain JSF. That is:

<p:selectOneMenu id="citizenship" value="#{Test.citizenship}" required="true" hideNoSelectionOption="true">

To

<h:selectOneMenu id="citizenship" value="#{Test.citizenship}" required="true" hideNoSelectionOption="true">

There appears to be something wrong with the version of PrimeFaces we are allowed to use on WebSphere - this happens to be the third time I have "fixed" a problem by switch to plain JSF.

BigMac66
  • 1,528
  • 5
  • 19
  • 35