Primefaces selectOneMenu侦听器未使用除字符串以外的对象调用

los*_*gio 2 primefaces jsf-2 tomcat7

我正在使用Jsf 2.0和Primefaces 3.2实现一个webapp.我注意到了这种意想不到的行为:我有一个selectOneMenu和一个commandButton,如下所示

<p:selectOneMenu id="selsel" value="#{bean.myObj}">
  <f:selectItems value="#{bean.myObjList}" />
</p:selectOneMenu>
<p:commandButton id="btnid" value="Ok" actionListener="#{bean.updateSelectValues()}" />
Run Code Online (Sandbox Code Playgroud)

会发生的是,如果myObj不是a String,updateSelectValues则不调用该方法.我根本看不到任何异常或错误,它只是没有被调用.这是支持bean:

private List<MyObj> myObjList;
private MyObj myObj;
// getters and setters

public void updateSelectValues() {
  System.out.println(this.myObj);
}
Run Code Online (Sandbox Code Playgroud)

myObj的代码:

public class MyObj implements Serializable {

  private static final long serialVersionUID = 1L;

  private String param1;
  private int param2;

  @Override
  public String toString() {
    StringBuilder builder = new StringBuilder();
    builder.append("MyObj [param1=");
    builder.append(this.param1);
    builder.append(", param2=");
    builder.append(this.param2);
    builder.append("]");
    return builder.toString();
  }

}
Run Code Online (Sandbox Code Playgroud)

Bal*_*usC 8

那是因为HTML和HTTP不了解Java对象.String当JSF生成HTML时,所有Java对象都将转换为.String当要由JSF处理提交的表单数据时,应该将所有HTTP请求参数转换回Java对象.

至于你的具体问题,如果你已经添加了一个<h:message>,<h:messages>或等效的形式PrimeFaces(也更新它的AJAX的提交),那么你应该已经注意到了"空转换器"转换错误.此外,如果您已经注意到服务器日志,您还应该看到有关未处理消息的警告.

您需要创建一个自定义Converter,在其中转换MyObj它的唯一String表示.例如:

@FacesConverter(forClass=MyObj.class)
public class MyObjConverter implements Converter {

    @Override
    public String getAsString(FacesContext context, UIComponent component, Object valueToRender) {
        // Convert MyObj to its unique String representation.
    }

    @Override
    public Object getAsObject(FacesContext context, UIComponent component, String submittedValue) {
        // Convert String to MyObj.
    }

}
Run Code Online (Sandbox Code Playgroud)

通常这些对象已经存储在某个数据库中或通过其ID进行映射.然后,您可以使用该ID作为唯一String表示.