Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Dynamically enable/disable he UNWRAP_ROOT_VALUE and WRAP_ROOT_VALUE in Jackson's ObjectMapper?

Is there a way to enable/disable the UNWRAP_ROOT_VALUE and WRAP_ROOT_VALUE in Jackson's ObjectMapper dynamically.
I have to enable/disable these properties depending on what service is called, some requests require a JsonRootName and some do not.

I have the @JsonRootName annotation in the classes that do require it.
I have a custom ObjectMapper class that extends the Jackson Object mapper.
I am calling a method to enable/disable the properties depending on what service is called but is it doesn't seem to be working.

public void setWrapValue(boolean wrap) {

    final AnnotationIntrospector introspector = new JacksonAnnotationIntrospector();     

    this.configure(org.codehaus.jackson.map.DeserializationConfig.Feature.UNWRAP_ROOT_VALUE, wrap);

    this.configure(org.codehaus.jackson.map.SerializationConfig.Feature.WRAP_ROOT_VALUE, wrap);
    this.setDeserializationConfig(this.getDeserializationConfig().withAnnotationIntrospector(introspector));

    this.setSerializationConfig(this.getSerializationConfig().withAnnotationIntrospector(introspector));
 }
like image 681
user86834 Avatar asked Jun 19 '13 09:06

user86834


People also ask

What is SerializationFeature Wrap_root_value?

We can use the "WRAP_ROOT_VALUE" feature of SerializationFeature enum that can be enabled to make root value wrapped within a single property JSON object where the key is a root name.

Is ObjectMapper thread safe Jackson?

Jackson's ObjectMapper is completely thread safe and should not be re-instantiated every time #2170.

Should I reuse ObjectMapper?

Note that copy() operation is as expensive as constructing a new ObjectMapper instance: if possible, you should still pool and reuse mappers if you intend to use them for multiple operations.

What does ObjectMapper class do?

Class ObjectMapper. ObjectMapper provides functionality for reading and writing JSON, either to and from basic POJOs (Plain Old Java Objects), or to and from a general-purpose JSON Tree Model ( JsonNode ), as well as related functionality for performing conversions.


1 Answers

1) Per-class root wrapping

There are two issues on jackson-databind,

  • https://github.com/FasterXML/jackson-annotations/issues/33 which is open but inactive;
  • https://github.com/FasterXML/jackson-databind/issues/1022 which marked for Jackson 3.x.

Without support from Jackson, I see no way to do this without writing more code than manually wrapping each class into a property.

One way could be leveraging JAXB's feature to de/serialize properties as per XPath-like expression (i.e. foo/bar would wrap a property under foo), but that is not supported by Jackson.

Edit:

I looked at the code, DefaultSerializerProvider and around. Jackson 2.9.9. Jackson currently does not distinguish "no property name" and "default property name". So, AFAICT, DefaultSerializerProvider doesn't know whether @JsonRootName is there or is empty.

If this disctinction was propagated, this could start working. I'm waiting for the maintainer to judge. However, without changes in Jackson itself, doing this from the outside would be a bit impractical.

2) Toggling root wrapping dynamically

Maybe you could have 2 ObjectMappers, one with and one without WRAP_ROOT_NAME, and use the right one.

However, if "some requests need it and some not" (assuming for the same endpoint), that's a bit weird. Or did you mean that for some endpoints you need to wrap types that you use as-s for other endpoints? Then maybe simple composition can be used. Hard to tell, please add some JSON examples and your model classes.

like image 92
Ondra Žižka Avatar answered Nov 05 '22 09:11

Ondra Žižka