使用的是ConverterFactory这个接口:
自定义实现类:
感谢
https://github.com/albertchendao/demos/tree/master/java/spring/HelloWorld-MVC-Enum
虽然没提出什么好的想法,不过还是小小的借鉴了下,不过仍然没有解决我的疑问:
下面的实现类:
public final class StringToBlackType implements ConverterFactory<String, BlackType>{
@Override
public <T extends BlackType> Converter<String, T> getConverter(
Class<T> targetType) {
if(!targetType.isEnum()) {
throw new UnsupportedOperationException("只支持转换到枚举类型");
}
return new StringToEnum<>(targetType);
}
private class StringToEnum<T extends BlackType> implements Converter<String, T> {
private final T[] all;
public StringToEnum(Class<T> enumType) {
all = enumType.getEnumConstants();
}
public T convert(String source) {
if (source.length() == 0) {
// It's an empty enum identifier: reset the enum value to null.
return null;
}
try {
Integer v = Integer.valueOf(source);
for(T t:all){
if(t.getBtid() == v) return t;
}
return null;
} catch (NumberFormatException e) {
return null;
}
}
}
}
以下是个人理解:
targetClass 是属性的目标类型,而source 从servlet 传过来的都是String类型,当目标类型是Enum类型的时候,开始调用converter,并试图转换成targetClass。下面是spring 自定义的stirngToEnum
/**
* Converts from a String to a {@link java.lang.Enum} by calling {@link Enum#valueOf(Class, String)}.
*
* @author Keith Donald
* @author Stephane Nicoll
* @since 3.0
*/
@SuppressWarnings({"unchecked", "rawtypes"})
final class StringToEnumConverterFactory implements ConverterFactory<String, Enum> {
@Override
public <T extends Enum> Converter<String, T> getConverter(Class<T> targetType) {
return new StringToEnum(ConversionUtils.getEnumType(targetType));
}
private class StringToEnum<T extends Enum> implements Converter<String, T> {
private final Class<T> enumType;
public StringToEnum(Class<T> enumType) {
this.enumType = enumType;
}
@Override
public T convert(String source) {
if (source.isEmpty()) {
// It's an empty enum identifier: reset the enum value to null.
return null;
}
return (T) Enum.valueOf(this.enumType, source.trim());
}
}
}
把这个转换器注入spring ,可以把文本转换成enum实例,注意大写
<!-- 转换器 -->
<bean id="conversionService"
class="org.springframework.format.support.FormattingConversionServiceFactoryBean">
<property name="converters">
<list>
<bean class="org.springframework.core.convert.support.StringToEnumConverterFactory" />
</list>
</property>
</bean>
<mvc:annotation-driven conversion-service="conversionService" />
枚举实例:
public enum BlackType {
ONE(3,"one"),
TWO(2,"two"),
THREE(1,"three"),
EMPTY(0,"none");
private final int btid;
private final String comment;
BlackType(int btid,String comment){
this.btid = btid;
this.comment = comment;
}
public int getBtid() {
return btid;
}
public String getComment() {
return comment;
}
public static BlackType fromById(int id){
for(BlackType b:values()){
if(b.getBtid() == id) return b;
}
return EMPTY;
}
}
如果想要在converter中实现子类特有的功能,就自己实现ConverterFactory,不过我依然有些不太明白这种使用factory所带来的好处,如果只是实现转换功能实现Converter就行了