Page:Aaron Swartz s A Programmable Web An Unfinished Work.pdf/46

From Wikisource
Jump to navigation Jump to search
This page has been proofread, but needs to be validated.

34 5. BUILDING A PLATFORM: PROVIDING APIS

lets you pick the function name. So a URL like http://www.example.net/info.json?callback=foo would return:

    >    foo([5, ‘‘foo’’]);

The whole technique is known as JSONP and, naturally, it’s automated by all the major JSON libraries so you don’t have to worry about any of these details.

Alright, so now that we have a pile of JSON, where do we put it. The answer, of course, is the same place as your HTML. Going back to an older example, let’s say we have some information about a book at:

http://books.example.org/b/3j7is

Where does the JSON go? At the very same place!

You see, HTTP has a nifty feature called Content Negotiation that allows for the same URL to return different formats depending on who’s requesting things. The classical example of content negotiation is the transition from GIF images to the newer PNG image format. Some older versions of Internet Explorer didn’t support PNG; servers could use Content Negotiation to send them older GIF images instead.

The way it works is that every time you make an HTTP request (like a GET), the client sends along a series of Accept headers saying what formats it likes. Here’s a typical example:

    >    Accept: text/html; q=1.0, text/*; q=0.8, image/gif;
         q=0.6, image/jpeg; q=0.6, image/*; q=0.5, */*; q=0.1

This says the browser prefers HTML, then takes text, then GIFs and JPEGs, then any other image, then anything else.

But for APIs we don’t need to do anything so complicated. We can just have our API clients send:

    >    Accept: application/json

and have the server keep an eye out for that and return the JSON version if it sees it. Otherwise, it serves the HTML as usual.

Of course, you’ll probably want to provide an option for people who can’t easily do Content Negotiation. So it’s traditional to let:

http://books.example.org/b/3j7is.html