get key names from JSON object using Gson

25,679

Instead of meandering through the Gson (JSON) API with loops and conditionals, I'd prefer to use Gson for what I think it does best: provide for very simple (de)serialization processing with just a few lines of code. I'd decouple any data manipulation/querying/presentation concerns from the (de)serialization concern. In other words, as much as reasonable, manipulate the data as necessary, before serializing it, and similarly, manipulate the data as necessary, after deserializing it.

So, if for some reason I wanted all of the keys from a JSON structure, and I wanted to use Gson, I'd likely approach it as follows. (Of course, I cannot currently think of any reason why such a thing could be useful.)

import java.io.FileReader;
import java.util.ArrayList;
import java.util.Collection;
import java.util.List;
import java.util.Map;

import com.google.gson.Gson;

public class App
{
  public static void main(String[] args) throws Exception
  {
    List keys1 = getKeysFromJson("input_without_lists.json");
    System.out.println(keys1.size());
    System.out.println(keys1);

    List keys2 = getKeysFromJson("input_with_lists.json");
    System.out.println(keys2.size());
    System.out.println(keys2);
  }

  static List getKeysFromJson(String fileName) throws Exception
  {
    Object things = new Gson().fromJson(new FileReader(fileName), Object.class);
    List keys = new ArrayList();
    collectAllTheKeys(keys, things);
    return keys;
  }

  static void collectAllTheKeys(List keys, Object o)
  {
    Collection values = null;
    if (o instanceof Map)
    {
      Map map = (Map) o;
      keys.addAll(map.keySet()); // collect keys at current level in hierarchy
      values = map.values();
    }
    else if (o instanceof Collection)
      values = (Collection) o;
    else // nothing further to collect keys from
      return;

    for (Object value : values)
      collectAllTheKeys(keys, value);
  }
}

input_without_lists.json

{
    "widget": {
        "debug": "on",
        "window": {
            "title": "Sample Konfabulator Widget",
            "name": "main_window",
            "width": 500,
            "height": 500
        },
        "image": {
            "src": "Images/Sun.png",
            "name": "sun1",
            "hOffset": 250,
            "vOffset": 250,
            "alignment": "center"
        },
        "text": {
            "data": "Click Here",
            "size": 36,
            "style": "bold",
            "name": "text1",
            "hOffset": 250,
            "vOffset": 100,
            "alignment": "center",
            "onMouseUp": "sun1.opacity = (sun1.opacity / 100) * 90;"
        }
    }
}

input_with_lists.json

[{
    "widget": {
        "debug": "on",
        "windows": [{
            "title": "Sample Konfabulator Widget",
            "name": "main_window",
            "width": 500,
            "height": 500
        },{
            "title": "Sample Konfabulator Widget",
            "name": "main_window",
            "width": 500,
            "height": 500
        },{
            "title": "Sample Konfabulator Widget",
            "name": "main_window",
            "width": 500,
            "height": 500
        }]
    }
}]
Share:
25,679
user2229544
Author by

user2229544

Updated on April 01, 2020

Comments

  • user2229544
    user2229544 about 4 years

    I have a JSON object that I'd like to get the key names from and store them in an ArrayList. I've used the following code

    jsonData(String filename) {
        JsonParser parser = new JsonParser();
        JsonElement jsonElement = null;
    
        try {
            jsonElement = parser.parse(new FileReader(filename));
        } catch (JsonIOException | JsonSyntaxException | FileNotFoundException e) {
            // TODO Auto-generated catch block
            e.printStackTrace();
        }
    
        JsonObject jsonObject = jsonElement.getAsJsonObject();
    
        int i = 0;
        for (Entry<String, JsonElement> entry : jsonObject.entrySet()) {
            String key = entry.getKey();
            JsonElement value = entry.getValue();
    
            keys.add(key);
            i++;
        }
        nKeys = i;
    }
    

    If I use this code with a simple JSON object

    {
        "age":100,
        "name":"mkyong.com",
        "messages":["msg 1","msg 2","msg 3"]
    }
    

    This works fine. age, name, and messages (not the values) are added to my ArrayList. Once I try and Use this same code with a more complex JSON like this

    {"widget": {
        "debug": "on",
        "window": {
            "title": "Sample Konfabulator Widget",
            "name": "main_window",
            "width": 500,
            "height": 500
        },
        "image": { 
            "src": "Images/Sun.png",
            "name": "sun1",
            "hOffset": 250,
            "vOffset": 250,
            "alignment": "center"
        },
        "text": {
            "data": "Click Here",
            "size": 36,
            "style": "bold",
            "name": "text1",
            "hOffset": 250,
            "vOffset": 100,
            "alignment": "center",
            "onMouseUp": "sun1.opacity = (sun1.opacity / 100) * 90;"
        }
    }}
    

    I only get the root key. Can someone point me in the right direction with this?

    Thanks everyone!

  • user2229544
    user2229544 about 11 years
    Thanks! I'll give that a try now. What I'm trying to do is parse a JSON object and place the values of each key in an array for later use. After I have each key I want to output them and then let the user tell me which data they want. All the examples I've found show how to pull data from a key, but you need the key ahead of time.