FasterXML / jackson-databind

General data-binding package for Jackson (2.x): works on streaming API (core) implementation(s)
Apache License 2.0
3.53k stars 1.39k forks source link

@JsonAnyGetter does not handle null Map Values Properly #1929

Open bthelen opened 6 years ago

bthelen commented 6 years ago

When using @JsonAnyGetter annotation, the settings objectMapper.configure(SerializationFeature.WRITE_NULL_MAP_VALUES, false); and objectMapper.setPropertyInclusion(JsonInclude.Value.construct(JsonInclude.Include.NON_NULL, JsonInclude.Include.NON_NULL)); do not appear to be respected.

When serializing a map that is not annotated with @JsonAnyGetter null values are handled as expected (i.e. they do not appear in the JSON).

We have tested this against 2.8.10 and 2.9.4 with the same results.

See https://github.com/bthelen/json-any-getter-test for example.

cowtowncoder commented 6 years ago

Thank you for reporting this. It is possible handling of inclusion via @JsonAnyGetter is not handled as they should and/or expected from user perspective.

But come to think of that, it is not necessarily clear what is expected handling: is it considered serialization of Map (similar to serializing a Map, except "unwrapping" entries). Or should these be considered as virtual properties of enclosing POJO? Handling follows (and needs to follow) different rules (for Map its "content" inclusion, for properties simple "value" inclusion).

It seems to me that inclusion should be considered as properties, since use of Map is sort of implementation detail; and serialization should be handled as if all entries were regular properties. Then again, it is not -- for example -- possible to do much for "NON_DEFAULT" case, as these properties do not really have "default" value (unless one considered null to be default?).

Above is just thinking out aloud: I think your case is simpler, and one where distinction does not make a difference (null exclusion is simple enough).

spifd commented 5 years ago

Is there any workaround to avoid serializing the parent object containing a field annotated with @JsonAnyGetter on a null or empty map? Custom serializer on the parent object?

cowtowncoder commented 5 years ago

@spifd not 100% I understand that question: but for purposes of serialization exclusion, parent object is just a POJO and can only be excluded if it's null or "default" (in which case you want to implement equals() so that default instance can be compared against). There is no definition of "empty" for POJOs currently, except via custom JsonSerializer.