gpt4 book ai didi

java - 使用 Jackson 根据条件注入(inject) json 属性

转载 作者:行者123 更新时间:2023-11-30 07:14:27 24 4
gpt4 key购买 nike

我有一个 json 格式,我正在使用 Jackson API 将其转换为 Java 对象模型。我正在使用Jaxsonxml 2.1.5 解析器。 json响应如下所示。

 {
"response": {
"name": "states",
"total-records": "1",
"content": {
"data": {
"name": "OK",
"details": {
"id": "1234",
"name": "Oklahoma"
}
}
}
}
}

现在 json 响应格式已更改。如果total-records1 details将是一个带有 id 的对象和name属性。但如果total-records大于1然后details将是一个如下所示的对象数组:

    {
"response": {
"name": "states",
"total-records": "4",
"content": {
"data": {
"name": "OK",
"details": [
{
"id": "1234",
"name": "Oklahoma"
},
{
"id": "1235",
"name": "Utah"
},
{
"id": "1236",
"name": "Texas"
},
{
"id": "1237",
"name": "Arizona"
}
]
}
}
}
}

我的 Java Mapper 类与之前的 json 类似,如下所示回应。

    @JsonIgnoreProperties(ignoreUnknown = true)
public class MapModelResponseList {

@JsonProperty("name")
private String name;

@JsonProperty("total-records")
private String records;

@JsonProperty(content")
private Model model;

public Model getModelResponse() {
return model;
}

public void setModel(Model model) {
this.model = model;
}
}

客户端代码

    package com.test.deserializer;

import com.fasterxml.jackson.databind.DeserializationFeature;
import com.fasterxml.jackson.databind.ObjectMapper;
import com..schema.model.Person;

public class TestClient {

public static void main(String[] args) {
String response1="{\"id\":1234,\"name\":\"Pradeep\"}";
TestClient client = new TestClient();
try {
Person response = client.readJSONResponse(response1, Person.class);
} catch (Exception e) {
e.printStackTrace();
}
}

public <T extends Object> T readJSONResponse(String response, Class<T> type) {
ObjectMapper mapper = new ObjectMapper();
mapper.enable(DeserializationFeature.ACCEPT_EMPTY_STRING_AS_NULL_OBJECT);
T result = null;
try {
result = mapper.readValue(response, type);
} catch (Exception e) {
e.printStackTrace();
}
return (T) result;
}

}

现在基于 total-records如何处理映射到 ModelModel 的列表目的。请告诉我。

最佳答案

您需要一个自定义解串器。这个想法是将对象处理与树处理混合和匹配。尽可能解析对象,但使用树 ( JSONNode ) 进行自定义处理。

关于MapModelResponseList ,删除 records属性并添加 List<Data>数组其中 Data只是 id/name 对的持有者类。您可以通过返回此列表的大小来获取总记录。

在解串器中,执行以下操作:

public final class MapModelDeserializer extends BeanDeserializer {
public MapModelDeserializer(BeanDeserializerBase src) {
super(src);
}

protected void handleUnknownProperty(JsonParser jp, DeserializationContext ctxt, Object beanOrClass, String propName) throws IOException, JsonProcessingException {
if ("content".equals(propName)) {
MapModelResponseList response = (MapModelResponseList) beanOrClass;

// this probably needs null checks!
JsonNode details = (JsonNode) jp.getCodec().readTree(jp).get("data").get("details");

// read as array and create a Data object for each element
if (details.isArray()) {
List<Data> data = new java.util.ArrayList<Data>(details.size());

for (int i = 0; i < details.size(); i++) {
Data d = jp.getCodec().treeToValue(details.get(i), Data.class);
data.add(d);
}

response.setData(data);
}
// read a single object
else {
Data d = jp.getCodec().treeToValue(details, Data.class);
response.setData(java.util.Collections.singletonList(d));
}

super.handleUnknownProperty(jp, ctxt, beanOrClass, propName);
}

请注意,您没有实现 deserialize() - 默认实现用于创建MapModelResponseList像平常一样。 handleUknownProperty()用于处理content元素。由于@JsonIgnoreProperties(ignoreUnknown = true),您不关心的其他数据将被忽略在 super 调用中。

关于java - 使用 Jackson 根据条件注入(inject) json 属性,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/38684201/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com