7 ms·
Please, please don't help to persist the convention of putting the API version number in the URL. There are far better ways of doing it. http://stackoverflow.c
by transmit101 14y ago
Please, please don't help to persist the convention of putting the API version number in the URL. There are far better ways of doing it.
http://stackoverflow.com/a/975394/62871 http://stackoverflow.com/a/975394/62871
- MatthewPhillips 14y agoAlso don't put the format in the URL, that's what Accepts is for.
- andraz 14y agoWhile in theory great Accepts are just additional burden for web developers. We don't want to need to deal with headers. We want to fetch an url and get _the_same_data_ no matter if the url was entered in the browser, wget, or inside the app we're writing. For a simple developer, output format is just another parameter and it shouldn't be hidden in HTTP stack.
- MatthewPhillips 14y agoI don't think 1 additional line of code is much of a burden. If you put it in the URL you're forcing the server to ignore the Accept header that the browser sends and pay attention to some non-standard url substring instead.
- andraz 14y agoIt's not just one additional line of code. It is additional work every time you try to view result in the browser. Which you basically can't because you can't put accept header in url bar.. At least in python, making requests becomes quite a few more lines of code if you want to add headers. There's usually a short-hand command if you just want to get full data from an url and a "create-an-object, then set these parameters, then this, then open a connection then read what's there". Mandatory headers are just a way to make life of a regular developer painful.
- MatthewPhillips 14y agoSounds like you just need to abstract that part into a function. Much better solution than breaking HTTP. HTTP is not supposed to send the same results for a given URL, it is supposed to send the same results for the a given request. In the case of the browser, it asks for HTML.
- qw 14y agoI can see that using "Accept" can be considered a more elegant solution, I don't see how adding a parameter will break HTTP. There is nothing in the HTTP standard that says what an URL should or should not return. The Accept-header is just an additional source of information.
- MatthewPhillips 14y agoNot actually, the Accept header isn't a mere suggestion. If the server chooses not to fulfill it, the correct response is 406 Not Acceptable. This is why browsers send something like this in their Accept header: Accept: text/html,application/xhtml+xml,application/xml;q=0.9,/;q=0.8 This says "we would prefer one of these formats, but we'll take whatever you got".
- rapala 14y agoThis is exactly the reason why even the good standards fail. Instead of writing 10 lines of code to abstract your specific use case, you want it to be the default behavior. How many times have you cursed something like IE for not implementing CSS properly?
- icebraining 14y agoModify Headers[1] lets you easily configure the headers your browser sends: https://addons.mozilla.org/en-US/firefox/addon/modify-headers/ https://addons.mozilla.org/en-US/firefox/addon/modify-header...
- Gigablah 14y agoI was fooling around with Javascript MVC lately, and came across a problem -- let's say I have this URL, "example.com/objects/1". If I open it in the browser, the server returns a barebones HTML page. JS in the page makes a separate ajax call to the same address, the server detects the accept header, returns JSON data, and the page is populated with content. Now I navigate off the page to a different site, and press the back button. Instead of the HTML page, I get the cached JSON response. Now if I change the ajax call to "example.com/objects/1.json" instead, that keeps the URLs separate and the browser won't cache the wrong response. Is there a better way to solve this?
- MatthewPhillips 14y agoThe server needs to respond with a Vary header which tells the user agent (the browser) how to identify what it should cache. [1]https://developer.mozilla.org/en/HTTP/Content_negotiation https://developer.mozilla.org/en/HTTP/Content_negotiation
- Gigablah 14y agoAh, so I should set "Vary: Accept". Thanks, that was a great help.
- e98cuenc 14y agoThe problem I have with Vary headers is that many reverse proxies will just not cache anything with a Vary header. The reason is that if they add the value of the header that "varies" to the key of the cache, now they have to cache under many different keys the same content. Think of all the different "Accept" headers that clients can send you, each one of these will get an entry in your cache. And now add other headers that should also be in "Vary" like "Cookies", "Accept-Language", etc. and your cache will be virtually useless.
- buddydvd 14y agoInteresting. Perhaps, instead of relying on "Vary: Accept" the server should respond with: "Vary: YourCustomHeader". The API client, on the other hand, will include "YourCustomHeader: SomeConstantValue" when making requests to the server. That way, the reverse proxy will only store up to two versions in its cache.
- mikegirouard 14y agoExcellent point. I can't agree more. In the long run, this makes things far more flexible. Also, I might be nitpicking here, but I think the difference between a URL and a URI is that the URL explicitly defines the media type. If that's the case, then the advice would be to use URIs pointing to resources in combination with `Accept` headers.
- icebraining 14y agoAlso, I might be nitpicking here, but I think the difference between a URL and a URI is that the URL explicitly defines the media type. No, no. An URL is an URI. And the URL doesn't define any media-type, those are hacks created frameworks; there's no such thing in the spec.
- j_s 14y agoI think the server-side could easily support both, to keep the purists happy and still be easy to use/work through proxies/caches/etc.
- lucaspiller 14y agoI'm not convinced that versioning media-types is the best way. I agree it is a more correct way as opposed to basically abusing REST, but I think overall putting the version in the URL is better. From the linked answer: > * you break permalinks > * The url changes will spread like a disease through your interface. What do you do with representations that have not changed but point to the representation that has? If you change the url, you break old clients. If you leave the url, your new clients may not work. Putting the version somewhere else in the request doesn't fix this. If you drop support for an old API version it is going to break stuff. It is easier to spot the issue if you return a 404 rather than a 500 or 400 error, or even correct data that breaks the app consuming the API as it is expecting something else. > * Versioning media types is a much more flexible solution. The main issue I have with this is I have had the "pleasure" of working with pretty stupid people implementing clients on my API. They easily get POST and GET requests mixed up, HTTP and HTTPS, whether or not the request should be authenticated. I don't want to add something else to confuse them even more...
- andraz 14y agoexactly! All use of headers in web APIs just makes it harder to understand them by regular developers of API cleints.
- Graphon 14y agoUsing a content-type header instead of .json or .xml (etc) extension in the URL is just another example of this phenomenon. There's a reason people are moving to use dot extensions in URLs - it's easier to adopt and test.
- deleted 14y ago[deleted]
- MatthewPhillips 14y ago> The main issue I have with this is I have had the "pleasure" of working with pretty stupid people implementing clients on my API. They easily get POST and GET requests mixed up, HTTP and HTTPS, whether or not the request should be authenticated. I don't want to add something else to confuse them even more... Where does the madness end? Do you treat everything as though it were GET and stick the real method (and every other request header) in a query parameter? I think it's ok to assume a basic level of understanding of one of the best documented specs in computing.
- anderse 14y agoBeware that proxies sometimes strip the accept header. I know of at least one European ISP that does this for its 3gs users.