java Jackson - 反序列化嵌套的 JSON

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/17921188/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-11-01 19:36:56  来源:igfitidea点击:

Hymanson - Deserialize nested JSON

javaHymansonjson-deserialization

提问by Anand

I have a JSON string which will be of the following format:

我有一个 JSON 字符串,其格式如下:

{
  "response": { 
    "execution_status": "ready", 
    "report": {
      "cache_hit": true, 
      "created_on": "2013-07-29 08:42:42", 
      "fact_cache_error": null, 
      "fact_cache_hit": true, 
      "header_info": null, 
      "name": null, 
      "report_size": "5871", 
      "row_count": "33", 
      "url": "report-download?id=278641c223bc4e4d63df9e83d8fcb4e6"
     }, 
  "status": "OK"
  }
}

The response part of the JSON is common for a bunch of response types. The report part of this JSON holds good only for this response. So I had created a Response class as shown below with getters and setters (have not included the getters and setters here for brevity):

JSON 的响应部分对于一系列响应类型是通用的。此 JSON 的报告部分仅适用于此响应。因此,我创建了一个带有 getter 和 setter 的响应类,如下所示(为简洁起见,此处未包括 getter 和 setter):

@JsonRootName(value = "response")
public class Response implements Serializable {

    private static final long serialVersionUID = -2597493920293381637L;

    @JsonProperty(value = "error")
    private String error;
    @JsonProperty(value = "error_code")
    private String errorCode;
    @JsonProperty(value = "error_id")
    private String errorId;
    @JsonProperty(value = "error_description")
    private String errorDescription;
    @JsonProperty(value = "method")
    private String method;
    @JsonProperty(value = "service")
    private String service;
    @JsonProperty(value = "status")
    private String status;
    @JsonProperty(value = "execution_status")
    private String executionStatus;
}

And then, I created a Report class with the fields in the report element as below. The ReportResponse class will extend from the Response class (again the getters and setters are not included for brevity):

然后,我使用报告元素中的字段创建了一个报告类,如下所示。ReportResponse 类将从 Response 类扩展(同样,为简洁起见,不包括 getter 和 setter):

public class ReportResponse extends Response {

    private static final long serialVersionUID = 4950819240030644407L;

    @JsonProperty(value = "cache_hit")
    private Boolean cacheHit;
    @JsonProperty(value = "created_on")
    private Timestamp createdOn;
    @JsonProperty(value = "fact_cache_error")
    private String factCacheError;
    @JsonProperty(value = "fact_cache_hit")
    private Boolean factCacheHit;
    @JsonProperty(value = "header_info")
    private String headerInfo;
    @JsonProperty(value = "json_request")
    private String jsonRequest;
    @JsonProperty(value = "name")
    private String name;
    @JsonProperty(value = "report_size")
    private Integer reportSize;
    @JsonProperty(value = "row_count")
    private Integer rowCount;
    @JsonProperty(value = "url")
    private String url;
}

Now when I use the ObjectMapper to map to the ReportResponse object, I get the following error:

现在,当我使用 ObjectMapper 映射到 ReportResponse 对象时,出现以下错误:

String jsonString = "{\"response\": {\"execution_status\": \"ready\", \"report\":   {\"cache_hit\": true, \"created_on\": \"2013-07-29 09:53:44\", \"fact_cache_error\": null, \"fact_cache_hit\": false, \"header_info\": null, \"name\": null, \"report_size\": \"5871\", \"row_count\": \"33\", \"url\": \"report-download?id=2ff62c07fc3653b68f2073e7c1aa0517\"}, \"status\": \"OK\"}}";
ObjectMapper mapper = new ObjectMapper();
ReportResponse reportResponse = mapper.readValue(jsonString, ReportResponse.class);

Caused by: com.fasterxml.Hymanson.databind.exc.UnrecognizedPropertyException: Unrecognized field "report"

I know that I can create a separate Report class and then embed it in the ReportResponse with the @JsonProperty anotation. Is there a way I can avoid that and mark the ReportResponse class with an annotation which would map it to the "report" element in the JSON?

我知道我可以创建一个单独的 Report 类,然后使用 @JsonProperty 注释将它嵌入到 ReportResponse 中。有没有办法可以避免这种情况并使用注释标记 ReportResponse 类,该注释会将其映射到 JSON 中的“report”元素?

回答by nutlike

There is no annotation which could handle this case yet. There is a ticket requesting this feature.

目前还没有可以处理这种情况的注释。有一张请求此功能的票。

Here is a brief statement from one of the owners regarding this topic.

以下是一位业主关于此主题的简短声明。

Quote from the mentioned statement:

引用上述声明:

Tatu Saloranta: "… @JsonProperty does not support transformations, since the data binding is based on incremental parsing and does not have access to full tree representation. Supporting @JsonUnwrapped was non-trivial, but doable; and thus converse ("@JsonWrapped") would be doable, theoretically speaking. Just plenty of work. …"

Tatu Saloranta:“……@JsonProperty 不支持转换,因为数据绑定基于增量解析并且无法访问完整的树表示。支持@JsonUnwrapped 是重要的,但可行;因此反过来(“@JsonWrapped” ) 从理论上讲是可行的。只是大量的工作。......”

回答by Juned Ahsan

I see couple of problems in your code. First thing is that you don't have reportattribute in your Response class, which is required as per the json structure you have shown. Secondly you need to provide the getters and setters in your bean classes as those will be used by the Hymanson for marhsalling and unmarshalling of json/object.

我在您的代码中看到了几个问题。首先report,您的 Response 类中没有属性,根据您显示的 json 结构,这是必需的。其次,您需要在 bean 类中提供 getter 和 setter,因为 Hymanson 将使用它们来对 json/object 进行编组和解组。