Java JSF列表转换器
如何在JSF2中为类a的项目列表编写转换器?我已经为类a编写了一个转换器,但是这些项使用默认的toString()函数显示:A@hashcode“ 我需要使用转换器,而不是支持bean方法,以便进行验证(Hibernate Validator) 更多信息 以下是我使用列表的方式:Java JSF列表转换器,java,jsf-2,converter,Java,Jsf 2,Converter,如何在JSF2中为类a的项目列表编写转换器?我已经为类a编写了一个转换器,但是这些项使用默认的toString()函数显示:A@hashcode“ 我需要使用转换器,而不是支持bean方法,以便进行验证(Hibernate Validator) 更多信息 以下是我使用列表的方式: <h:inputText id="destinations" value="#{rule.destinations}" converter="gr.panayk.vinyls.Destination"/>
<h:inputText id="destinations" value="#{rule.destinations}" converter="gr.panayk.vinyls.Destination"/>
其中#{rule.destinations}是List
类型。我期待一个逗号分隔的转换目的地列表
解决方案
我附上BalusC提议的列表转换器
@FacesConverter(value="gr.panayk.vinyls.converter.DestinationList")
public class DestinationListConverter implements Converter
{
@Override
public Object getAsObject(final FacesContext context, final UIComponent component, final String values)
{
final Validator validator = Validation.buildDefaultValidatorFactory().getValidator();
final List<Destination> result = new ArrayList<Destination>();
for (String value : values.split(",", -1))
{
final String trimmedValue = value.trim();
final Set<ConstraintViolation<Destination>> violations = validator.validateValue(Destination.class, "data", trimmedValue);
if (!violations.isEmpty())
{
throw new ConverterException(new FacesMessage(violations.iterator().next().getMessage()));
}
result.add(new Destination(trimmedValue));
}
final Set<ConstraintViolation<Rule>> violations = validator.validateValue(Rule.class, "destinations", result);
if (!violations.isEmpty())
{
throw new ConverterException(new FacesMessage(violations.iterator().next().getMessage()));
}
return result;
}
@Override
public String getAsString(final FacesContext context, final UIComponent component, final Object value)
{
if (value instanceof List<?>)
{
final StringBuffer result = new StringBuffer();
final List<?> list = (List<?>) value;
for (int i = 0; i < list.size()-1; i++)
{
if (list.get(i) instanceof Destination)
{
result.append(((Destination) list.get(i)).getData());
result.append(", ");
}
else
{
throw new IllegalArgumentException( "Cannot convert " + value + " object to Destination in DestinationConverter." );
}
}
if (!list.isEmpty())
{
if (list.get(list.size()-1) instanceof Destination)
{
result.append(((Destination) list.get(list.size()-1)).getData());
}
else
{
throw new IllegalArgumentException( "Cannot convert " + value + " object to Destination in DestinationConverter." );
}
}
return result.toString();
}
else
{
throw new IllegalArgumentException( "Cannot convert " + value + " object to List in DestinationConverter." );
}
}
}
@FacesConverter(value=“gr.panayk.vinyls.converter.DestinationList”)
公共类DestinationListConverter实现转换器
{
@凌驾
公共对象getAsObject(最终FacesContext上下文、最终UIComponent组件、最终字符串值)
{
最终验证器验证器=Validation.buildDefaultValidatorFactory().getValidator();
最终列表结果=新建ArrayList();
for(字符串值:values.split(“,”,-1))
{
最终字符串trimmedValue=value.trim();
最终设置冲突=validator.validateValue(Destination.class,“data”,trimmedValue);
如果(!inflictions.isEmpty())
{
抛出新的ConverterException(新的FacesMessage(inflictions.iterator().next().getMessage());
}
结果.添加(新目的地(trimmedValue));
}
最终设置冲突=validator.validateValue(Rule.class,“destinations”,result);
如果(!inflictions.isEmpty())
{
抛出新的ConverterException(新的FacesMessage(inflictions.iterator().next().getMessage());
}
返回结果;
}
@凌驾
公共字符串getAsString(最终FacesContext上下文、最终UIComponent组件、最终对象值)
{
if(列表的值实例)
{
最终StringBuffer结果=新StringBuffer();
最终列表=(列表)值;
对于(int i=0;i
我已经为类a编写了一个转换器,但是这些项使用默认的toString()函数显示:A@hashcode“
如果没有在组件上显式声明转换器,则可能发生这种情况。例如,在
和
中,显式声明转换器是强制的,因为JSF/EL所知道的是值的类型是列表
,而不是列表
(在运行时会丢失泛型类型)。如果不声明转换器,则这些值将被视为字符串
(这是HTML输出和HTTP请求参数值的默认值)
例如
与
当您使用诸如
之类的单项输入时,不需要显式声明上述转换器,因为for class
无论如何都会与之匹配。现在我得到:java.lang.IllegalArgumentException:无法转换[gr.panayk.vinyls.model]。Destination@59c527be,gr.panayk.vinyls.model。Destination@679b622d]对象在DestinationConverter中。这是我的转换器抛出的消息。它似乎正在尝试将列表转换为项目。我会在我的用例中添加更多信息。顺便说一句,谢谢。我认为你是JSF领域的顶级专家。如果您需要更多信息,请告诉我。您只需编写相应的代码,即可在getAsString()
和getAsObject()
中执行列表
字符串
转换作业(分别构建逗号分隔的字符串和在逗号上拆分)。然而,这是一个非常特殊的用例,使得转换器对于多次获取/返回单个项目的正常输入不可用。没关系,我不会在其他任何地方使用列表。谢谢
@FacesConverter(value="aConverter", forClass=A.class)
public class AConverter implements Converter {
// ...
}