gpt4 book ai didi

java - SelectManyCheckbox 中的 JSF/Primefaces 枚举转换器

转载 作者:行者123 更新时间:2023-12-01 09:01:24 24 4
gpt4 key购买 nike

我正在努力寻找为什么这不起作用。

我有一个 selectManyCheckbox

<h:form>

<p:selectManyCheckbox id="listCars" value="#{controller.listSelectedCarTypes}" converter="genericEnumConverter">
<f:selectItems value="#{controller.listCarTypeValues}" />
</p:selectManyCheckbox>

<p:commandButton value="Pesquisar" action="#{controller.filter}" process="@this, @form" update="panelResults" icon="ui-icon-search"/>

</h:form>

Controller 具有 getters/setters,列表的声明和初始化如下:

private List<CarType> listSelectedCarTypes = null;
private List<CarType> listCarTypeValues = null;

@PostConstruct
public void init(){
listSelectedCarTypes = new ArrayList<CarType>();
listCarTypeValues = new ArrayList<CarType>();
listCarTypeValues.add(CarType.OFF_ROAD);
listCarTypeValues.add(CarType.CONVERSIBLE);
listCarTypeValues.add(CarType.TRUCK);
}

枚举是基本的东西:

public enum CarType  {
OFF_ROAD {
@Override
public String getDescription() {
return "Cool but Hot Off the Road"
}
},
TRUCK {
@Override
public String getDescription() {
return "Holy moly a Monster Truck"
}
}

// lots of enums...
;

public abstract String getDescription();
@Override
public String toString() {
return getDescription();
}
}

最后,这是我从另一个 stackoverflow 引用资料中获得的转换器...

@FacesConverter(value="genericEnumConverter")
public class GenericEnumConverter implements Converter {

private static final String ATTRIBUTE_ENUM_TYPE = "GenericEnumConverter.enumType";

@Override
public String getAsString(FacesContext context, UIComponent component, Object value) {
System.out.println("value: "+value);
if (value instanceof Enum) {
component.getAttributes().put(ATTRIBUTE_ENUM_TYPE, value.getClass());
return ((Enum<?>) value).name();
} else {
throw new ConverterException(new FacesMessage("Value is not an enum: " + value.getClass()));
}
}

@Override
@SuppressWarnings({"rawtypes", "unchecked"})
public Object getAsObject(FacesContext context, UIComponent component, String value) {
Class<Enum> enumType = (Class<Enum>) component.getAttributes().get(ATTRIBUTE_ENUM_TYPE);
try {
System.out.println("enumType: "+enumType+ " value: "+value);
System.out.println("CarType.valueOf(value): "+CarType.valueOf(value));
System.out.println("Enum.valueOf(enumType, value): "+Enum.valueOf(enumType, value));
return Enum.valueOf(enumType, value);
} catch (IllegalArgumentException e) {
throw new ConverterException(new FacesMessage("Value is not an enum of type: " + enumType));
}
}

}

因此,当 View 和 Controller 初始化时,它会按预期执行,并且为组件的每个值调用 getAsString,并正常打印。输出:

value: Cool but Hot Off the Road
value: Holy moly a Monster Truck
...

但是,当我提交表单并调用 getAsObject 时,它会在 Enum.valueOf(enumType, value) 上抛出 IllegalArgumentException。

enumType: class my.project.enums.CarType$120 value: TRUCK
CarType.valueOf(value): Holy moly a Monster Truck
Value is not an enum of type: class my.project.enums.CarType$120

奇怪的是...这个:CarType.valueOf(value) 有效...

但是这个:Enum.valueOf(enumType, value) 不要。

为了使 selectManyCheckbox 正常工作,我必须为我的枚举 CarType 而不是 Generic 创建一个显式转换器。

谁能给我解释一下吗?提前致谢。

最佳答案

这是核心 Java 问题。枚举类 CarType有抽象方法,每个枚举值都是 CarType 的实例子类。请参阅:Java Enum getDeclaringClass vs getClass

解决方案是设置((Enum)value).getDeclaringClass()而不是value.getClass()作为属性 ATTRIBUTE_ENUM_TYPEgetAsString(...)方法。

提示:我认为这就是类的问题,因为我注意到类名中有一个数字 my.project.enums.CarType$120 .

关于java - SelectManyCheckbox 中的 JSF/Primefaces 枚举转换器,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/41637649/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com