views:

1111

answers:

4

I am new to JSON and trying to recover some text from a JSON variable.

The JSON variable is sent from a Javascript File and has this structure:

foo({
  "query": {
  "count": "2",
  "created": "2009-07-25T08:17:54Z",
  "lang": "en-US",
  },
  "results": {
   "result": [
    {
     "abstract": "<b>Pizza</b> Hut®. Order Online for Delivery or Carry-out. Fast &amp; Easy.",
     "title": "<b>Pizza</b> Hut"
    },
    {
     "abstract": "Official site of Domino's <b>Pizza</b> delivery chain, which offers thin crust, deep dish, and hand tossed <b>pizzas</b> with a variety of side items and beverages. Site <b>...</b>",
     "title": "Domino's <b>Pizza</b>"
    }
   ]
  }
 }
});

The JSON goes to a callback function named foo:

function foo(o){
  var out = document.getElementById('container');
  out.innerHTML = o.query.count;
}

My Problem: I know how to print out the query count variable using the callback function above, but I don't know how to print out the the title of the first result in the results array.

How can I change the callback function to display the first result title? And also, is there a foreach statement, where I could print out all the titles from all the results?

Thanks!

UPDATE: JSBIN for this code is at: http://jsbin.com/ejiwa/edit

+4  A: 

Does the following work:

o.results.result[0].title

to get the first result title? And to iterate over all results:

for (var i=0; i<o.results.result.length; i++) {
    var result = o.results.result[i];
    alert(result.title);
}

EDIT: Are you sure you copied it right? Here's what I get in Rhino:

js> o = {
  "query": {
  "count": "2",
  "created": "2009-07-25T08:17:54Z",
  "lang": "en-US",
  },
  "results": {
   "result": [
    {
     "abstract": "<b>Pizza</b> Hutr. Order Online for Delivery or Carry-out. Fast &amp; Easy.",
     "title": "<b>Pizza</b> Hut"
    },
    {
     "abstract": "Official site of Domino's <b>Pizza</b> delivery chain, which offers thin crust, deep dish, and hand tossed <b>pizzas</b> with a variety of side items and beverages. Site <b>...</b>",
     "title": "Domino's <b>Pizza</b>"
    }
   ]
  }
 }

js> o.results.result[0].title
<b>Pizza</b> Hut
ars
no, unfortunately it does not
chris
@chris: ars's code works perfectly for me, though I did have to correct a typo in your code - you have an extra closing brace at the end of your call to `foo()`.
RichieHindle
Weird. See the output I just pasted from my side.
ars
Ahh. Just saw @Richie's comment. Good catch!
ars
Here is the jsbin file: http://jsbin.com/ejiwa/edit where I can't get it to work. Could you see if it works there?
chris
Works fine without the typo: http://jsbin.com/esore/edit
ars
chris
the new jsbin is at: http://jsbin.com/uyefo/edit
chris
Never mind, got it to work!. Thanks!!!!
chris
+1  A: 

As you can see from the JSON, the object has a property called "results" which contains a property called "result" which is an array of objects.

To display the first of that, you simply do as you already did with count, but just follow the structure to the title instead.

o.query.results.result[0].title

To loop over each result, you can simply loop over the result property like an array, for example like this:

var results = o.query.results.result;
for(var i = 0; i < results.length; i++) {

}

JSON is simply JavaScript code. Think of the JSON snippet as a JavaScript object declaration and you should have no problems understanding it.

Jani Hartikainen
Using this statement: out.innerHTML = o.results.result[0].title; doesn't seem to work.
chris
Ah figures.. o.query.results.result[0].title is the correct path :P Looks like there's a mistake in your pasted JSON snippet
Jani Hartikainen
A: 

I am not sure what the o parameter is in your callback function. I usually assign the XMLHttpRequest or ActiveXObject to a global var req.

Then use a callback:

 function json_callback() {
    if (req.readyState == 4) {
            if (req.status == 200) {
                    jsonObj = eval("(" + req.responseText + ")");
                    var out = document.getElementById('container');
                    out.innerHTML = jsonObj.query.count;
            }
       }
 }

It should be noted that you should only use eval() if you fully trust the server and the data the server is sending the client. There are JSON parsers available which are actually faster than eval() and also more secure as they limit it to only JSON whereas eval() can parse and execute all of JavaScript which could be a security risk. It is expected in the next version of ECMAScript that there will be a standard JSON parser built in.

Sean A.O. Harney
+1  A: 

The actual object has a slightly different structure than you wrote. results is actually an element of query. So try this:

o.query.results.result[0].title
Gumbo
i think i made a mistake while trying to prettify the code, but firebug says: o.query.results is undefined
chris
It works for me when I run that on the original data from Yahoo. `function foo(o) { return o.query.results.result[0].title; }` returns `<b>Pizza</b> Hut`.
Gumbo
Never mind, you are right. Thanks!!!
chris