Deserialisieren verschachtelten Array als ArrayList mit Jackson
Habe ich ein Stück von JSON sieht wie folgt aus:
{
"authors": {
"author": [
{
"given-name": "Adrienne H.",
"surname": "Kovacs"
},
{
"given-name": "Philip",
"surname": "Moons"
}
]
}
}
Habe ich eine Klasse zum speichern von Informationen zum Autor:
public class Author {
@JsonProperty("given-name")
public String givenName;
public String surname;
}
Und zwei wrapper-Klassen:
public class Authors {
public List<Author> author;
}
public class Response {
public Authors authors;
}
Diese arbeitet, aber mit zwei wrapper-Klassen zu sein scheint, unnötig. Ich möchte einen Weg finden, zu entfernen Authors
Klasse und haben eine Liste als Eigenschaft der Einstiegsklasse. Ist sowas möglich ist mit Jackson?
Update
Gelöst, dass mit benutzerdefinierten deserializer:
public class AuthorArrayDeserializer extends JsonDeserializer<List<Author>> {
private static final String AUTHOR = "author";
private static final ObjectMapper mapper = new ObjectMapper();
private static final CollectionType collectionType =
TypeFactory
.defaultInstance()
.constructCollectionType(List.class, Author.class);
@Override
public List<Author> deserialize(JsonParser jsonParser, DeserializationContext deserializationContext)
throws IOException, JsonProcessingException {
ObjectNode objectNode = mapper.readTree(jsonParser);
JsonNode nodeAuthors = objectNode.get(AUTHOR);
if (null == nodeAuthors //if no author node could be found
|| !nodeAuthors.isArray() //or author node is not an array
|| !nodeAuthors.elements().hasNext()) //or author node doesn't contain any authors
return null;
return mapper.reader(collectionType).readValue(nodeAuthors);
}
}
Und verwenden Sie es wie folgt:
@JsonDeserialize(using = AuthorArrayDeserializer.class)
public void setAuthors(List<Author> authors) {
this.authors = authors;
}
Dank @wassgren für die Idee.
InformationsquelleAutor der Frage Dmitry | 2015-01-12
Du musst angemeldet sein, um einen Kommentar abzugeben.
Sehe ich mindestens zwei Wege, um dies zu tun, wenn Sie wollen, um loszuwerden, wrapper-Klassen. Die erste ist die Verwendung der Jackson-Baum-Modell (
JsonNode
) und die zweite ist die Verwendung einer Deserialisierung feature namensUNWRAP_ROOT_VALUE
.Alternative 1: Verwendung
JsonNode
Beim Deserialisieren von JSON mit Jackson gibt es mehrere Möglichkeiten, um zu Steuern, welche Art von Objekte, die erstellt werden sollen. Die
ObjectMapper
Deserialisieren können die JSON-z.B.Map
JsonNode
(über diereadTree
-Methode) oder ein POJO.Wenn Sie kombinieren die
readTree
-Methode mit derPOJO
Umwandlung der Wrapper kann komplett entfernt werden. Beispiel:Die Deserialisierung kann dann wie folgt Aussehen:
Wenn Sie das Baum-Modell-Ansatz der wrapper-Klassen kann vollständig entfernt werden.
Alternative 2: entfernen Sie eine der Wrapper und packen Sie das root-Wert
Der zweite Ansatz ist das entfernen nur einer der Wrapper. Angenommen, Sie entfernen die
Authors
Klasse, aber halten dieResponse
-wrapper. Wenn Sie fügen Sie eine@JsonRootName
-annotation können Sie später Auspacken der top-level-Namen.Dann, für die mapper verwenden Sie einfach:
Dem zweiten Ansatz nur entfernt einer der wrapper-Klassen, sondern die parsing-Funktion ist Recht hübsch.
InformationsquelleAutor der Antwort wassgren