skip to Main Content

I interact with a set of APIs that all return a similar response:

{
    "common1": ...,
    "common2": ...,
    "common3": ...,
    "someList": [
        //polymorph objects here
    ]
}

Currently, I have a separate POJO for each of these responses. However I would like to factorize this in a common object since I always perform the same actions with such object and that makes a lot of code duplication.

Initially, I had thought to create a similar Jackson class:

public class CommonClass<T> {
    @JsonProperty("common1")
    private final CommonType1 common1;
    @JsonProperty("common2")
    private final CommonType2 common2;
    @JsonProperty("common3")
    private final CommonType3 common3;
    @JsonProperty("someList")
    private final List<T> someList;

    //constructor and getters here
}

This would work fine, except for an issue: the Json name of someList changes as well. Sometimes it’s someListA, sometimes it’s someListB… basically it changes depending on the type it contains.

That makes it impossible to follow this approach (at least I think) since I can’t dynamically change the value of the JsonProperty() annotations in my POJO.

I know that I could create a base class and then multiple extensions of such class, each one with a different list (differently named), but that wouldn’t be my ideal solution because I wouldn’t be able to have a common getter to process the elements without downcasting to the concrete type of POJO that I’m handling.

Do you have any idea/suggestion/approach for such problem?

2

Answers


  1. The simplest way is to deserialize it as a Map<String, Object> and than treat your map the same way except when retrieving someList* property instead of looking for a particular key such as someListA or SomeListB just search for the key that starts with "someList" prefix

    Login or Signup to reply.
  2. If the list of options for the name is not too long, you can use JsonAlias.

    Annotation that can be used to define one or more alternative names for a property, accepted during deserialization as alternative to the official name. Alias information is also exposed during POJO introspection, but has no effect during serialization where primary name is always used.

    Example:

    public class CommonClass<T> {
        @JsonProperty("common1")
        private final CommonType1 common1;
        @JsonProperty("common2")
        private final CommonType2 common2;
        @JsonProperty("common3")
        private final CommonType3 common3;
        @JsonProperty("someList")//official name, used during serialization
        @JsonAlias({"someListA", "someListB"})//aliases used during deserialization, if the official name was not found
        private final List<T> someList;
    }
    
    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search