Частичная сериализация JSON во время выполнения (для запросов RESTful)

Я пытаюсь преобразовать объект Java в JSON в Tomcat (в настоящее время используется Джексон). Основываясь на полях в запросе RESTful, я хочу сериализовать только те поля. Я хочу поддерживать запросы для любого подмножества полей, поэтому я бы хотел сделать это во время выполнения (динамически).

Например, предположим, что я хочу поддерживать частичную сериализацию для объектов User:

class User {
    private final String id;
    private final String firstName;
    private final String lastName;

    public User(String id, String firstName, String lastName) {
        this.id = id;
        this.firstName = firstName;
        this.lastName = lastName;
    }

    public String getId() { return id; }
    public String getFirstName() { return firstName; }
    public String getLastName() { return lastName; }
}

Если я сделаю запрос для:

GET /users/{id}/?fields=firstName,lastName

Я хочу получить что-то вроде {"firstName":"Jack","lastName":"Johnson"}.

Если я сделаю запрос для:

GET /users/{id}/?fields=firstName

Я хочу получить что-то вроде {"firstName":"Jack"}.

Jackson JSON View дает возможность определять подмножества логических свойств (объекты, доступные через геттеры или поля) для сериализации. Однако они определяются статически (используя аннотации) и выбираются только динамически (для сериализации). На практике я хочу поддержать запрос любого подмножества полей объекта, поэтому я могу потенциально иметь тысячи JSON Views (10 полей подразумевают 1023 подмножества!).

Что библиотека JSON поддерживает частичную сериализацию во время выполнения?

Ответы

Ответ 1

Мы используем Google GSON для конвертирования между объектом Java и JSON. Я не уверен, есть ли у него функциональность, которую вы ищете, но она очень проста в использовании и документы тоже хороши.

Если вы не можете найти библиотеку, которая делает то, что вам нужно, я предлагаю использовать более свободные структурированные классы (например, HashMap) или пользовательские классы представления для связи между вашим кодом и JSON. Это добавит еще один слой или два, но уменьшит сложность. Удачи.

Ответ 2

Я думаю, что json-lib и flex-json поддерживают более динамичную/гибкую фильтрацию.

С Джексоном, что некоторые пользователи делают, это использовать HashMaps или JsonNodes как более свободные структуры и отфильтровывать оттуда.

Кроме того, хотя это не поможет вам в краткосрочной перспективе, у Jackson 1.6 есть улучшения как для JsonNode (keepAll (String... names), remove (String... names) и, возможно, ObjectMapper, так как это известно для улучшения.

Ответ 3

Так как Spring 4.2.0.Release, у вас есть полный контроль над возвращаемыми полями или вы можете сделать это с помощью JsonFilters, как описано в следующих ссылках:  1. https://jira.spring.io/browse/SPR-12586  2. http://wiki.fasterxml.com/JacksonFeatureJsonFilter

@RequestMapping(method = RequestMethod.POST, value = "/springjsonfilter")
    public @ResponseBody MappingJacksonValue byJsonFilter(...) {
        MappingJacksonValue jacksonValue = new MappingJacksonValue(responseObj);    
        jacksonValue.setFilters(customFilterObj);
        return jacksonValue;
    }