0

Here's the JSON I'm parsing.

   <item>{\"name\":{\"mainName\":\"Ham and cheese
                    sandwich\",\"alsoKnownAs\":[]},\"placeOfOrigin\":\"\",\"description\":\"A ham and cheese
                    sandwich is a common type of sandwich. It is made by putting cheese and sliced ham
                    between two slices of bread. The bread is sometimes buttered and/or toasted. Vegetables
                    like lettuce, tomato, onion or pickle slices can also be included. Various kinds of
                    mustard and mayonnaise are also
                    common.\",\"image\":\"https://upload.wikimedia.org/wikipedia/commons/thumb/5/50/Grilled_ham_and_cheese_014.JPG/800px-Grilled_ham_and_cheese_014.JPG\",\

"ingredients\":[\"Sliced
                bread\",\"Cheese\",\"Ham\"]}

alsoKnownAs and ingredients arrays don't have keys. I need to convert them to lists and add them to the Sandwich object. Currently, it doesn't work. I thought the code inside the for loop would be enough. Can someone please take a look? Thank you in advance.

I based my code on the answers in this thread: Converting JSONarray to ArrayList

Also, one of the posters in the above thread suggested using a helper method from this link(line 45). https://gist.github.com/codebutler/2339666

My code:

public static Sandwich parseSandwichJson(String json) {
        // If the JSON string is empty or null, then return early.
        if (TextUtils.isEmpty(json)) {
            return null;
        }

        Sandwich sandwiches = null;
        try {

            // Create a JSONObject from the JSON file
            JSONObject jsonObject = new JSONObject(json);

            //fetch JSONObject named name
            JSONObject objectName = jsonObject.getJSONObject("name");

            // Extract the value for the key called "main_name"
            String mainName = "";
            if (objectName.has("mainName")) {
                mainName = objectName.optString(KEY_MAIN_NAME);
            }

            JSONArray alsoKnownAsArray = objectName.optJSONArray(KEY_ALSO_KNOWN_AS);
            List<String> alsoKnownData = new ArrayList();
            for (int i = 0; i < alsoKnownAsArray.length(); i++) {
               alsoKnownData.add(alsoKnownAsArray.getString(i));

            }

            String placeOfOrigin = "";
            if (objectName.has("placeOfOrigin")) {
                placeOfOrigin = objectName.optString(KEY_PLACE_OF_ORIGIN);
            }

            String description = "";
            if (objectName.has("description")) {
                description = objectName.optString(KEY_DESCRIPTION);
            }

            String image = "";
            if (objectName.has("image")) {
                image = objectName.optString(KEY_IMAGE);
            }

                       JSONArray ingredientsArray = objectName.optJSONArray(KEY_INGREDIENTS);
            List<String> ingredientsData = new ArrayList<String>();
            if (ingredientsArray != null) {
                for (int i = 0; i < ingredientsArray.length(); i++) {
                    ingredientsData.add(ingredientsArray.getString(i));
                }
            }

            Sandwich sandwich = new Sandwich(mainName, alsoKnownAsArray, placeOfOrigin, description, image, ingredientsArray);
            sandwiches.add(sandwich);


        } catch (JSONException e) {
            // If an error is thrown when executing any of the above statements in the "try" block,
            // catch the exception here, so the app doesn't crash. Print a log message
            // with the message from the exception.
            Log.e("QueryUtils", "Problem parsing sandwich JSON results", e);
        }
        // Return the list of sandwiches
        return sandwiches;
    }
Abdullah Ilgaz
  • 719
  • 1
  • 17
  • 39
LeadBox4
  • 83
  • 2
  • 11

2 Answers2

0

You can parse the JSON this way:

public class JsonUtils {

public static Sandwich parseSandwichJson(String json) {

    try {
        JSONObject mainJsonObject = new JSONObject(json);

        JSONObject name = mainJsonObject.getJSONObject("name");
        String mainName = name.getString("mainName");

        JSONArray alsoKnownAsArray = name.getJSONArray("alsoKnownAs");
        List<String> alsoKnownAs = new ArrayList<>(alsoKnownAsArray.length());

        for ( int i = 0; i < alsoKnownAsArray.length(); i++ ) {
            alsoKnownAs.add(alsoKnownAsArray.getString(i));

            Log.i("alsoKnownAs", "I am here" + alsoKnownAs);
        }

        String placeOfOrigin = mainJsonObject.optString("placeOfOrigin");

        String description = mainJsonObject.getString("description");

        String image = mainJsonObject.getString("image");

        JSONArray ingredientsArray = mainJsonObject.getJSONArray("ingredients");
        List<String> ingredients = new ArrayList<>(ingredientsArray.length());

        for ( int i = 0; i < ingredientsArray.length(); i++ ) {
            Log.i("ingredients", "These are the ingredients" + ingredients);
            ingredients.add(ingredientsArray.getString(i));
        }

        return new Sandwich(mainName, alsoKnownAs, placeOfOrigin, description, image, ingredients);

    } catch (JSONException e) {
        e.printStackTrace();
    }
    return null;
  }
}
  • I'm aware of Udacity guidelines. I have an idea of how to populate the view. So that there are no issues with Udacity, can you please delete the populate views code? Can you please elaborate on why my parsing code doesn't work? – LeadBox4 Sep 24 '18 at 04:06
  • I think you got it wrong here List alsoKnownData = new ArrayList(); for (int i = 0; i < alsoKnownAsArray.length(); i++) { alsoKnownData.add(alsoKnownAsArray.getString(i)); } – Show Young Soyinka Sep 24 '18 at 06:20
  • Instead of List ingredients = new ArrayList<>(ingredientsArray.length()); – Show Young Soyinka Sep 24 '18 at 06:22
  • You have to set the lenht of the list ingredients to the length of arraylist – Show Young Soyinka Sep 24 '18 at 06:24
  • Why return null; ? – LeadBox4 Sep 25 '18 at 07:08
  • Because I have returned the SandWish object in the try-and-catch methods above, so I don't want to return any more thing – Show Young Soyinka Sep 25 '18 at 09:25
  • If you didn't return your Sandwish object from try and catch, your object will always be null even if you returned it outside the try and catch – Show Young Soyinka Sep 25 '18 at 09:29
  • Initially(in the code above) I declared Sandwich outside of the try catch method. I wrote a similar code when parsing an array instead of an object(like here). There, I declared the array above try catch and returned the list outside try catch. – LeadBox4 Sep 26 '18 at 06:36
  • Try to recognize that every logic you are performing happened inside try and catch, hence you need to return the result for which you started try and catch, otherwise, the list of sandwich will always be null. – Show Young Soyinka Sep 26 '18 at 06:41
  • Another way to look into this is to pretend to erase try and catch and everything inside it, glaringly, you will see the list of sandwich is always null, so you must always return null outside try and catch and return the result inside try and catch – Show Young Soyinka Sep 26 '18 at 06:44
  • Please mark this answer as accepted if it works for you and ask another question if you have. I will be willing to help. Thanks – Show Young Soyinka Sep 26 '18 at 07:00
0

Use Gson for parsing (https://github.com/google/gson)

Add this 2 class for data handle

public class CustomData
{
    private List<String> ingredients;

    private String placeOfOrigin;

    private String description;

    private Name name;

    private String image;

    public List<String> getIngredients ()
    {
        return ingredients;
    }

    public void setIngredients (List<String> ingredients)
    {
        this.ingredients = ingredients;
    }

    public String getPlaceOfOrigin ()
    {
        return placeOfOrigin;
    }

    public void setPlaceOfOrigin (String placeOfOrigin)
    {
        this.placeOfOrigin = placeOfOrigin;
    }

    public String getDescription ()
    {
        return description;
    }

    public void setDescription (String description)
    {
        this.description = description;
    }

    public Name getName ()
    {
        return name;
    }

    public void setName (Name name)
    {
        this.name = name;
    }

    public String getImage ()
    {
        return image;
    }

    public void setImage (String image)
    {
        this.image = image;
    }

}

Class Name:

public class Name
{
    private String[] alsoKnownAs;

    private String mainName;

    public String[] getAlsoKnownAs ()
    {
        return alsoKnownAs;
    }

    public void setAlsoKnownAs (String[] alsoKnownAs)
    {
        this.alsoKnownAs = alsoKnownAs;
    }

    public String getMainName ()
    {
        return mainName;
    }

    public void setMainName (String mainName)
    {
        this.mainName = mainName;
    }

}

Function to parse JSON to Object

public CustomData parseJsonToData(String jsonString) {
    CustomData data = new Gson().fromJson(jsonString, CustomData.class);
    return data;
}

So you can get List by

CustomData data = parseJsonToData(jsonString)
List<String> ingredients = data.getIngredients()
Tung Duong
  • 1,156
  • 7
  • 19