我有这个SelectOneMenu:
<h:selectOneMenu value="#{orderController.requestVO.requestSituation}">
<f:converter converterId="ComboConverter"/>
<f:selectItems value="#{orderController.requestSituation}" var="requestSituation"
itemLabel="#{requestSituation.description}" itemValue="#{requestSituation}" />
</h:selectOneMenu>
requestSituation
是ArrayList
,内容RequestSituationVO
它填充正确,生成此HTML:
<select name="j_idt14:j_idt20" size="1">
<option value="13">Pedido Recusado</option>
<option value="11">Pedido Validado</option>
<option value="12" selected="selected">Pedido Confirmado</option>
<option value="12" selected="selected">Pedido Faturado</option>
</select>
我有这个Converter
,这里是我困惑的地方,我读了很多,我知道它必须做什么,但不知道它是如何工作的。
这是:
@FacesConverter(value = "ComboConverter", forClass = RequestSituationVO.class)
public class ComboConverter implements Converter
{
private static RequestSituationVO requestSituationVO = new RequestSituationVO();
@Override
public Object getAsObject(FacesContext context, UIComponent component, String value)
{
requestSituationVO.setId(Integer.valueOf(value));
requestSituationVO = (RequestSituationVO) new RequestSituationBO().getRequestSituation(requestSituationVO).toArray()[0];
return (RequestSituationVO) requestSituationVO;
}
@Override
public String getAsString(FacesContext context, UIComponent component, Object value)
{
requestSituationVO = (RequestSituationVO) value;
String teste = String.valueOf(requestSituationVO.getId());
return teste;
}
}
当我提交自己的网页时,我认为SelectOneMenu
会自动从requestSituation
设置requestVO
方法的值。但是当我提交时,我会收到一条消息Value not valid
,引用我的SelectOneMenu
。
我需要在RequestSituationVO
上设置所选值,以便将其发送到Business方法。
答案 0 :(得分:10)
你的转换器很好。否则你会得到类似
的转换错误'null Converter'的转换错误设置值'com.example.RequestSituationVO@hashcode'
您有验证错误。如果所选项目的Object#equals()
测试未对列表中的任何可用项目返回true
,则会抛出此特定项目。 JSF正在检查以防止被篡改的请求发起攻击。在您的特定情况下,这可能有以下原因:
equals()
类的RequestSituationVO
方法丢失或损坏。#{orderController.requestSituation}
在显示表单的请求和处理表单提交的请求之间发生了不兼容的更改。我认为这是前者。鉴于您的RequestSituationVO
具有唯一标识对象的Integer id
属性,这应该是:
@Override
public boolean equals(Object other) {
return (other instanceof RequestSituationVO) && (id != null)
? id.equals(((RequestSituationVO) other).id)
: (other == this);
}
@Override
public int hashCode() {
return (id != null)
? (this.getClass().hashCode() + id.hashCode())
: super.hashCode();
}
如果equals()
方法不是问题,那么它就是后一种原因。这可以通过确保#{orderController.requestSituation}
在显示表单和处理表单提交期间返回完全相同的列表来解决。这可以通过将bean放在视图范围中而不是在getter中完成业务逻辑来实现。或者,如果它实际上代表了应用程序范围的数据,您可以将其重构为单独的应用程序范围的bean。
答案 1 :(得分:3)
您似乎忘了在equals
中实施hashCode
和RequestSituation
这是非常重要,因为JSF会将提交的值与所有给定的项目进行比较。
如果您未实施equals
,则认为提交的项目不在列表中,
所以它拒绝它。 (The value is not valid.
)