Определить Map-Key с джексоном - PullRequest
0 голосов
/ 13 июля 2020

Как я могу определить ключ карты, который я хочу использовать для десериализации объекта JSON с помощью Джексона?

Моя структура выглядит так:

Class01:

public class Class01{
    private String id;
    private Map<String, Class02> entries;
}

Class02:

public class Class02{
    private String name;
    private String otherStuff;
}

Я хочу, чтобы Джексон использовал строку имени в качестве ключа для объекта карты.

JSON выглядит так:

{
    "id": "1",
    "entries": [
      {
        "name": "1",
        "otherStuff": "asdf"
      },
      {
        "name": "2",
        "otherStuff": "ghkj"
      },
      {
        "name": "3",
        "otherStuff": "klyx"
      }]
}

Я использую этот код для чтения из файла json:

List<Class01> classes01 = objectMapper.readValue(jsonText, new TypeReference<List<Class01>>(){});

Я уже пробовал добавить @JsonDeserialize(using = HashMapValueDeserializer.class) на карту

Мой метод десериализации выглядит так:

@Override
public Map<String, Class02> deserialize(JsonParser parser, DeserializationContext ctxt) throws IOException {
    Map<String, Class02> ret = new HashMap<>();

    ObjectCodec codec = parser.getCodec();
    TreeNode classes02 = codec.readTree(parser);

    String name, otherStuff;

    if (classes02.isArray()) {
        for (JsonNode class02: (ArrayNode) classes02) {

            name = class02.get("name").asText();
            if(class02.get("otherStuff")!=null) otherStuff = platformModule.get("otherStuff").asText();
            else otherStuff = null;

            ret.put(name, new Class02(name, otherStuff));
        }
    }
    return ret;
}

Ответы [ 3 ]

0 голосов
/ 13 июля 2020

использовать строку имени в качестве ключа для объекта карты.

Это невозможно при использовании синтаксического анализатора Джексона по умолчанию. entries - ваш ключ. И это List<Class02>, а не карта

В качестве альтернативы вы можете иметь List<Map<String, String>> entries, если хотите карту, но ключ списка по-прежнему определяется для самого внешнего объекта

0 голосов
/ 13 июля 2020

Поскольку ваша структура JSON не совпадает с Map, вы можете выполнить эту операцию в установщике. В Class01 вы можете использовать entries сеттер, как это

void setEntries(List<Class02> list){
   this.entries = list.stream().collect(
          Collectors.toMap(Class02::getName(), Function.identity()));
}
0 голосов
/ 13 июля 2020

Измените поле записей в Class01 на List:

private List<Class02> entries;

Или для карты используйте это json:

String json = "{\"id\":\"1\",\"entries\":{\"entryOne\":{\"name\":\"1\",\"otherStuff\":\"2\"},\"entryTwo\":{\"name\":\"3\",\"otherStuff\":\"4\"}}}";

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...