1

i'm trying to parse Json with the google Gson library, but for the moment i can't get it to work ...

Here is the Json i'm supposed to get :

{
"shoppingLists": [
    {
        "ShoppingList": {
            "id": "51",
            "name": "loool",
            "created": "2014-03-22 13:03:22",
            "modified": "2014-03-22 13:03:22"
        },
        "ShoppingItem": [
            {
                "id": "24",
                "shopping_item_category_id": "19",
                "name": "Biscuits",
                "description": "",
                "created": "2014-02-05 17:43:45",
                "modified": "2014-02-05 17:43:45",
                "category_name": "Confiseries \/ Gouters"
            },
            {
                "id": "25",
                "shopping_item_category_id": "19",
                "name": "Snickers",
                "description": "",
                "created": "2014-02-05 17:44:08",
                "modified": "2014-02-05 17:44:08",
                "category_name": "Confiseries \/ Gouters"
            },
            {
                "id": "26",
                "shopping_item_category_id": "19",
                "name": "C\u00e9reales",
                "description": "",
                "created": "2014-02-05 17:44:57",
                "modified": "2014-02-05 17:44:57",
                "category_name": "Confiseries \/ Gouters"
            }
        ]
    }
 ]
}

Here are my models :

shoppingLists :

public class shoppingLists {
        public ShoppingList ShoppingList;
        public List<ShoppingItem> ShoppingItems;
}

ShoppingList :

public class ShoppingList {
public int id;
public String name;
public String created;
public String modified;
}

ShoppingItem :

public class ShoppingItem {
public int id;
public int shopping_item_category_id;
public String name;
public String description;
public String created;
public String modified;
public String category_name;
}

Here is my AsyncTask which get the Json from the server :

public class APIRetrieveLists extends AsyncTask<APIRequestModel, Void, List<shoppingLists>>{

SQLHelper _sqlHelper = null;
Context _context;
ProgressBar _pb;

public APIRetrieveLists(Context context, ProgressBar pb){
    this._context = context;
    this._pb = pb;
}


@Override
protected void onPreExecute(){
}

@Override
protected void onPostExecute(List<shoppingLists> model){
    this._sqlHelper = new SQLHelper(this._context);
    if (model != null){
        for (shoppingLists cn : model){
            Log.i("infos", "list's name => " + cn.ShoppingList.name);
        }
    }else{
        Log.i("infos", "model is null");
    }
}

@Override
protected List<shoppingLists> doInBackground(APIRequestModel... arg0) {
    APIRequestModel model = arg0[0];
    try
    {
        try
        {
            List<NameValuePair> nameValuePairs = new ArrayList<NameValuePair>();
            nameValuePairs.add(new BasicNameValuePair("access_token", model.getToken()));
            HttpClient httpclient = new DefaultHttpClient();
            HttpPost httppost = new HttpPost("http://apiurl/index.json");
            httppost.setEntity(new UrlEncodedFormEntity(nameValuePairs, HTTP.UTF_8));
            HttpResponse response = httpclient.execute(httppost);
            BufferedReader reader = new BufferedReader(new InputStreamReader(response.getEntity().getContent()));
            String s = "";
            String all = "";
            while ((s = reader.readLine()) != null){
                all += s;
            }
            Gson gson = new Gson();
            List<shoppingLists> Obj = (List<shoppingLists>) gson.fromJson(all, new TypeToken<List<shoppingLists>>(){}.getType());
            return (Obj);
        } 
        catch (ClientProtocolException e) {
            Log.i("infos", "first");
            return (null);
        } 
    }
    catch (Exception e){
        Log.i("infos", "second");
        return (null);
    }
}
}

The exception "second" is always firing ... Log.i("infos", "model is null"); is also executed. if someone could help :) thank you ! regards.

json

2 Answers 2

2

Add one more wrapper to your shoppingLists, as your jsonObject had shoppingLists as key and array of ShoppingListItem as value. Also you need to annotate @SerializedName for ShoppingItems field because it is not matching with the key in Json.

Find below updated classes and parser

Gson gson = new Gson();
FinalClass myObj = gson.fromJson(jsonString, FinalClass.class);

Classes

public class FinalClass {
    public ArrayList<ShoppingListItem> shoppingLists;
}

public class ShoppingListItem {
    public ShoppingList ShoppingList;
    @SerializedName("ShoppingItem")
    public List<ShoppingItem> ShoppingItems;
}

public class ShoppingList {
    public int id;
    public String name;
    public String created;
    public String modified;
}

public class ShoppingItem {
   public int id;
   public int shopping_item_category_id;
   public String name;
   public String description;
   public String created;
   public String modified;
   public String category_name;
}
Sign up to request clarification or add additional context in comments.

7 Comments

Still getting the second exception, is the class name important to the parser ?
@bottus can you paste the exception/Logcat you are getting? class name can be anything.. but important thing is object/variable should match with keys in json
Here is the exception : com.google.gson.JsonSyntaxException: java.lang.IllegalStateException: Expected BEGIN_OBJECT but was STRING at line 1 column 6
@bottus Can you paste your exact complete Json response you are receiving from web service? As per Json you provided in your question, I am suggesting the changes..
i can't get it in eclipse properly displayed ... any advice about this please ?
|
1

You don't have a list of shoppingLists items in the json - if my glasses don't fool me. So changing:
List<shoppingLists> Obj = (List<shoppingLists>) gson.fromJson(all, new TypeToken<List<shoppingLists>>(){}.getType());

into:

shoppingLists obj = gson.fromJson(all, shoppingLists.class);

will not cause any runtime gson exceptions. Eventually you can wrap that single parsed obj into a List so it matches with your current code. For Example:

shoppingLists obj = gson.fromJson(all, shoppingLists.class);
ArrayList<shoppingLists> result = new ArrayList<shoppingLists>();
result.add(obj);
return result;

7 Comments

i can eventually get several shoppingLists, i changed my fromJson into List<shoppingLists> Obj = (List<shoppingLists>) gson.fromJson(all, shoppingLists.class); but it still doesn't work .. also i get a warning because of the cast
The thing is gson.fromJson will parse a shoppingLists. Casting that to a list will throw a runtime exception. Updating the answer a bit.
Still getting an exception even with what you said gunar, and adding the obj to the list is okay but imagine that i have several shoppingLists in the json, this woudn't work anymore right ?
I posted my answer considering above given JSON example. If you have cases when you receive an array, then that's a different story
If the server changes the data type of the response, then you're in trouble because you don't know how to parse the response. The answer from Uttam looks promising.
|

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.