0

I created the following custom tag for my JSF 2.2 application:

<et:gridRowLabelPasswordMessage
    label_name="Password"
    password_id="password"
    password_value="#{myAuthenticator.password}"
    password_required="true"
    password_match=""
    password_binding="#{pw}" />

The following is the key part of the custom tag file:

<p:password
    id="#{password_id}"
    value="#{password_value}"
    placeholder="#{label_name}"
    binding="#{password_binding}"
    required="#{password_required}"
    requiredMessage="#{label_name} is required."
    match="#{password_match}" />

Due to an issue with PrimeFaces p:password, I can not set match="" so I need to test password_match and only include match if password_match is not empty. After first, I tried to use the ui:fragment as shown below:

<ui:fragment rendered="#{empty password_match}">
    <p:password
        id="#{password_id}"
        value="#{password_value}"
        placeholder="#{label_name}"
        binding="#{password_binding}"
        required="#{password_required}"
        requiredMessage="#{label_name} is requred." />
</ui:fragment>
<ui:fragment rendered="#{not empty password_match}">
    <p:password
        id="#{password_id}"
        value="#{password_value}"
        placeholder="#{label_name}"
        binding="#{password_binding}"
        required="#{password_required}"
        requiredMessage="#{label_name} is requred."
        match="#{password_match}" />
</ui:fragment>

The result was that when I set password_match = "" the p:password was not rendered at all. In other words, neither test returned true. My only theory is that ui:fragment doesn't work in the custom tag files.

I then changed my code to the following and it worked as expected.

<c:choose>
    <c:when test="#{empty password_match}">
        <p:password
            id="#{password_id}"
            value="#{password_value}"
            placeholder="#{label_name}"
            binding="#{password_binding}"
            required="#{password_required}"
            requiredMessage="#{label_name} is required." />
    </c:when>
    <c:otherwise>
        <p:password
            id="#{password_id}"
            value="#{password_value}"
            placeholder="#{label_name}"
            binding="#{password_binding}"
            required="#{password_required}"
            requiredMessage="#{label_name} is required."
            match="#{password_match}" />
    </c:otherwise>
</c:choose>
BalusC
  • 1,082,665
  • 372
  • 3,610
  • 3,555
Reed Elliott
  • 223
  • 2
  • 15
  • The match attribute of an password should point to the id of a second `p:password`. Does it? And why do you need the binding? And what PF / JsFimpl version? – Kukeltje Jul 27 '15 at 06:39
  • 3
    You're creating 2 components with the same id. That could be the issue. `rendered=false` means component gets created, but not rendered. `c:when test="false"` means component does not get created. – Vsevolod Golovanov Jul 27 '15 at 08:10
  • @Vsevolod: It is. Only, I wonder why OP didn't got an exception like this http://stackoverflow.com/questions/18768527/jsf-conditional-includes-cause-component-id-has-already-been-found-in-the-view – BalusC Jul 27 '15 at 08:12
  • @Kukeltje: I want my tag to be able to handle the case where I set the match and the case where I do not set the match. I believe that PrimeFaces 5.2.8 has a bug as described in [PrimeFaces Forum](http://forum.primefaces.org/viewtopic.php?f=3&t=42851). I am using GlassFish 4.1. I bind the password to a variable so that I can test for invalid and display a message. See above link for complete code. – Reed Elliott Jul 28 '15 at 02:23
  • @VsevolodGolovanov: Thanks! I am just beginning to understand the JSF lifecycle and the difference between [taghandlers and components](http://www.ninthavenue.com.au/jsf-c-foreach-vs-ui-repeat). Your answer fits in well with my new understanding. – Reed Elliott Jul 28 '15 at 02:32

0 Answers0