Home > other >  How to deserialize a JSON Map<Int, Map<String, String>> using gson?
How to deserialize a JSON Map<Int, Map<String, String>> using gson?

Time:11-29

guys!

How can I deserialize a JSON Map<Int, Map<String, String>> using gson or any other library?

I want to convert this string:

{
    "123": {
        "KEY_ONE": "blablabla",
        "KEY_TWO": "blablabla",
    },
    "456": {
        "KEY_ONE": "blablabla"
        "KEY_TWO": "blablabla"
    }
}

Into this: Map<Int, Map<String, String>>

I tried these two options:

`

var gson = Gson()

// Try 1:
var mapper = gson.fromJson(payload, Map::class.java)

// Try 2:
val mapper = object: TypeToken<Map<Int, Map<String, String>>>(){}.getType()
var xmlBase64 = gson.fromJson(payload, type::class.java) //Map<Int, Map<String, String>>

`

On both attempts, I get the following error: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was STRING at line 1 column 1 path $

CodePudding user response:

"Try 2" using TypeToken is the correct approach but you are using it incorrectly: When calling Gson.fromJson just pass type directly as argument (without ::class.java):

val type = object: TypeToken<Map<Int, Map<String, String>>>(){}.type
val xmlBase64: Map<Int, Map<String, String>> = gson.fromJson(payload, type)

"Try 1" using a raw Map might also work because Gson uses default types based on the JSON value types (e.g. JSON object as Map, JSON string as String), but it is not type safe and you will encounter ClassCastExceptions when you try to use the deserialized data but the JSON data had a different format or when your code assumes the wrong types.

When using Gson 2.10 or newer, prefer the fromJson overloads with TypeToken parameter (that is, omit the .type call on the TypeToken) because they are type-safe:

val typeToken = object: TypeToken<Map<Int, Map<String, String>>>(){}
val xmlBase64 = gson.fromJson(payload, typeToken)

However, the IllegalStateException you are experiencing also indicates that your JSON data is in an incorrect format. Possibly it is wrapped inside extra double quotes (e.g. "{...}" instead of {...})? Try to log the JSON data (or set a breakpoint) and verify that is has the expected format. Besides that the sample JSON data you provided has some incorrect commas; use a tool such as https://jsonlint.com/ to verify that it is valid JSON.

  • Related