vigenere
vigenere

Reputation: 307

How to parse JsonPrimitive

I have the following json which i need to parse:

{
 "resource1": {
  "fare": 7511,
  "typeoftravel": "domestic",
  "vertical": "flight",
  "extra": "[{'duration': u'3h 0m', 'arrtime': u'2015-05-05t1930', 'nostops': 0, 'deptime': u'2015-05-05t1630', 'flightno': u'6E478'}]",
  "roundtrip": "O",
  "destination": "BLR",
  "returndate": 0,
  "lastupdated": "2015-03-29T10:40:12",
  "source": "IXC",
  "carrier": "IndiGo",
  "date": 20150505,
  "class": "E"
 },
 "resource2": {
  "fare": 6320,
  "typeoftravel": "domestic",
  "vertical": "flight",
  "extra": "[{'duration': u'4h 25m', 'arrtime': u'2015-05-06t2210', 'nostops': 0, 'deptime': u'2015-05-06t1745', 'flightno': u'9W7076'}]",
  "roundtrip": "O",
  "destination": "BLR",
  "returndate": 0,
  "lastupdated": "2015-03-29T17:08:09",
  "source": "IXC",
  "carrier": "Jet Airways",
  "date": 20150506,
  "class": "E"
 }
}

I am not able to determine what kind of field "extra" is. It's not a jsonObject or jsonArray. I am able to cast it to jsonPrimitive but now how do i parse this. I am using Gson for parsing.

Upvotes: 0

Views: 10135

Answers (1)

Mohamed Shaaban
Mohamed Shaaban

Reputation: 1169

Assuming you have the following classes:

Resources:

public class Resources {

    Resource resource1;
    Resource resource2;
}

Resource:

import java.util.List;

public class Resource {

    int fare;
    String typeoftravel;
    String vertical;
    String roundtrip;
    String destination;
    int returndate;
    String lastupdated;
    String source;
    String carrier;
    long date;
    String clazz;
    List<Extra> extra;
}

Extra:

public class Extra {

    String duration;
    String arrtime;
    int nostops;
    String deptime;
    String flightno;
}

One possible solution, is to register new JsonSerializer to your Gson object, which will

  1. Copy all normal fields, except extra
  2. Extract extra as String
  3. Parse extracted extra again to remove the quotes
  4. Then deserialize it as List using TypeToken

See below code for explanation

ResourceDeserializer

import java.lang.reflect.Type;
import java.util.List;

import com.google.gson.JsonDeserializationContext;
import com.google.gson.JsonDeserializer;
import com.google.gson.JsonElement;
import com.google.gson.JsonObject;
import com.google.gson.JsonParseException;
import com.google.gson.JsonParser;
import com.google.gson.reflect.TypeToken;


public class ResourceDeserializer implements JsonDeserializer<Resource> {

    @Override
    public Resource deserialize(JsonElement value, Type type,
            JsonDeserializationContext context) throws JsonParseException {

        final JsonObject resourceJson = value.getAsJsonObject();

        final Resource resource = new Resource();
        resource.fare = resourceJson.get("fare").getAsInt();
        resource.typeoftravel = resourceJson.get("typeoftravel").getAsString();
        resource.vertical = resourceJson.get("vertical").getAsString();
        resource.roundtrip = resourceJson.get("roundtrip").getAsString();
        resource.destination = resourceJson.get("destination").getAsString();
        resource.returndate = resourceJson.get("returndate").getAsInt();
        resource.lastupdated = resourceJson.get("lastupdated").getAsString();
        resource.source = resourceJson.get("source").getAsString();
        resource.carrier = resourceJson.get("carrier").getAsString();
        resource.date = resourceJson.get("date").getAsLong();
        resource.clazz = resourceJson.get("class").getAsString();

        Type listType = new TypeToken<List<Extra>>(){}.getType();

        String extraStr = resourceJson.get("extra").getAsString();

        extraStr = extraStr.replaceAll("u?(\'[^\']+\')", "$1");

        JsonElement extraList = new JsonParser().parse(extraStr);

        resource.extra = context.deserialize(extraList, listType);

        return resource;
    }

}

Registering the above deserializer

Gson gson = new GsonBuilder()
        .registerTypeAdapter(Resource.class, new ResourceDeserializer())
        .create();

Note that, I renamed the attribute class to clazz, because class is a reserved word!

Upvotes: 2

Related Questions