0

I have a jsf 2 select input with a converter tied to the selectentries. My object has an id field that is a long that should be the value. When my converter is called, it gets called with the whole list of select items (List<SimpleEntityGroup>) instead of the SimpleEntityGroup so I can just return the .getId() of the group.

The debug output is:

Converting to String

[SimpleEntityGroup [id=1, name=Group 1], SimpleEntityGroup [id=2, name=Group 2], SimpleEntityGroup [id=3, name=Group 3]]

I am expecting the method to be called 3 times with a single SimpleEntityGroup each time, not all 3 as a list at once. The method is supposed to return a String, and if I return "1" then all my values in the select are one, so I know it is using the converter in the right spot. Why is it calling it like this?

<h:selectOneMenu value="#{simpleEntityBacking.simpleEntity.group}" converter="SimpleEntityGroupConverter">
    <f:selectItems value="#{simpleEntityBacking.groups}" var="c"
        itemLabel="#{c.name}" itemValue="#{c.id}" />
</h:selectOneMenu>

Here is my backing bean - getters and setters and all omitted:

public class SimpleEntityBacking {
    private static final Logger L = Logger.getLogger(SimpleEntityBacking.class);

    @ManagedProperty(value="#{simpleEntity}")
    private SimpleEntity simpleEntity;
    
    @ManagedProperty(value="#{groups}")
    private List<SimpleEntityGroup> groups;
    
    @EJB
    private SimpleEntityDao ed;
    
    /**
     * 
     */
    public SimpleEntityBacking() {
        
    }

Here's my converter:

/* (non-Javadoc)
     * @see javax.faces.convert.Converter#getAsObject(javax.faces.context.FacesContext, javax.faces.component.UIComponent, java.lang.String)
     */
    @Override
    public Object getAsObject(FacesContext arg0, UIComponent arg1, String arg2) {
        return ed.getGroupById(new Long(arg2));
    }

    /* (non-Javadoc)
     * @see javax.faces.convert.Converter#getAsString(javax.faces.context.FacesContext, javax.faces.component.UIComponent, java.lang.Object)
     */
    @Override
    public String getAsString(FacesContext arg0, UIComponent arg1, Object arg2) {
        L.debug("Converting to String");
        L.debug(arg2);
        SimpleEntityGroup g = (SimpleEntityGroup) arg2;
        return g.getId().toString();
    }
Community
  • 1
  • 1
mikeb
  • 10,578
  • 7
  • 62
  • 120

1 Answers1

0

Found the answer, the select needs to look like this:

                <h:selectOneMenu value="#{simpleEntityBacking.simpleEntity.group}" converter="#{simpleEntityGroupConverter}">
                    <f:selectItems value="#{simpleEntityBacking.groups}" var="c"
                        itemLabel="#{c.name}" />
                </h:selectOneMenu>

Note the converter has a #{} around it and the itemValue is not specified.

Now, the converter has to look like so:

@ManagedBean
@ApplicationScoped
public class SimpleEntityGroupConverter implements Converter {
    private static final Logger L = Logger.getLogger(SimpleEntityGroupConverter.class);

    @EJB
    private SimpleEntityDao ed;

The JSF converter annotation for the class does not allow EJB injection, so you have to annotate as a managed bean and do the value=#{} in the select.

mikeb
  • 10,578
  • 7
  • 62
  • 120