Bankzilla
Bankzilla

Reputation: 2096

Loop through complex JSON object

I have one extremely complex json object, I'm needing to write all the properties and keys out as they are. I've got the concept of it just can't get the execution.

Needing to keep recalling the function if the object has a object and so on. I'm hitting snags though, some of the keys aren't being outputted, some of the values are being broken up as

0:h 1:t 2:t 3:p 4: 5:/ 6:/ etc....
name:Travel
scheme:
label:

I assume there's a little error somewhere in my code that needs to be changed.

ObjectValues = function(obj){
for(var j in obj){
   if(typeof(obj[j]) == "object"){
       for(var k in obj[j]){
         ObjectValues(obj[j][k]);
       }
   } else {
       console.log(j + ":" + obj[j]);
   }
}

_

{
"title": "Norway Tourism: Wildlife and Nature",
"author": "",
"categories": [
    {
        "name": "Travel",
        "scheme": "",
        "label": ""
    }
],
"countries": [

],
"content": [
    {
    "thumbnails": [
    {
        "audioChannels": 0,
        "audioSampleRate": 0,
        "bitrate": 0,
        "checksums": {
            "md5": "7089E4E044069AE7702DEC686"
        }
      }
    ]
   }
  ]
}

Upvotes: 3

Views: 7548

Answers (4)

Matthew Flaschen
Matthew Flaschen

Reputation: 284836

Use:

ObjectValues = function(obj) {
    var isArray = obj instanceof Array;
    for (var j in obj) {
        if (obj.hasOwnProperty(j)) {
            if (typeof(obj[j]) == "object") {
                if(!isArray)
                {
                    console.log(j + ":");
                }
                ObjectValues(obj[j]);
            } else if(!isArray) {
                console.log(j + ":" + obj[j]);
            }
        }
    }
}

Note the removed loop. The way you were splitting it up, you were losing the k names.

You should also use hasOwnProperty to avoid serializing unwanted keys.

If the value is an object, you still want to serialize the key (e.g. you don't want to lose foo for {foo: {} }).

Finally, I had to do an array check, because arrays are objects, and we do want to output the keys nested within arrays, but we don't want to output the array indices themselves.

Demo at jsFiddle.

Upvotes: 2

Mike Samuel
Mike Samuel

Reputation: 120516

ObjectValues = function(v, k){
  if (typeof v == "object") {
    for (var kp in v) {
      if (Object.hasOwnProperty.call(v, kp)) {
        ObjectValues(v[kp], k != undefined ? k + "." + kp : kp);
      }
    }
  } else {
    console.log(k + ":" + v);
  }
};

should work even for JSON values that are not objects. It will work for

ObjectValues(JSON.parse("0"));

which would not be handled by the original and it will not iterate over characters in a top-level string if you do ObjectValues("http://...").

Upvotes: 8

Frunsi
Frunsi

Reputation: 7147

As there is a jquery tag to your question:

I personally use the jquery.dump plugin for such purposes.

Upvotes: 0

Greg Pettit
Greg Pettit

Reputation: 10830

Can't say it's the only problem, but you're missing a comma after the countries array.

Also, for segments like "categories" (and others), are you sure it needs to be wrapped in square braces? In JS terms, that's an array. So I believe you're saying that you have an array, but in this case the only member of that array is an object.

Upvotes: 0

Related Questions