6 ms·
While this seems like a good solution, I'm not sure the problem is real: to me, a v1 API and a v2 API are two separate APIs, so the URLs for that API aren't rea
by terryjsmith 14y ago
While this seems like a good solution, I'm not sure the problem is real: to me, a v1 API and a v2 API are two separate APIs, so the URLs for that API aren't really changing during it's lifetime (ie. the v1 stuff will stay the same for those continuing to use it). I think this is just a mis-interpretation of a core REST/web principle that the URIs for a specific resource in the API shouldn't change (hence creating a v2 or other sub-directory if you're going to change the output or functionality).
- ldh 14y agoSure, if your URIs are versioned those are by definition not going to change. However, I would stress that the 'R' in URI stands for "Resource", not "particular version of an API to request that resource". It seems like your approach places the implementation details of requesting a resource over the actual identifier for that resource.
- bonzoesc 14y agoIt's useful semantically to think of different versions of a resource as different resources. It makes reasoning about them free of any assumptions the previous versions may have introduced.
- ldh 14y agoI'm not dismissing the idea that resources need to be versioned, certainly a client written against v1 might not be able to handle the v2 representation of the resource. It's just that I think the abstraction the resource is representing generally doesn't change just because the implementation details behind it have. If you change the way a "customerId" is formatted in V2, the idea of providing a "customer" resource hasn't changed, and as a matter of style I think it's cleaner that the URL for the customer record representing a single person doesn't change or suddenly split into multiple resources which really represent one entity. IMO the header-versioned approach expresses the semantic difference you point out cleanly, and in addition does not come with undesirable side-effect of diluting the URI concept.
- candybar 14y agoI don't get this diluting the URI concept. Different versions are often going to have more differences than simply representation. They may provide additional features and have slightly different semantics. It's not the same resource. And even if it were, do you guys propose that if I were to request the same data represented in slightly different ways (say order data grouped by customers or grouped by date) within the same version, I should use headers to distinguish between the two, instead of a query string?
- ldh 14y agoI would say it emphatically is the same resource, in the same way that content negotiation can return you either a JSON or HTML representation of a given resource with the same URL, for example. I don't have a strong opinion on query strings but I would suspect performing various actions on a given resource or collections of resources could be handled just as well with plain URLs: /customers/byDate /customers/byName. To me those represent resources comprised of differing collections of customer resources. I'm not sure there's a substantial difference there.
- candybar 14y agoRight, I didn't mean to introduce query strings as a third option (to me it's part of the URL), but if you think it's okay to have two different URLs for orders by date and orders by customer name, which can be merely differences in representation, not data (each order can still have the full information, representing the same information), why isn't it okay to have two different URLs for two different versions, which may differ in much the same way?
- ldh 14y agoI think you're still conflating resource with representation. I would consider /customers/byDate to be a resource. It happens to be a collection containing references to other resources (customers) which you can then navigate to directly if you want. You can get the byDate collection/resource in varying represenations; JSON, XML, etc. Same with the individual customer resources contained within the collection. Here's a thought experiment. Say you write a client for version 1 of a URL-versioned API. While we're at it, let's encode representation in the URL as well (/api/v1/customers/1.xml, /api/v1/customers/2.json). Say your client stores references to these resources, maybe the user can add them to a list of favorites. Now there's an API upgrade and you point your client to /api/v2/*. Do you just go in with a regex and munge the stored URLs? If you call what you're doing REST, now you're breaking HATEOS. What if the URL scheme changes with the new version? Seems quite likely when the developer already doesn't subscribe to the notion of having a single URL for a resource. What if you want to store a representation-neutral link to a resource and the user can toggle their view between them? Do you make the assumption that you can munge the "extension"? That's a lot of brittle, in-band assumptions to make with URLs which are supposed to be opaque identifiers. Seems more flexible to have separate, well-defined mechanisms for handling this stuff. Disclaimer: I don't have a lot of experience in this area, I'm just arguing for what makes sense to me to explore the ideas. I also acknowledge that plenty of sites use URL-versioned and content-negotiated schemes and have little interest in arguing what's "true REST" but it seems to me that following a stricter interpretation of these concepts does come with some nice benefits.
- optymizer 14y agoOk, therefore: GET / HTTP/1.0 GET / HTTP/1.1 should be GET /v1 GET /v2 and YOU'd have to tell the browser which site uses which version. Wouldn't it be nicer if the browser could tell the server which version of the interface it understands? It happens that the metadatum follows the URI in HTTP requests. The author can't do that, but he can use a header field to achieve the same. Hence the idea to use "Accept:" for versioning.
- zimbatm 14y agoThat's not the same layer. HTTP versioning is on the transport level. All that the author is going to achieve is to have broken client codes every time he's going to bump his API version because most developers won't bother to check the content-type. Or he has control of both the client and server code and then in that case it doesn't matter.
- optymizer 14y agoN.B.: yes it's the same layer. HTTP is at the Application layer in the Internet layer model (and this is the Internet, not your school's Network class where they dream about OSI layers). It's irrelevant which layer this is happening at. The point is that there is a resource address and a resource version. Decoupling those allows you to retain the same resource address for different resource versions - whether this is done for backwards compatibility, multi-language support or other reasons. "All that the author is going to achieve is to have broken client codes every time he's going to bump his API version because most developers won't bother to check the content-type." The point of the article was in fact to teach those mediocre developers who "won't bother", to actually bother to understand these concepts.
- moviewatcher 14y agoHTTP versioning is part of the HTTP protocol which is at the Application Layer in both the Internet Layer Model and the OSI Layer Model. Educate yourself: http://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol http://en.wikipedia.org/wiki/Hypertext_Transfer_Protocol
- 14y ago