javamongodbspring-bootspring-dataspring-data-mongodb

How to store a Map of Maps of Lists from a JSON file with Spring Data MongoDB?


I am using Spring Data and MongoDB for the first time. I have a JSON document similar to this:

key: "key",
attributes: [
    {
        type1: [
            {
                class1: "class1",
                genres : [
                    "genre1",
                    "genre2"
                ]
            },
            {
                class2: "class2",
                genres : [
                    "genre2",
                    "genre3"
                ]
            }
        ]
    }
]

Types and classes are dynamic ideally. There are a lot of types and classes it could be and only as a very last resort would I want to make variables for them.

I know I am able to get the "key" field in my entity class, with simply creating a variable String key; and a method String getKey() and using @Field("key") (optionally).

But how would I be able to get the entire "attributes" array in the my desired format: Map\<types, Map<classes, List<genres>>>

Currently I have something like this:

    @Document("Test")
    public class Test {
        String key;
        Map<String, Map<String, List<String>>> attributes;
    
        @Field("key")
        public String getKey() { return key; }
    
        @Field("attributes")
        public Map<String, Map<String, List<String>>> getAttributes() { return attributes; }
    }

Would I be able to grab the attributes map of maps in this manner? Or is that wishful thinking and I'd actually have to grab each list or map separately and how to do that?

I'm able to alter my JSON structure if that would fit the map of maps of lists object better as well.


Solution

  • Figured it out. Maps can be defined only by the curly braces and not the square brackets.

    So my attributes.json file looks like this:

    "key": "key",
    "attributes": {
        "type1": {
                "class1": {
                    "classValue": "example value",
                    "genres":[ "genre1", "genre2" ]
                },
                "class2": {
                    "classValue": "other value",
                    "genres":[ "genre2", "genre3" ]
                }
        },
        "type2": {
                "class3": {
                    "classValue": "another value",
                    "genres":[ "genre1", "genre2" ]
                }
        }
    }
    

    In my Attribute class it becomes:

    public class Attribute {
        String key;
        Map<String, Map<String, ClassDetails> attributes;
        //constructor, getters, and setters
    }
    

    The first two map keys are able to be saved as any String, meaning I preserve the different types and classes.

    In order to preserve the class value and genres, I created a POJO called ClassDetails:

    public class ClassDetails{
        String classValue;
        List<String> genres;
        //constructors, getters, and setters
    }
    

    Ex: Below would return the string "other value"

    Attribute attr = mongoTemplate.findOne(query, Attribute.class);
    return attr.getAttributes().get("type1").get("class2").getClassValue()