Десериализовать различное количество объектов в список в Java, используя Джексона - PullRequest
0 голосов
/ 26 ноября 2018

Приложение My Spring Boot вызывает API REST и получает JSON с различным числом объектов.Например,

{
  "content": {
    "guest_1": {
      "name": {
        "firstName": "a",
        "lastName": "b"
      },
      "vip": false
    },
    "guest_2": {
      "name": {
        "firstName": "c",
        "lastName": "d"
      },
      "vip": false
    },
    ...more guests omitted...
  }
}

Может быть от одного до многих гостей, и я не знаю их количество заранее.Как вы можете видеть, они не находятся в массиве, а являются объектами.

Я бы хотел избежать десериализации в класс, подобный

public class Content {

  @JsonProperty("guest_1")
  private Guest guest1;

  @JsonProperty("guest_2")
  private Guest guest2;

  // More Guests here each having their own field
}

Что бы я хотелиспользуется

public class Content {

  private List<Guest> guests;
}

Аннотация @JsonAnySetter, о которой я читал в https://www.baeldung.com/jackson-annotations, выглядит многообещающе, но я не могу заставить ее работать.

3.2.Преобразование в объект в https://www.baeldung.com/jackson-json-node-tree-model выглядит также хорошо, но это тоже не сработало.

Я не уверен, смогу ли я заставить Джексона сделать это декларативным способом или яследует написать кастом JsonDeserializer.Не могли бы вы помочь мне?

1 Ответ

0 голосов
/ 26 ноября 2018

@JsonAnySetter будет работать, так как позволяет указать тип POJO в качестве второго параметра.Вы можете воссоздать пример JSON как, опуская методы setXXX() и getXXX() в POJO для ясности:

private static class Content {
    private Guests content;
}

private static class Guests  {
    private List<Guest> guests = new ArrayList<>();

    @JsonAnySetter
    private void addGuest(String name, Guest value) {
        guests.add(value);
    }
}

private static class Guest {
    private Name name;
    private boolean vip;
}

private static class Name {
    private String firstName;
    private String lastName;
}

На вашем примере JSON будет получено:

Content root = new ObjectMapper().readValue(json, Content.class);
root.getContent().getGuests().stream()
        .map(Guest::getName)
        .map(Name::getFirstName)
        .forEach(System.out::println); // a, c
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...