A Jackson Filter matching the path of the current value to serialize against the AntPathMatcher. The inclusion / exclusion works similar to the ant file include / exclude functionality. Ant / Maven users should mostly be aware of how this works.
- Java 5
- Jackson 2.5.0+ (2.5.0.RELEASE and its dependencies included)
Add a dependency to your project with the following co-ordinates:
- GroupId:
ch.mfrey.jackson - ArtifactId:
jackson-antpathfilter - Version:
${jackson-antpathfilter.version}
<dependency> <groupId>ch.mfrey.jackson</groupId> <artifactId>jackson-antpathfilter</artifactId> <version>${jackson-antpathfilter.version}</version> </dependency>String[] filter = new String[] {"*", "*.*", "!not.that.path"}; ObjectMapper objectMapper = new ObjectMapper(); objectMapper.addMixIn(Object.class, AntPathFilterMixin.class); FilterProvider filterProvider = new SimpleFilterProvider().addFilter("antPathFilter", new AntPathPropertyFilter(filter)); objectMapper.setFilters(filterProvider); objectMapper.writeValueAsString(someObject);= Inclusion:
"*", "**", "*.*", "someproperty.someNesterProperty.*", = Exclusion:
"!property", "!**.someExpensiveMethod"; = With Spring 4.2.2+
public class AntPathMappingJackson2HttpMessageConverter extends MappingJackson2HttpMessageConverter { public AntPathMappingJackson2HttpMessageConverter(ObjectMapper originalObjectMapper) { super(originalObjectMapper.copy().addMixIn(Object.class, HibernateAwareAntPathFilterMixin.class)); } @Override public boolean canWrite(Class<?> clazz, MediaType mediaType) { return AntPathFilterMappingJacksonValue.class.isAssignableFrom(clazz); } @JsonFilter("antPathFilter") @JsonIgnoreProperties({"hibernateLazyInitializer", "handler"}) public static class HibernateAwareAntPathFilterMixin { } } public class AntPathFilterMappingJacksonValue<T> extends MappingJacksonValue { public AntPathFilterMappingJacksonValue(final T value, final String... filters) { super(value); setFilters(new SimpleFilterProvider().addFilter("antPathFilter", new AntPathPropertyFilter(filters))); } }@Configuration @EnableWebMvc public class DispatcherConfiguration extends WebMvcConfigurerAdapter { @Bean public FactoryBean<ObjectMapper> jacksonObjectMapperFactory() { // Normal Jackson configuration } @Bean public HttpMessageConverter antpathJacksonConverter() { return new AntPathMappingJackson2HttpMessageConverter(jacksonObjectMapperFactory().getObject()); } @Override public void extendMessageConverters(List<HttpMessageConverter<?>> converters) { converters.add(0, antpathJacksonConverter()); } }@Controller @RequestMapping(value = "/someObject") public class SomeController { @RequestMapping @ResponseBody public AntPathFilterMappingJacksonValue<SomeClass> getSomeObject() { return new AntPathFilterMappingJacksonValue<>(someObject, "*", "*.*", "!not.that.path"); } }Data
{ "address": { "streetName":"At my place", "streetNumber":"1" }, "email":"somewhere@no.where", "firstName":"Martin", "lastName":"Frey", "manager":{ "address":null, "email":"john.doe@no.where", "firstName":"John", "lastName":"Doe", "manager":null } } Filter: **, Result: {"address":{"streetName":"At my place","streetNumber":"1"},"email":"somewhere@no.where","firstName":"Martin","lastName":"Frey","manager":{"address":null,"email":"john.doe@no.where","firstName":"John","lastName":"Doe","manager":null}} Filter: firstName, Result: {"firstName":"Martin"} Filter: **,!manager, Result: {"address":{"streetName":"At my place","streetNumber":"1"},"email":"somewhere@no.where","firstName":"Martin","lastName":"Frey"} Filter: manager,manager.firstName,manager.lastName, Result: {"manager":{"firstName":"John","lastName":"Doe"}} Filter: *,address.*,manager.firstName, Result: {"address":{"streetName":"At my place","streetNumber":"1"},"email":"somewhere@no.where","firstName":"Martin","lastName":"Frey","manager":{"firstName":"John"}} Filter: **,-manager,!**.streetNumber, Result: {"address":{"streetName":"At my place"},"email":"somewhere@no.where","firstName":"Martin","lastName":"Frey"} Filter: "reports", "reports.firstName" Result: {"reports":[{"firstName":"First 0"},{"firstName":"First 1"},{"firstName":"First 2"},{"firstName":"First 3"},{"firstName":"First 4"},{"firstName":"First 5"},{"firstName":"First 6"},{"firstName":"First 7"},{"firstName":"First 8"},{"firstName":"First 9"}]} 