正确反序列化带有反序列化器的对象与杰克逊
我需要一个自定义反序列化器来在复杂的POJO中投射字符串。反序列化一直运行直到使用反序列化器:特别是在使用自定义反序列化器时,我的对象的非对象属性未被序列化。正确反序列化带有反序列化器的对象与杰克逊
我有一个有pojo作为参数的宁静的web服务。
public PreventivoResponse calculate(@FormParam(value = "preventivo") PreventivoWs preventivo) throws Exception;
所以我的类PreventivoWs需要fromString(String)
方法。这里类定义:
@XmlRootElement
@XmlAccessorType(XmlAccessType.FIELD)
@JsonIgnoreProperties(ignoreUnknown = true)
@JsonInclude(JsonInclude.Include.NON_NULL)
public class PreventivoWs implements Serializable{
private static final long serialVersionUID = -554141724349909424L;
private ClienteMultiSelect cliente;
private String riferimento;
private List<EmailWS> email;
private String dataritiro;
private String dataconsegna;
private Long tipoconsegna;
private IndirizzoWS partenza;
private IndirizzoWS destinazione;
List<ColloWs> colli;
HashMap<Long, String> services;
...
}
里面的JSONObject我有一个枚举定义为
{
"value" : "A",
"text" : "Active"
}
但该对象需要串并转换器转换:
public class TipoPersonaFGJsonDeserializer extends JsonDeserializer<TipoPersonaFG> {
@Override
public TipoPersonaFG deserialize(JsonParser jsonParser, DeserializationContext context)
throws IOException, JsonProcessingException {
JsonToken currentToken = null;
while ((currentToken = jsonParser.nextValue()) != null) {
switch (currentToken) {
case VALUE_STRING:
switch (jsonParser.getCurrentName()) {
case "value":
String name = jsonParser.getText();
return TipoPersonaFG.valueOf(name);
}
break;
default:
break;
}
}
return null;
}
}
,它被标注上物业:
@JsonDeserialize(using = TipoPersonaFGJsonDeserializer.class)
private TipoPersonaFG tipo;
的fromString方法简单地调用杰克逊ObjectMapper:
public static PreventivoWs fromString(String jsonString) throws IOException{
ObjectMapper mapper = new ObjectMapper();
PreventivoWs oggetto = mapper.readValue(jsonString, PreventivoWs.class);
return oggetto;
}
如果jsonString未指定枚举,它工作正常:对象是完全反序列化; 如果我在jsonString中添加枚举,所有对象属性都被反序列化(email,cliente,partenza,destinazione,...),但其他属性被忽略(dataritiro,dataconsegna,tipoconsegna)。
为什么?定制解串器打破了反序列化的标准过程?
UPDATE: 解析过程被中断时,自定义串并转换器发生:ⅰ移动cliente
属性(它包含特定枚举)在JSON对象的末尾:现在字段dataconsegna,dataritiro等被deserialised 。
所以反序列化过程结束时,自定义解串器发生(甚至cliente对象中断)
解决了! 写在Jackson Wiki:
必须正确处理超越价值的任何令牌反序列化(没有更多的,还是不会少)
所以,问题是在解串器:你必须停止END_OBJECT时( })被发现,另一方面jsonParser继续直到流结束,消耗所有其他的令牌。
@Override
public TipoPersonaFG deserialize(JsonParser jsonParser, DeserializationContext context)
throws IOException, JsonProcessingException {
JsonToken currentToken = null;
String name = null;
while ((currentToken = jsonParser.nextValue()) != null) {
switch (currentToken) {
case VALUE_STRING:
switch (jsonParser.getCurrentName()) {
case "value":
name = jsonParser.getText();
break;
}
break;
case END_OBJECT:
if(name != null)
return TipoPersonaFG.valueOf(name);
else
return null;
}
}
return TipoPersonaFG.valueOf(name);
}
我已经加入的情况下条件END_OBJECT仅消耗第一“}”和正确地关闭枚举对象的解析。返回已在END_OBJECT情况下移动,否则'}'标记将保留在流中,并且它将关闭该枚举的父项。
所以你需要解析你的对象从'{'标记到'}'标记