简体   繁体   English

RestTemplate和Jackson-自定义JSON反序列化?

[英]RestTemplate & Jackson - Custom JSON deserializing?

The webservice returns an empty string instead of NULL which causes Jackson to crash. Web服务将返回一个空字符串而不是NULL,这将导致Jackson崩溃。 So I created a custom parser, and I'm trying to parse it manually? 因此,我创建了一个自定义解析器,并尝试手动解析它? Any idea How I could achieve this? 知道我该如何实现吗?

What Am I doing wrong here? 我在这里做错了什么? All I'm trying to do is to parse JSON to object as I normally would. 我要做的就是像往常一样将JSON解析为对象。 The field names are added to my properties using @JsonProperty so the parser should know how to convert it. 使用@JsonProperty将字段名称添加到我的属性中,因此解析器应该知道如何进行转换。

public class InsertReplyDeserializer extends JsonDeserializer<ListingReply> {

    @Override
    public ListingReply deserialize(JsonParser jsonParser, DeserializationContext arg1)
            throws IOException, JsonProcessingException {

        ObjectCodec oc = jsonParser.getCodec();
        JsonNode node = oc.readTree(jsonParser);

        // If service returns "" instead of null return a NULL object and don't try to parse
        if (node.getValueAsText() == "")
            return null;


       ObjectMapper objectMapper = new ObjectMapper();
       ListingReply listingReply = objectMapper.readValue(node, ListingReply.class);


       return listingReply;
    }

}

Here is how I resolved it 这是我解决的方法

@Override
public MyObject deserialize(JsonParser jsonParser, DeserializationContext arg1)
        throws IOException, JsonProcessingException {

    ObjectCodec oc = jsonParser.getCodec();
    JsonNode node = oc.readTree(jsonParser);

    if (node.getValueAsText() == "")
        return null;

    MyObject myObject = new MyObject();
    myObject.setMyStirng(node.get("myString").getTextValue());

    JsonNode childNode = node.get("childObject");
    ObjectMapper objectMapper = new ObjectMapper();
    ChildObject childObject = objectMapper.readValue(childNode,
            ChildObject.class);

             myObject.setChildObject(childObject);
             return myObject;
}

I am not sure you need to manually parse response. 我不确定您是否需要手动解析响应。 You solution would work but seems sub-optimal in my opinion. 您的解决方案可以工作,但在我看来似乎不太理想。 Since it looks like that you are using RestTemplate, you should rather write (or move your parser code to) your own message converter. 由于看起来您正在使用RestTemplate,因此您应该宁愿编写(或将解析器代码移至)自己的消息转换器。 Then add this converter to your rest template object which will internally deserialize the value for you. 然后将此转换器添加到您的rest模板对象中,该对象将在内部为您反序列化值。 Something along the lines, 沿线的东西,

public class CustomHttpmsgConverter extends  AbstractHttpMessageConverter<Object> {
private ObjectMapper objectMapper = new ObjectMapper();
@Override
protected Object readInternal(Class clazz, HttpInputMessage inputMessage) throws IOException, HttpMessageNotReadableException {
   InputStream istream = inputMessage.getBody();
   String responseString = IOUtils.toString(istream);
   if(responseString.isEmpty()) //if your response is empty
     return null;
   JavaType javaType = getJavaType(clazz);
   try {
       return this.objectMapper.readValue(responseString, javaType);
   } catch (Exception ex) {
    throw new HttpMessageNotReadableException(responseString);
    }
}

//add this converter to your resttemplate
    RestTemplate template = new RestTemplate();
    List<HttpMessageConverter<?>> converters = new ArrayList<HttpMessageConverter<?>>();
    converters.add(new CustomHttpmsgConverter());
    template.setMessageConverters(converters);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM