44

I'm working through designing a RESTful API. We know we want to return JSON and XML for any given resource. I had been thinking we would do something like this:

GET /api/something?param1=value1
Accept:  application/xml (or application/json)

However, someone tossed out using extensions for this, like so:

GET /api/something.xml?parm1=value1 (or /api/something.json?param1=value1)

What are the tradeoffs with these approaches? Is it best to rely on the accept header when an extension isn't specified, but honor extensions when specified? Is there a drawback to that approach?

4 Answers4

40

This, "However, philosophically - the first approach is the only approach.", and this "The proper official RESTful approach is to use Accept: header." are widely perceived to be the case, but are also absolutely incorrect.

Here's a brief snippet from Roy Fielding (who defined REST)...

"section 6.2.1 does not say that content negotiation should be used all the time." cite

That particular conversation is in the context of the 'Accept-Language:' header, but the same applies equally to the 'Accept:' header, as made clear later in his response...

"I have no idea why people can't see the second and third link on the top page

http://www.ics.uci.edu/~fielding/pubs/dissertation/top.htm

that point to the two PDF editions."

What he means there is that there's no issue in using different endpoints for different representations of the same source data. (In this case one .html endpoint and two different .pdf endpoints.)

Also in a similar discussion, this time regarding the virtues of using query parameters vs. using file extensions for different media types...

"That's why I always prefer extensions. Neither choice has anything to do with REST." cite

Again, that's slightly different to Accept vs. filename extensions, but Fielding's stance is still clear.

Answer - it really doesn't much matter. The trade-offs between the two aren't very significant and both are acceptable styles.

VoiceOfUnreason
  • 34,589
  • 2
  • 44
  • 83
10

The proper official RESTful approach is to use Accept: header.

However, you have to be careful not to break cacheability, which is one of REST's requirements. You need to have Vary: Accept header and cache which understands it. In ideal world you'd have it, but in real life your millage may vary. So the second solution isn't as clean, but it might be more practical.

Also, note that some very old browsers used to ignore headers, relying on the extension instead.

vartec
  • 20,846
9

Technically it doesn't really matter - your web server will be able to pass process it appropriately as it looks like. (I am assuming this but doesn't look like a showstopper).

However, philosophically - the first approach is the only approach. In REST, the URL actually only points to a URI - which is only a resource. Think for a moment this resource same as object in object oriented programming. You talk to this resource through only 4 methods (aka GET/POST/PUT/DELETE -or if anything that transport allows) but that method doesn't become description of object. Same way, the aspects the return value is not the URI. The object is still something and not something.xml or something.json

Suppose if you don't want to use Accept header, but if you still want to be truly REST philosophically, i wont mind something like:

GET /api/something?parm1=value1&return_type=xml

as opposed to

GET /api/something.xml?parm1=value1 (or /api/something.json?param1=value1)

But as i said, this difference is only philosophical.

Dipan Mehta
  • 10,612
0

@vartec: I think you are wrong

The proper official RESTful principle says nothing should be hidden in HTTP headers as it is the URI which is exposed or referenced, any detail about the request/response should be provided as part of URI

Hence i strongly recommend to avoid using header for details which about the request & response, and stick to

 GET /api/something.xml?parm1=value1 (or /api/something.json?param1=value1)

I am not able to find the references quickly, but i will post back with them (actually you could refer the O'reilly publication book "RESTful web services" (http://shop.oreilly.com/product/9780596529260.do) which confirms the same

Basav
  • 111