Ajax and Web Service Data Formats Part 2: JSON and JSONP

Contributing Editor

This is the second article in a series discussing web service data formats for Ajax. In part 1, we examined XML, SOAP and HTML. Today, we take a closer look at JSON and JSONP.

JSON

JavaScript Object Notation was devised by JavaScript guru Douglas Crockford. Essentially, it’s a lightweight data-interchange format written using JavaScript object and array literal syntax.

We can convert the XML books example in the first article to a comparable JSON format:


[
	{
		title: "The Principles of Beautiful Web Design, 2nd Edition",
		url: "http://www.sitepoint.com/books/design2/",
		author: "Jason Beaird",
		publisher: "SitePoint",
		price: {
			currency: "USD",
			amount: 39.95
		}
	},
	{
		title: "jQuery: Novice to Ninja",
		url: "http://www.sitepoint.com/books/jquery1/",
		author: "JEarle Castledine & Craig Sharkie",
		publisher: "SitePoint",
		price: {
			currency: "USD",
			amount: 29.95
		}
	},
	{
		title: "Build Your Own Database Driven Website",
		url: "http://www.sitepoint.com/books/phpmysql4/",
		author: "Kevin Yank",
		publisher: "SitePoint",
		price: {
			currency: "USD",
			amount: 39.95
		}
	}
]

This is an array of books represented as objects with title, url, author, publisher and price properties. Price is a child object with the currency and numeric amount properties.

It’s easy to parse a string of JSON data in JavaScript. Ideally, you can use the browser’s native JSON.parse(json-string) method or a library such as Douglas Crockford’s JSON-js. Even if these are not available, you can fallback to JavaScript’s native eval() function. There’s no parsing code to write and it’s easy to retrieve data:


var json = xhr.responseText;
var book = JSON.parse(json);
alert(book[0].title); // first book title
alert(book[1].url); // second book URL

The advantages of JSON are:

  • A smaller, less verbose format than XML.
  • JSON is generally readable, although it’s best if tabs and carriage returns are used to delimit the data. Unlike XML, browsers do not normally display JSON in a readable format although viewing add-ons are available for Firefox, Chrome and Opera.
  • It’s easy to parse and use JSON data in JavaScript.
  • JSON support is provided in other languages such as PHP.

There are a few disadvantages:

  • JSON has less support than XML in server-side languages, although many third-party libraries are available from the JSON.org website.
  • Security issues can arise if you rely on eval() to parse JSON strings — the payload could contain a malicious script.

However, JSON’s benefits more than outweigh the risks. It’s an ideal Ajax data format is should probably be your first choice.

JSONP (or JSON-P)

If you’re using XMLHttpRequest to call a JSON web service, the response is returned as a string which can be parsed using JSON.parse() or eval(). However, you can also create Ajax components which use script-injection techniques, i.e. a script tag is added to the DOM which loads remote code:


var script = document.createElement("script");
script.src = "http://webservice.com/?a=1&b=2";
document.getElementsByTagName("head")[0].appendChild(script);

Unlike XMLHttpRequest, script injection can retrieve data from remote servers on different domains. This makes the technique ideal for traffic analyzers, bookmarklets, widgets and advertising systems.

Unfortunately, any returned JSON data is executed immediately as native JavaScript code. It’s not assigned to a variable so it’s lost forever. We can overcome this problem by passing the name of a callback function to our web service:


var script = document.createElement("script");
script.src = "http://webservice.com/?a=1&b=2&callback=MyDataHandler";
document.getElementsByTagName("head")[0].appendChild(script);

The web service returns JSON data wrapped in a call to the callback function. This is JSONP, or “JSON with padding,” e.g.


MyDataHandler([
	{
		title: "The Principles of Beautiful Web Design, 2nd Edition",
		url: "http://www.sitepoint.com/books/design2/",
		author: "Jason Beaird",
		publisher: "SitePoint",
		price: {
			currency: "USD",
			amount: 39.95
		}
	}
	...
]);

The JSON object is parsed and passed to the MyDataHandler() function as soon as the download completes.

