我是java和objectMapper的新手。我正在尝试解析json字段,该字段可能是键具有两种类型,它可以是字符串或数组。
示例:
{
"addresses": [],
"full_name": [
"test name_1",
"test name_2"
],
}
或
{
{
"addresses": [],
"full_name": "test name_3",
}
}
类示例:
@JsonIgnoreProperties(ignoreUnknown = true)
@Data -> lombok.Data
public class Document {
private List<String> addresses;
@JsonProperty("full_name")
private String fullName;
}
我使用objectMapper反序列化json,当'full_name'字段包含字符串但到达数组时,反序列化失败。
这个想法是,当到达属性中的字符串放置值但到达数组时,将de数组元素串联为字符串(String.join(“,”,value))
可以在类方法中应用自定义反序列化吗?例如setFullName()(使用lombok.Data)
我在该网站上看到了其他示例,但没有用。
谢谢大家
答案 0 :(得分:5)
从杰克逊2.6开始,您可以使用JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY
@JsonProperty("full_name")
@JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY)
private String[] fullName;
答案 1 :(得分:2)
详细说明@Deadpool答案,您可以使用setter接受数组,然后将其连接到字符串:
@JsonProperty("full_name")
@JsonFormat(with = JsonFormat.Feature.ACCEPT_SINGLE_VALUE_AS_ARRAY)
void setFullName(String[] name)
{
this.fullName = String.join(",", name);
}
答案 2 :(得分:0)
两个答案都很好。我只想提及自定义反序列化器。
您可以轻松地从StdDeserializer<Document>
扩展并覆盖deserialize
方法:
public class BaseModelDeserializer extends StdDeserializer<Document> {
@Override
public Document deserialize(JsonParser p, DeserializationContext ctxt, Document value) throws IOException {
JsonNode root = p.getCodec().readTree(p);
JsonNode node = root.get("full_name");
if(node.isArray()) {
//get array data from node iterator then join as String and
//call setFirstName
}
return value;
}
}
那就别忘了调用registerModule
中的ObjectMapper
来注册您的deserializer