我正在尝试使用JSON将Ext JS 4中的表单提交给Spring 3 Controller。我使用Spring的内置Jackson JSON支持使用Jackson 1.9.8进行序列化/反序列化。
我有一个状态字段,在Domain对象中最初为新记录。提交表单时,它会生成以下json(缩小到几个字段)
{"id":0,"name":"someName","status":""}
提交后,在服务器日志中看到以下内容
"nested exception is org.codehaus.jackson.map.JsonMappingException: Can not construct instance of com.blah.domain.StatusEnum from String value '': value not one of the declared Enum instance names"
所以看来杰克逊期待一个有效的枚举值或根本没有值,包括一个空字符串。无论是在Ext JS,Jackson还是Spring,我如何解决这个问题?
我尝试创建自己的ObjectMapper,例如
public class MyObjectMapper extends Object Mapper {
public MyObjectMapper() {
configure(DeserializationConfig.Feature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT, true);
}
}
并将其作为属性发送到MappingJacksonMappingView,但这不起作用。我也尝试将其发送到MappingJacksonHttpMessageConverter,但这不起作用。附带问题:我应该在自己的ObjectMapper中发送哪一个?
建议?
答案 0 :(得分:2)
您可以做的另一件事是为您的特定枚举创建一个专门的反序列化器(扩展org.codehaus.jackson.map.JsonDeserializer
),它具有不匹配的默认值。我所做的就是为枚举创建一个抽象的反序列化程序,使其反序列化,并在遇到问题时加快这个过程。
public abstract class EnumDeserializer<T extends Enum<T>> extends JsonDeserializer<T> {
private Class<T> enumClass;
public EnumDeserializer(final Class<T> iEnumClass) {
super();
enumClass = iEnumClass;
}
@Override
public T deserialize(final JsonParser jp,
final DeserializationContext ctxt) throws IOException, JsonProcessingException {
final String value = jp.getText();
for (final T enumValue : enumClass.getEnumConstants()) {
if (enumValue.name().equals(value)) {
return enumValue;
}
}
return null;
}
}
这是泛型类,基本上只需要一个枚举类,迭代枚举的值并检查下一个标记以匹配任何名称。如果他们这样做,则返回它,否则返回null;
然后如果你有一个enum MyEnum,你就可以创建一个EnumDeserializer
的子类:
public class MyEnumDeserializer extends EnumDeserializer<MyEnum> {
public MyEnumDeserializer() {
super(MyEnum.class);
}
}
然后,无论您在哪里声明MyEnum
:
@JsonDeserialize(using = MyEnumDeserializer.class)
public enum MyEnum {
...
}
答案 1 :(得分:1)
我不熟悉Spring,但为了以防万一,在客户端处理它可能更容易:
Ext.define('My.form.Field', {
extend: 'Ext.form.field.Text',
getSubmitValue: function() {
var me = this,
value;
value = me.getRawValue();
if ( value === '' ) {
return ...;
}
}
});
您也可以通过将allowBlank
属性设置为false
来禁止提交空字段。
答案 2 :(得分:1)
结束在EXT JS模型中添加默认值,因此始终存在值。希望我没有这个,但这不是什么大不了的事。
答案 3 :(得分:1)
我有同样的问题。我正在阅读带有一些空字符串的JSON流。我无法控制JSON流,因为它来自外部服务。我总是收到相同的错误消息。我试过这个:
mapper.getDeserializationConfig().with(DeserializationConfig.Feature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT);
但没有任何影响。看起来像一个Bug。