JSON and JSONP have become popular Ajax data formats. However, it is possible to reduce the data size even further — we’ll discuss the options in the final post in this series.

Free book: Jump Start HTML5 Basics

Grab a free copy of one our latest ebooks! Packed with hints and tips on HTML5's most powerful new features.

  • wwb_99

    You missed one of the biggest disadvantages with JSON — there is no concept of a schema such as in XML, so there is no way to validate the data’s form without attempting to parse it as well as build tool support for it.

    This isn’t to say JSON is the lesser of most evils here.

    • moneymark

      Exactly what I was thinking. Not being able to provide a well defined contract is the biggest glaring disadvantage of JSON. I love working with and using JSON, but the aforementioned disadvantage should not be overlooked.

    • Web Dev

      You should not need a schema. JSON’s structure has a strict set of rules which define what types are being passed through.

      • wwb_99

        Well formed data does not mean you have valid data . . .

    • http://www.optimalworks.net/ Craig Buckler

      Do you validate your incoming Ajax XML data against a schema in JavaScript? It is possible — you can use IE’s validateOnParse method (I don’t think other browsers support it) or a proxy service.

      However, what’s the advantage? Ultimately, you’re grabbing individual items of data from the XML and, if they’re not there, you know there’s a problem. In many cases, validation is an unnecessary extra step which will slow down Ajax requests.

      • wwb_99

        Does it matter for ajax requests to the browser? Generally not so much — and that is where JSON truly shines. But I thought this series was about “Web Service Data” as well and in that context you really do care if the data matches your schema. Especially if you are working in strongly-typed compiled languages where you can’t be loosey goosey about what is a stiring vs an int vs a long vs a double. Being able to validate the incoming data against a schema saves you from having to write a lot of self-defensive code throughout the system. Or deal with many failures.

      • http://www.optimalworks.net/ Craig Buckler

        The series is about web service data formats which are (commonly) used for Ajax. Schema validation is certainly useful, but I’d generally see it being used to verify incoming data or debugging. That’ll occur well before it’s used for Ajax requests.

      • wwb_99

        But what about ajax responses? Do you trust the client not to submit evil stuff?

  • Kevin Albs

    Cool, I’ve never tried using JSON with Ajax or using the script injection. Thanks for the tips.

  • Stormrider

    You haven’t mentioned any of the benefits (or disadvantages) of using JSONP – why would I use this instead of returning JSON and defining a callback function to handle it? What is the point?

    • http://www.optimalworks.net/ Craig Buckler

      JSONP has the same advantages and disadvantages as JSON. However, it’s a solution to the specific situation when you’re using script injections rather than XMLHttpRequest for Ajax calls.

      Personally, I’d recommend XHR/JSON if you’re making multiple calls to a web service on the same domain. If you’re making relatively few cross-domain calls, script injections are a good solution — but you’ll need JSONP.

  • rudiedirkx

    Your first JSON ‘example’ actually isn’t valid. Keys have to be quoted as well:
    {"title": "bla"}
    Try executing JSON.parse('[{"title":"bla"}]') and JSON.parse('[{title:"bla"}]')
    If the native JSON functions aren’t the standard, what is!?

    • http://www.optimalworks.net/ Craig Buckler

      Thanks rudiedirkx.

      Quotes around aren’t normally necessary for JavaScript object literal properties (unless they have spaces or start with numbers), but you’re correct that it’s necessary when using the browser’s native JSON.parse method.

      eval() doesn’t need quotes and it’s possible other parsers don’t either.

  • Jason

    In this article you use both JSON.parse (correct) and JSON.Parse (incorrect, capital P). You’d probably save folks some headaches if you corrected this. Nice article though!

    • http://www.optimalworks.net/ Craig Buckler

      Well spotted Jason — it’s been corrected.

  • Big Bob

    Might want to mention that jquery (and probably other libraries) have built-in support for jsonp. No need to roll your own

  • madr

    Instead of eval, the following should be encouraged:
    var results = new Function('return ' + json_string)();
    Used in the jQuery source according to Paul Irish.