Tuesday, January 21, 2014

What does RESTful Authentication mean and how does it work. I can't find a good overview on google. My only understanding is that you pass the session key (remeberal) in the URL, but this could be horribly wrong.
Thanks for your input!
share|improve this question
1 
When I google Restful Authentication I find a dozen RoR plugins. I'm assuming those are NOT what you're looking for. If not RoR, then what language? What web server? –  S.Lott Nov 26 '08 at 2:21
 
It won't be horribly wrong if you use HTTPS. The complete HTTP request along with the URL would be encrypted. –  Bharat Khatri Jul 24 '13 at 14:08
1 
@BharatKhatri: Yes it would. I would never pass sensitive information in the URL visible to the user. This information is much more likely to leak for practical purposes. HTTPS can't help for accidental leakage. – Jo So Sep 12 '13 at 9:25
add comment

12 Answers

up vote135down voteaccepted
How to handle authentication in a RESTful Client-Server architecture is a matter of debate.
Commonly, it can be achieved, in the SOA over HTTP world via:
  • HTTP basic auth over HTTPS;
  • Cookies and session management;
  • Query Authentication with additional signature parameters.
You'll have to adapt, or even better mix those techniques, to match your software architecture at best.
Each authentication scheme has its own PROs and CONs, depending on the purpose of your security policy and software architecture.
HTTP basic auth over HTTPS
This first solution, based on the standard HTTPS protocol, is used by most web services.
It's easy to implement, available by default on all browsers, but has some known draw-backs, like the awful authentication window displayed on the Browser, which will persist (there is no LogOut-like feature here), some server-side additional CPU consumption, and the fact that the user-name and password are transmitted (over HTTPS) into the Server (it should be more secure to let the password stay only on the client side, during keyboard entry, and be stored as secure hash on the Server).
Session via Cookies
To be honest, a session managed on the Server is not truly Stateless.
One possibility could be to maintain all data within the cookie content. And, by design, the cookie is handled on the Server side (Client in fact does even not try to interpret this cookie data: it just hands it back to the server on each successive request). But this cookie data is application state data, so the client should manage it, not the server, in a pure Stateless world.
The cookie technique itself is HTTP-linked, so it's not truly RESTful, which should be protocol-independent, IMHO.
Query Authentication
Query Authentication consists in signing each RESTful request via some additional parameters on the URI. See this reference article.
It was defined as such in this article:
All REST queries must be authenticated by signing the query parameters sorted in lower-case, alphabetical order using the private credential as the signing token. Signing should occur before URL encoding the query string.
This technique is perhaps the more compatible with a Stateless architecture, and can also be implemented with a light session management (using in-memory sessions instead of DB persistence).
Server-side data caching can be always available. For instance, in our framework, we cache the responses at the SQL level, not at the URI level. So adding this extra parameter doesn't break the cache mechanism.
It's worth concluding that REST is not only HTTP-based, even if, in practice, it's mostly implemented over HTTP. REST can use other communication layers. So a RESTful authentication is not just a synonym of HTTP authentication, whatever Google answers. It should even not use the HTTP mechanism at all, but shall be abstracted from the communication layer.
See this article for some details about RESTful authentication in a client-server ORM, based on JSON and REST. Since we allow communication not only over HTTP/1.1, but also named pipes or GDI messages (locally), we tried to implement a truly RESTful authentication pattern, and not rely on HTTP specificity (like header or cookies).
share|improve this answer
1 
If you use Cookie as a better replacement for HTTP Basic Auth you can do truly stateless authentication with a method for expiring the authentication and ability to logout. An example implementation could use cookie called Emulated-HTTP-Basic-Auth with similar value to real HTTP Basic Auth and in addition set expire time. Log out can then be implemented with removing that cookie. I'd guess that any client able to support HTTP Basic Auth can also support cookie authentication done this way. –  Mikko Rantalainen Apr 23 '13 at 7:40
1 
@MikkoRantalainen But this cookie will still be managed by the server, as I wrote. It is some kind of stateless, but not "pure" stateless. In all cases, you need JavaScript code dedicated to client login/logout, which is perfectly possible e.g. with HTTP Digest Auth - good idea, but no big benefit, here, to reinvent the wheel. –  Arnaud Bouchez May 3 '13 at 5:15
1 
I would claim that server implements the UI and logic for configuring the header but the header itself is stateless. A client designed for the API could skip using server help for configuring the header and just pass the required information similar to HTTP Basic Auth. My point is that common UAs (browsers) have such a poor implementation of Basic Auth that it cannot be used. A server provided emulation for the same stuff in another header (Cookie) can be used instead. –  Mikko Rantalainen May 3 '13 at 11:00
 
