本文介绍了第一次序列化后配置ObjecMapper空序列化无效的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

使用ObjectMapper进行一些实验时,偶然发现了此行为.请参阅下面的Junit5测试用例,并在注释中为我打印出什么内容.

Stumbled on this behavior when making some experiments with ObjectMapper. See Junit5 test cases below and what those print for me in comments.

class TestIt {

    private ObjectMapper om = new ObjectMapper();
    private TestClass testClass = new TestClass();

    @Getter @Setter
    public class TestClass {
        private final String value = LocalDate.now().toString();
        private String valueLeftNull;
    }
    
    @Test
    void defaultMapping() throws JsonProcessingException {
        System.out.println(om.writeValueAsString(testClass));
        // {"value":"2020-11-02","valueLeftNull":null}
    }

    @Test
    void nonNull() throws JsonProcessingException {
        om.setSerializationInclusion(Include.NON_NULL);
        System.out.println(om.writeValueAsString(testClass));
        // {"value":"2020-11-02"}
    }

    @Test
    void both() throws JsonProcessingException {
        System.out.println(om.writeValueAsString(testClass));
        om.setSerializationInclusion(Include.NON_NULL);
        System.out.println(om.writeValueAsString(testClass));
        System.out.println(om.writeValueAsString(new TestClass()));
        // {"value":"2020-11-02","valueLeftNull":null}
        // {"value":"2020-11-02","valueLeftNull":null}
        // {"value":"2020-11-02","valueLeftNull":null}

    }

}

最后一个both()是我想知道的. ObjectMapper在第一次序列化后忽略包含指令是正常功能吗?

The last one both() is what I am wondering. Is it normal functionality that ObjectMapper ignores the inclusion instruction after the first serialization?

推荐答案

默认情况下Jackson创建实例.它是在需要时按需创建的,并缓存.因此,它的配置取决于ObjectMapper的当前状态,如果更改ObjectMapper,则需要清除缓存:

By default Jackson creates BeanSerializer instance for each POJO class. It is created on demand when is needed and cached. So it's configuration depends from current state of ObjectMapper and if you change ObjectMapper you need to clear cache:

((DefaultSerializerProvider) om.getSerializerProvider()).flushCachedSerializers();

强制ObjectMapper创建BeanSerializer的新实例.

看看 BeanSerializerFactory :

cachedSerializersCount 方法:

最好的解决方案可能是创建两个ObjectMapper实例:

Probably the best solution would be to create two instances of ObjectMapper:

class TestIt {

    private JsonMapper nonNullMapper = JsonMapper.builder()
                .serializationInclusion(JsonInclude.Include.NON_NULL)
                .build();
    private JsonMapper defaultMapper = JsonMapper.builder().build();
    private TestClass testClass = new TestClass();

    @Getter
    @Setter
    public static class TestClass {
        private final String value = LocalDate.now().toString();
        private String valueLeftNull;
    }

    void defaultMapping() throws JsonProcessingException {
        System.out.println(defaultMapper.writeValueAsString(testClass));
    }

    void nonNull() throws JsonProcessingException {
        System.out.println(nonNullMapper.writeValueAsString(testClass));
    }

    void both() throws JsonProcessingException {
        System.out.println(defaultMapper.writeValueAsString(testClass));
        System.out.println(nonNullMapper.writeValueAsString(testClass));
        System.out.println(nonNullMapper.writeValueAsString(new TestClass()));
    }
}

这篇关于第一次序列化后配置ObjecMapper空序列化无效的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持!

09-25 18:28