Of course, the server could support accepting both HTTP Basic Auth and Cookie. However, try to never request HTTP Basic Auth from a browser to avoid the bad UI. –  Mikko Rantalainen May 3 '13 at 11:01
1 
show 1 more comment
I really doubt whether the people enthousiastically shouting "HTTP Authentication" ever tried making a browser-based application (instead of a machine-to-machine web service) with REST. (no offense intended - I just don't think they ever faced the complications)
Problems I found with using HTTP Authentication on RESTful services that produce HTML pages to be viewed in a browser are:
  • user typically gets an ugly browser-made login box, which is very user-unfriendly. you cannot add password retrieval, help boxes, etcetera.
  • logging out or logging in under a different name is a problem - browsers will keep sending authentication information to the site until you close the window
  • timeouts are difficult
A very insightful article that tackles these point by point is here, but this results to a lot of browser-specific javascript hackery, workarounds to workarounds, et cetera. As such, it is also not forward-compatible so will require constant maintenance as new browsers are released. I do not consider that clean and clear design, plus I feel it is a lot of extra work and headache just so that I can enthusiastically show my REST-badge to my friends.
I believe cookies are the solution. But wait, cookies are evil, aren't they? No they're not, the way cookies are used often is evil. A cookie itself is just a piece of client-side information, just like the HTTP authentication info that the browser would keep track of while you browse. And this piece of client-side information is sent to the server at every request, again just like the HTTP Authentication info would be. Conceptually, the only difference is that the content of this piece of client-side state can be determined by the server as part of its response.
By making sessions a RESTful resource with just the following rules:
  • session maps a key to a user id (and possibly a last-action-timestamp for timeouts)
  • If a session exists, then that means that the key is valid.
  • Login means POSTing to /sessions, a new key is set as a cookie
  • Logout means DELETEing /sessions/{key} (with overloaded POST, remember, we're a browser and HTML 5 is a long way to go yet)
  • Authentication is done by sending the key as a cookie at every request and checking whether the session exists and is valid
The only difference to HTTP Authentication, now, is that the authentication key is generated by the server and sent to the client who keeps sending it back, instead of the client computing it from the entered credentials.
converter42 adds that when using https (which we should), it is important that the cookie will have its secure flag set, so that authentication info is never sent over a non-secure connection. Great point, hadn't seen it myself.
I feel that this is a sufficient solution that works fine, but I must admit that I'm not enough of a security expert to identify potential holes in this scheme - all I know is that hundreds of non-RESTful web applications use essentially the same login protocol ($_SESSION inphp, HttpSession in Java EE, etc). The cookie header contents is simply used to address a server-side resource, just like an accept-language might be used to access translation resources, etcetera. I feel that it is the same, but maybe others don't? What do you think, guys?
share|improve this answer
6 
This is fine as long as you set the secure flag on the cookie so the client will never transmit it to the server over a non-secure connection. –  converter42 Mar 3 '11 at 17:07
35 
This is a pragmatic answer and the proposed solution works. However, using terms "RESTful" and "session" in the same sentence is just wrong (unless there is also "not" in between ;). In other words: any web service that uses sessions is NOT RESTful (by definition). Don't get me wrong - you can still use this solution (YMMV), but the term "RESTful" can't be used for it. I recommend the O'Reilly book on REST which is very readable and explains the subject in depth. –  johndodo Jul 29 '11 at 6:38 
12 
@skrebbel: pure REST solution would send authentication data each time it requests a resource, which is less than perfect (HTTP Auth does this). Proposed solution works and is better for most use cases, but it is not RESTful. No need for war, I use this solution too. I just don't claim it is RESTful. :) –  johndodo Aug 3 '11 at 14:11
41 
Oh come on, give an example then. What's that other way, that works well? I'd genuinely like to know. HTTP Auth surely isn't, you can't logout without closing the browser and you can't offer decent login UX without lots of browser-specific non-future-compatible JS. I don't care that much about "purely RESTful" vs "almost RESTful" and the whole associated religious debate, but if you say there are several ways, you should spell them out. –  skrebbel Aug 24 '11 at 15:47
8 
A truly RESTful authentication with real world user agents (a.k.a. "browsers") consists of a cookie containing the value of HTTP Authentication. This way the server can provide the UI for entering login and password and the server can force the logout (by deleting the cookie). In addition, instead of responding 401 to require login when authentication is failed, the server must use temporary redirect to login screen and after successful login use temporary redirect back to previous location. Plus the server must embed logout action (POST form) to pretty much every page for logged in users. –  Mikko Rantalainen Feb 7 '12 at 12:15
show 9 more comments
It's certainly not about "session keys" as it is generally used to refer to sessionless authentication which is performed within all of the constraints of REST. Each request is self-describing, carrying enough information to authorize the request on its own without any server-side application state.
The easiest way to approach this is by starting with HTTP's built-in authentication mechanisms in RFC 2617.
share|improve this answer
add comment
First and foremost, a RESTful web service is STATELESS (or in other words, SESSIONLESS). Therefore, a RESTful service does not have and should not have a concept of session or cookies involved. The way to do authentication or authorization in the RESTful service is by using the HTTP Authorization header as defined in the RFC 2616 HTTP specifications. Every single request should contain the HTTP Authorization header, and the request should be sent over an HTTPs (SSL) connection. This is the correct way to do authentication and to verify the authorization of requests in a HTTP RESTful web services. I have implemented a RESTful web service for the Cisco PRIME Performance Manager application at Cisco Systems. And as part of that web service, I have implemented authentication/authorization as well.
Rubens Gomes.

No comments: