CouchDB Proxy Authentication security - user roles confusion - authentication

On user auth success my auth server generates a token and passes it to the client.
The docs say that the client has to add the following headers:
X-Auth-CouchDB-UserName: username;
X-Auth-CouchDB-Roles:comma-separated (,) list of user roles;
X-Auth-CouchDB-Token: authentication token.
Does it mean that the client defines his own roles on every request? Why can't he add 'admin' into the list of roles then?

A client is anything that uses or requests resources from a server.
"The client" in this case is your proxy/auth server, not a web browser. (The documentation could probably stand to be clarified a bit.)
So yes, your proxy/auth server, the client to CouchDB, should set that header as appropriate.
By extension, it should also not pass through any X-Auth-Couch headers received from its client (presumably a web browser).

Good observation. Using the JWT Authentication would seem to close this loophole as my understanding is the entire token is signed-over.
That said, in neither case can one avoid:
having to fully trust the entity holding the secret
having to carefully guard against leakage of its headers
The former is sort of unavoidable, as the point of these plugins is to delegate authentication. Either you trust the proxy (or JWT issuer) or you leave those authentication_handlers disabled.
The latter is something that e.g. OAuth 1 hardened itself somewhat against, in that ± the entire request was signed over and one couldn't simply take a couple auth headers from an earlier leaked request and slap them on a new forged request. Nonce and timestamp fields were supposed to be checked to avoid verbatim replays of prior requests as well. (All this was dropped in OAuth 2 for whatever that's worth… and even OAuth 1 had some notable loopholes in practice…)
So in practice either the Proxy or the JWT authentication handlers should be used with care. Assuming a "firewall" of sorts drawn around both your CouchDB and authentication source, then as #Flimzy's answer mentions preventing unexpected headers making their way inwards from outside that boundary — as well as keeping the real headers from leaking outwards — should mitigate most potential abuse.

Related

Vue protecting paths from edited localstorage [duplicate]

When building SPA style applications using frameworks like Angular, Ember, React, etc. what do people believe to be some best practices for authentication and session management? I can think of a couple of ways of considering approaching the problem.
Treat it no differently than authentication with a regular web application assuming the API and and UI have the same origin domain.
This would likely involve having a session cookie, server side session storage and probably some session API endpoint that the authenticated web UI can hit to get current user information to help with personalization or possibly even determining roles/abilities on the client side. The server would still enforce rules protecting access to data of course, the UI would just use this information to customize the experience.
Treat it like any third-party client using a public API and authenticate with some sort of token system similar to OAuth. This token mechanism would used by the client UI to authenticate each and every request made to the server API.
I'm not really much of an expert here but #1 seems to be completely sufficient for the vast majority of cases, but I'd really like to hear some more experienced opinions.
This question has been addressed, in a slightly different form, at length, here:
RESTful Authentication
But this addresses it from the server-side. Let's look at this from the client-side. Before we do that, though, there's an important prelude:
Javascript Crypto is Hopeless
Matasano's article on this is famous, but the lessons contained therein are pretty important:
https://www.nccgroup.trust/us/about-us/newsroom-and-events/blog/2011/august/javascript-cryptography-considered-harmful/
To summarize:
A man-in-the-middle attack can trivially replace your crypto code with <script> function hash_algorithm(password){ lol_nope_send_it_to_me_instead(password); }</script>
A man-in-the-middle attack is trivial against a page that serves any resource over a non-SSL connection.
Once you have SSL, you're using real crypto anyways.
And to add a corollary of my own:
A successful XSS attack can result in an attacker executing code on your client's browser, even if you're using SSL - so even if you've got every hatch battened down, your browser crypto can still fail if your attacker finds a way to execute any javascript code on someone else's browser.
This renders a lot of RESTful authentication schemes impossible or silly if you're intending to use a JavaScript client. Let's look!
HTTP Basic Auth
First and foremost, HTTP Basic Auth. The simplest of schemes: simply pass a name and password with every request.
This, of course, absolutely requires SSL, because you're passing a Base64 (reversibly) encoded name and password with every request. Anybody listening on the line could extract username and password trivially. Most of the "Basic Auth is insecure" arguments come from a place of "Basic Auth over HTTP" which is an awful idea.
The browser provides baked-in HTTP Basic Auth support, but it is ugly as sin and you probably shouldn't use it for your app. The alternative, though, is to stash username and password in JavaScript.
This is the most RESTful solution. The server requires no knowledge of state whatsoever and authenticates every individual interaction with the user. Some REST enthusiasts (mostly strawmen) insist that maintaining any sort of state is heresy and will froth at the mouth if you think of any other authentication method. There are theoretical benefits to this sort of standards-compliance - it's supported by Apache out of the box - you could store your objects as files in folders protected by .htaccess files if your heart desired!
The problem? You are caching on the client-side a username and password. This gives evil.ru a better crack at it - even the most basic of XSS vulnerabilities could result in the client beaming his username and password to an evil server. You could try to alleviate this risk by hashing and salting the password, but remember: JavaScript Crypto is Hopeless. You could alleviate this risk by leaving it up to the Browser's Basic Auth support, but.. ugly as sin, as mentioned earlier.
HTTP Digest Auth
Is Digest authentication possible with jQuery?
A more "secure" auth, this is a request/response hash challenge. Except JavaScript Crypto is Hopeless, so it only works over SSL and you still have to cache the username and password on the client side, making it more complicated than HTTP Basic Auth but no more secure.
Query Authentication with Additional Signature Parameters.
Another more "secure" auth, where you encrypt your parameters with nonce and timing data (to protect against repeat and timing attacks) and send the. One of the best examples of this is the OAuth 1.0 protocol, which is, as far as I know, a pretty stonking way to implement authentication on a REST server.
https://www.rfc-editor.org/rfc/rfc5849
Oh, but there aren't any OAuth 1.0 clients for JavaScript. Why?
JavaScript Crypto is Hopeless, remember. JavaScript can't participate in OAuth 1.0 without SSL, and you still have to store the client's username and password locally - which puts this in the same category as Digest Auth - it's more complicated than HTTP Basic Auth but it's no more secure.
Token
The user sends a username and password, and in exchange gets a token that can be used to authenticate requests.
This is marginally more secure than HTTP Basic Auth, because as soon as the username/password transaction is complete you can discard the sensitive data. It's also less RESTful, as tokens constitute "state" and make the server implementation more complicated.
SSL Still
The rub though, is that you still have to send that initial username and password to get a token. Sensitive information still touches your compromisable JavaScript.
To protect your user's credentials, you still need to keep attackers out of your JavaScript, and you still need to send a username and password over the wire. SSL Required.
Token Expiry
It's common to enforce token policies like "hey, when this token has been around too long, discard it and make the user authenticate again." or "I'm pretty sure that the only IP address allowed to use this token is XXX.XXX.XXX.XXX". Many of these policies are pretty good ideas.
Firesheeping
However, using a token Without SSL is still vulnerable to an attack called 'sidejacking': http://codebutler.github.io/firesheep/
The attacker doesn't get your user's credentials, but they can still pretend to be your user, which can be pretty bad.
tl;dr: Sending unencrypted tokens over the wire means that attackers can easily nab those tokens and pretend to be your user. FireSheep is a program that makes this very easy.
A Separate, More Secure Zone
The larger the application that you're running, the harder it is to absolutely ensure that they won't be able to inject some code that changes how you process sensitive data. Do you absolutely trust your CDN? Your advertisers? Your own code base?
Common for credit card details and less common for username and password - some implementers keep 'sensitive data entry' on a separate page from the rest of their application, a page that can be tightly controlled and locked down as best as possible, preferably one that is difficult to phish users with.
Cookie (just means Token)
It is possible (and common) to put the authentication token in a cookie. This doesn't change any of the properties of auth with the token, it's more of a convenience thing. All of the previous arguments still apply.
Session (still just means Token)
Session Auth is just Token authentication, but with a few differences that make it seem like a slightly different thing:
Users start with an unauthenticated token.
The backend maintains a 'state' object that is tied to a user's token.
The token is provided in a cookie.
The application environment abstracts the details away from you.
Aside from that, though, it's no different from Token Auth, really.
This wanders even further from a RESTful implementation - with state objects you're going further and further down the path of plain ol' RPC on a stateful server.
OAuth 2.0
OAuth 2.0 looks at the problem of "How does Software A give Software B access to User X's data without Software B having access to User X's login credentials."
The implementation is very much just a standard way for a user to get a token, and then for a third party service to go "yep, this user and this token match, and you can get some of their data from us now."
Fundamentally, though, OAuth 2.0 is just a token protocol. It exhibits the same properties as other token protocols - you still need SSL to protect those tokens - it just changes up how those tokens are generated.
There are two ways that OAuth 2.0 can help you:
Providing Authentication/Information to Others
Getting Authentication/Information from Others
But when it comes down to it, you're just... using tokens.
Back to your question
So, the question that you're asking is "should I store my token in a cookie and have my environment's automatic session management take care of the details, or should I store my token in Javascript and handle those details myself?"
And the answer is: do whatever makes you happy.
The thing about automatic session management, though, is that there's a lot of magic happening behind the scenes for you. Often it's nicer to be in control of those details yourself.
I am 21 so SSL is yes
The other answer is: Use https for everything or brigands will steal your users' passwords and tokens.
You can increase security in authentication process by using JWT (JSON Web Tokens) and SSL/HTTPS.
The Basic Auth / Session ID can be stolen via:
MITM attack (Man-In-The-Middle) - without SSL/HTTPS
An intruder gaining access to a user's computer
XSS
By using JWT you're encrypting the user's authentication details and storing in the client, and sending it along with every request to the API, where the server/API validates the token. It can't be decrypted/read without the private key (which the server/API stores secretly) Read update.
The new (more secure) flow would be:
Login
User logs in and sends login credentials to API (over SSL/HTTPS)
API receives login credentials
If valid:
Register a new session in the database Read update
Encrypt User ID, Session ID, IP address, timestamp, etc. in a JWT with a private key.
API sends the JWT token back to the client (over SSL/HTTPS)
Client receives the JWT token and stores in localStorage/cookie
Every request to API
User sends a HTTP request to API (over SSL/HTTPS) with the stored JWT token in the HTTP header
API reads HTTP header and decrypts JWT token with its private key
API validates the JWT token, matches the IP address from the HTTP request with the one in the JWT token and checks if session has expired
If valid:
Return response with requested content
If invalid:
Throw exception (403 / 401)
Flag intrusion in the system
Send a warning email to the user.
Updated 30.07.15:
JWT payload/claims can actually be read without the private key (secret) and it's not secure to store it in localStorage. I'm sorry about these false statements. However they seem to be working on a JWE standard (JSON Web Encryption).
I implemented this by storing claims (userID, exp) in a JWT, signed it with a private key (secret) the API/backend only knows about and stored it as a secure HttpOnly cookie on the client. That way it cannot be read via XSS and cannot be manipulated, otherwise the JWT fails signature verification. Also by using a secure HttpOnly cookie, you're making sure that the cookie is sent only via HTTP requests (not accessible to script) and only sent via secure connection (HTTPS).
Updated 17.07.16:
JWTs are by nature stateless. That means they invalidate/expire themselves. By adding the SessionID in the token's claims you're making it stateful, because its validity doesn't now only depend on signature verification and expiry date, it also depends on the session state on the server. However the upside is you can invalidate tokens/sessions easily, which you couldn't before with stateless JWTs.
I would go for the second, the token system.
Did you know about ember-auth or ember-simple-auth? They both use the token based system, like ember-simple-auth states:
A lightweight and unobtrusive library for implementing token based
authentication in Ember.js applications.
http://ember-simple-auth.simplabs.com
They have session management, and are easy to plug into existing projects too.
There is also an Ember App Kit example version of ember-simple-auth: Working example of ember-app-kit using ember-simple-auth for OAuth2 authentication.

How token based authentication helps in cors, cdn, CSRF , mobile ready?

I was reading articles about token based authentication.
And when I was going through this article "Cookies Vs Tokens", I did not understand the following four points (I have asked my doubts below each of the quoted points)
Cross-domain / CORS: cookies + CORS don't play well across different
domains. A token-based approach allows you to make AJAX calls to any
server, on any domain because you use an HTTP header to transmit the
user information.
Why now there will not be cors problem ? What if someone one from the neighboring tab in the browser steals your token(because in javascript of that domain there is code which can clearly tell where the token is stored and how it is retrieved) and starts making
requests ?
And more over it is said "cookies + cors" . why is it said that cookie and cors don't play well ?
CDN: you can serve all the assets of your app from a CDN (e.g.
javascript, HTML, images, etc.), and your server side is just the API.
Why is this an advantage in token based auth systems ? We were using cdn's even when we were doing cookie based authentication right ?
This was because script tags can call scripts from other domains any way right ?
CSRF: since you are not relying on cookies, you don't need to protect
against cross site requests (e.g. it would not be possible to
your site, generate a POST request and re-use the existing
authentication cookie because there will be none).
What if someone one from the neighboring tab in the browser(from some other domain) steals your token and starts making
requests ? I cannot understand this either.
Mobile ready: when you start working on a native platform (iOS,
Android, Windows 8, etc.) cookies are not ideal when consuming a
secure API (you have to deal with cookie containers). Adopting a
token-based approach simplifies this a lot.
Did not understand it completely . Can someone explain , how?
The linked article is a bit sloppily written and does not properly define and distinguish between the various concepts.
First, you have to define what exactly you mean by "token based". The article does not do that, but it seems it has OAuth 2.0 JWT access tokens with the Bearer Token Usage (http://self-issued.info/docs/draft-ietf-oauth-v2-bearer.html) in mind. This means that:
Bearer access tokens are used. The upside of bearer tokens (as opposed to MAC token usage) is simplicity of usage -- all a client needs to pass to a server is a token. The downside is that whoever gets hold of such a token is considered its rightful owner, so he can do whatever he wants with it.
Tokens are passed in the Authorization HTTP header, following a specific syntax.
Then you have to define what you really mean by "cookie based" authentication -- which again, the article does not do. A cookie, essentially, is just a transport mechanism to pass data back and forth between client and servers of a specific domain, without the client having to do anything explicitly. So you can really stuff pretty much anything into a cookie -- even OAuth 2 access tokens.
What the author seems to have in mind is server side-managed sessions where a session id is passed in a cookie.
With these definitions in mind, it is possible to answer your questions:
Cross-domain / CORS: cookies + CORS don't play well across different domains. A token-based approach allows you to make AJAX calls to any server, on any domain because you use an HTTP header to transmit the user information.
This is true, but for different reasons: Cookies are scoped to a specific domain, so as long as you use cookies to pass a session id between clients and servers, you are bound to having to put all servers under one domain. This looks like a limitation, but the true limitation is somewhere else -- when using server side-managed sessions, a session id will only make sense to those servers who have access to the server side session management. Any server outside the domain most likely cannot make any sense of a session id.
A JWT access token, however, is self contained and can be interpreted by other parties as well. This is why access tokens are well suited for cross-domain/cross-service calls.
CDN: you can serve all the assets of your app from a CDN (e.g. javascript, HTML, images, etc.), and your server side is just the API.
Yes. But this does not really matter in practice because anyting you put into a CDN will most likely not require authentication in the first place -- so this is kind of a silly argument.
CSRF: since you are not relying on cookies, you don't need to protect against cross site requests (e.g. it would not be possible to your site, generate a POST request and re-use the existing authentication cookie because there will be none).
The danger of cookies w.r.t. CSRF is that they are passed implicitly to the server -- the browser adds a cookie to the request, regardless of whether it was good of rogue code that triggered the request.
When tokens are passed in a cookie, this danger applies to tokens we well. However, when they are passed in a header (as the Bearer Token Usage spec defines), this danger does not exist as the header needs to be added to teh request explicitly, every single time. This makes this approach more CSRF-safe than cookies.
However, when the rogue code can get hold of the token some other way (because it was passed as a URL parameter, for example (which the spec allows), it is still possible to make CSRF attacks with tokens.
Mobile ready: when you start working on a native platform (iOS, Android, Windows 8, etc.) cookies are not ideal when consuming a secure API (you have to deal with cookie containers). Adopting a token-based approach simplifies this a lot.
Dealing with cookie containers is usually easier than setting up OAuth, so I do not buy into this one.
Alright, I'll try to go through these in as structured a way as possible:
CORS + Cookies: Cookies were never meant to travel across domains. A cookie must be submitted to the server from its origin, cross-origin cookies don't exist. There is no need to worry about another application accessing the token if it's stored in localstorage since that one is site-specific, e.g every site gets it own allotted space of localstorage.
I'm not certain about this one. I'd assume they mean an authenticated CDN, e.g you provide a token to get access to the resources
Again, the token won't be stolen by a neighbour, because of how localstorage works. If you're worried you could actually issue a new token from the server with every response, effectively making one-time use tokens. That way, even if your token is compromised, it is far less likely to work.
Cookies are fairly complex structures, and if you one day decide you want to consume your API on a mobile device, it will be much easier to use a token, which is just a string (compared to a structured object)
The most important difference is that tokens are stateless, while cookies are not. Cookies will contain information about the authenticated user and context-specific data. A token, on the other hand, is just a string that an API consumer assumes can be used to access restricted data.

Authentication security concerns

I am a beginner web-developer and I have some doubts about the security of an API that I developed. It's a simple web-service that requires authentication in order to access/modify data.
I am wondering what are the best practices for authenticating users via HTTP.
Currently my app works like this:
User authenticates through an API request (POST) which requires the username and the password. The response contains info about the user and a TOKEN which will be used in the future for further requests.
My concerns: I don't know if the auth request should be POST. It sounds more like a GET, because POST should create something (at least this is the convention in Ruby on Rails). And then, even with POST or GET, the information is still "visible" during the transfer of the information. I heard something about HTTPS - how does that solves the problem?
The token is generated at user creation time - and remains the same in time. Is this bad? Should the token be generated again after a "logout"? I've seen APIs that use an API_KEY along a token for authentication. How does that work?
I have some GET requests to retrieve information about something. With this request I pass as an parameter the token retrieved from the authentication request. Is this ok? I mean that token is sensitive information.
Where can I find more information about these concerns of mine (book, article, w/e)?
HTTPs encrypts all traffic to your web site, and so would hide any get and post requests. It requires you to purchase an HTTPS certificate (which are cheap), and get a non-shared IP to host on (not so cheap). (If anyone talks about self signed certificates - well, it's possible, but ill advised if external people want to talk to your service).
Having a long lasting login token can be bad, it depends what sort of non-repudiation you want. If someone can log in 2 years ago, and continue using a token how do you know it's still the original requestor? Tokens should expire and have a way to re-request.
API keys generally work on a shared secret which is swapped out of band (by getting it from the hoster's web site generally). A custom authentication scheme and header is used, and must be calculated and checked for each request. This doesn't require HTTPS - the shared secret is used to generate the authentication header, but isn't sent with it, so the secret doesn't travel with each request. Of course you need to write this code, and figure out what you want the process to be. I'd generally avoid this unless you know what you're doing - you need to take a canonical representation of the request, sign it, then use that as the header. It's not complicated, but it's not simple either.
The problem with GET is more one of physical security than web security - I know that I log into sites regularly at work or at home in the company of others - I certainly don't want my credentials appended to the URL as a query string.
Using HTTPS (SSL) will secure your postdata as the information is encrypted before it is sent over the line. The encryption algortihm uses some quite clever maths in generating its decryption tokens to ensure that it's not susceptible to a man-in-the-middle attack.

REST API Token-based Authentication

I'm developing a REST API that requires authentication. Because the authentication itself occurs via an external webservice over HTTP, I reasoned that we would dispense tokens to avoid repeatedly calling the authentication service. Which brings me neatly to my first question:
Is this really any better than just requiring clients to use HTTP Basic Auth on each request and caching calls to the authentication service server-side?
The Basic Auth solution has the advantage of not requiring a full round-trip to the server before requests for content can begin. Tokens can potentially be more flexible in scope (i.e. only grant rights to particular resources or actions), but that seems more appropriate to the OAuth context than my simpler use case.
Currently tokens are acquired like this:
curl -X POST localhost/token --data "api_key=81169d80...
&verifier=2f5ae51a...
&timestamp=1234567
&user=foo
&pass=bar"
The api_key, timestamp and verifier are required by all requests. The "verifier" is returned by:
sha1(timestamp + api_key + shared_secret)
My intention is to only allow calls from known parties, and to prevent calls from being reused verbatim.
Is this good enough? Underkill? Overkill?
With a token in hand, clients can acquire resources:
curl localhost/posts?api_key=81169d80...
&verifier=81169d80...
&token=9fUyas64...
&timestamp=1234567
For the simplest call possible, this seems kind of horribly verbose. Considering the shared_secret will wind up being embedded in (at minimum) an iOS application, from which I would assume it can be extracted, is this even offering anything beyond a false sense of security?
Let me seperate up everything and solve approach each problem in isolation:
Authentication
For authentication, baseauth has the advantage that it is a mature solution on the protocol level. This means a lot of "might crop up later" problems are already solved for you. For example, with BaseAuth, user agents know the password is a password so they don't cache it.
Auth server load
If you dispense a token to the user instead of caching the authentication on your server, you are still doing the same thing: Caching authentication information. The only difference is that you are turning the responsibility for the caching to the user. This seems like unnecessary labor for the user with no gains, so I recommend to handle this transparently on your server as you suggested.
Transmission Security
If can use an SSL connection, that's all there is to it, the connection is secure*. To prevent accidental multiple execution, you can filter multiple urls or ask users to include a random component ("nonce") in the URL.
url = username:key#myhost.com/api/call/nonce
If that is not possible, and the transmitted information is not secret, I recommend securing the request with a hash, as you suggested in the token approach. Since the hash provides the security, you could instruct your users to provide the hash as the baseauth password. For improved robustness, I recommend using a random string instead of the timestamp as a "nonce" to prevent replay attacks (two legit requests could be made during the same second). Instead of providing seperate "shared secret" and "api key" fields, you can simply use the api key as shared secret, and then use a salt that doesn't change to prevent rainbow table attacks. The username field seems like a good place to put the nonce too, since it is part of the auth. So now you have a clean call like this:
nonce = generate_secure_password(length: 16);
one_time_key = nonce + '-' + sha1(nonce+salt+shared_key);
url = username:one_time_key#myhost.com/api/call
It is true that this is a bit laborious. This is because you aren't using a protocol level solution (like SSL). So it might be a good idea to provide some kind of SDK to users so at least they don't have to go through it themselves. If you need to do it this way, I find the security level appropriate (just-right-kill).
Secure secret storage
It depends who you are trying to thwart. If you are preventing people with access to the user's phone from using your REST service in the user's name, then it would be a good idea to find some kind of keyring API on the target OS and have the SDK (or the implementor) store the key there. If that's not possible, you can at least make it a bit harder to get the secret by encrypting it, and storing the encrypted data and the encryption key in seperate places.
If you are trying to keep other software vendors from getting your API key to prevent the development of alternate clients, only the encrypt-and-store-seperately approach almost works. This is whitebox crypto, and to date, no one has come up with a truly secure solution to problems of this class. The least you can do is still issue a single key for each user so you can ban abused keys.
(*) EDIT: SSL connections should no longer be considered secure without taking additional steps to verify them.
A pure RESTful API should use the underlying protocol standard features:
For HTTP, the RESTful API should comply with existing HTTP standard headers. Adding a new HTTP header violates the REST principles. Do not re-invent the wheel, use all the standard features in HTTP/1.1 standards - including status response codes, headers, and so on. RESTFul web services should leverage and rely upon the HTTP standards.
RESTful services MUST be STATELESS. Any tricks, such as token based authentication that attempts to remember the state of previous REST requests on the server violates the REST principles. Again, this is a MUST; that is, if you web server saves any request/response context related information on the server in attempt to establish any sort of session on the server, then your web service is NOT Stateless. And if it is NOT stateless it is NOT RESTFul.
Bottom-line: For authentication/authorization purposes you should use HTTP standard authorization header. That is, you should add the HTTP authorization / authentication header in each subsequent request that needs to be authenticated. The REST API should follow the HTTP Authentication Scheme standards.The specifics of how this header should be formatted are defined in the RFC 2616 HTTP 1.1 standards – section 14.8 Authorization of RFC 2616, and in the RFC 2617 HTTP Authentication: Basic and Digest Access Authentication.
I have developed a RESTful service for the Cisco Prime Performance Manager application. Search Google for the REST API document that I wrote for that application for more details about RESTFul API compliance here. In that implementation, I have chosen to use HTTP "Basic" Authorization scheme. - check out version 1.5 or above of that REST API document, and search for authorization in the document.
In the web a stateful protocol is based on having a temporary token that is exchanged between a browser and a server (via cookie header or URI rewriting) on every request. That token is usually created on the server end, and it is a piece of opaque data that has a certain time-to-live, and it has the sole purpose of identifying a specific web user agent. That is, the token is temporary, and becomes a STATE that the web server has to maintain on behalf of a client user agent during the duration of that conversation. Therefore, the communication using a token in this way is STATEFUL. And if the conversation between client and server is STATEFUL it is not RESTful.
The username/password (sent on the Authorization header) is usually persisted on the database with the intent of identifying a user. Sometimes the user could mean another application; however, the username/password is NEVER intended to identify a specific web client user agent. The conversation between a web agent and server based on using the username/password in the Authorization header (following the HTTP Basic Authorization) is STATELESS because the web server front-end is not creating or maintaining any STATE information whatsoever on behalf of a specific web client user agent. And based on my understanding of REST, the protocol states clearly that the conversation between clients and server should be STATELESS. Therefore, if we want to have a true RESTful service we should use username/password (Refer to RFC mentioned in my previous post) in the Authorization header for every single call, NOT a sension kind of token (e.g. Session tokens created in web servers, OAuth tokens created in authorization servers, and so on).
I understand that several called REST providers are using tokens like OAuth1 or OAuth2 accept-tokens to be be passed as "Authorization: Bearer " in HTTP headers. However, it appears to me that using those tokens for RESTful services would violate the true STATELESS meaning that REST embraces; because those tokens are temporary piece of data created/maintained on the server side to identify a specific web client user agent for the valid duration of a that web client/server conversation. Therefore, any service that is using those OAuth1/2 tokens should not be called REST if we want to stick to the TRUE meaning of a STATELESS protocol.
Rubens

REST and authentication variants

I am currently working on a REST library for .net, and I would like to hear some opinions about an open point I have: REST and authentication.
Here is an example of an RESTful interface used with the library:
[RestRoot("/user")]
public interface IUserInterface
{
[RestPut("/")]
void Add(User user);
[RestGet("/")]
int[] List();
[RestGet("/get/{id}")]
User Get(int id);
[RestDelete("/delete/{id}")]
void Delete(int id);
}
The server code then just implements the interface and the clients can obtain the same interface through a factory. Or if the client is not using the library a standard HTTP request also works.
I know that there are the major ways of either using HTTP Basic Auth or sending a token to requests requiring authenticated users.
The first method (HTTP Basic Auth), has the following issues (partly web browser specific):
The password is transmitted with every request - even with SSL this has some kind of "bad feeling".
Since the password is transmitted with a request header, it would be easy for an local attacker to look at the transmitted headers to gain the password.
The password is available in the browsers memory.
No standard way to expire user "sessions".
Login with a browser interrupts the look and feel of a page.
The issues for the second method are more focused on implementation and library use:
Each request URI which needs authentication must have a parameter for the token, which is just very repetitive.
There is a lot more code to write if each method implementation needs to check if a token is valid.
The interface will become less specific e.g. [RestGet("/get/{id}")] vs. [RestGet("/get/{id}/{token}")].
Where to put the token: at the end of the URI? after the root? somewhere else?
My idea was to pass the token as parameter to the URL like http:/server/user/get/1234?token=token_id.
Another possibility would be to send the parameter as an HTTP header, but this would complicate usage with plain HTTP clients I guess.
The token would get passed back to the client as a custom HTTP header ("X-Session-Id") on each request.
This then could be completely abstracted from the interface, and any implementation needing authentication could just ask which user the token (if given) belongs to.
Do you think this would violate REST too much or do you have any better ideas?
I tend to believe that authentication details belong in the header, not the URI. If you rely on a token being placed on the URI, then every URI in your application will need to be encoded to include the token. It would also negatively impact caching. Resources with a token that is constantly changing will no longer be able to be cached. Resource related information belongs in the URI, not application related data such as credentials.
It seems you must be targeting web browsers as a client? If so you could investigate using HTTP Digest access authentication or issuing clients their own SSL certificates to uniquely identify and authenticate them. Also, I don't think that session cookies are necessarily a bad thing. Especially when having to deal with a browser. As long as you isolate the cookie handling code and make the rest of the application not rely on it you would be fine. The key is only store the user's identity in the session, nothing else. Do not abuse server side session state.
If you are targeting clients other than the browser then there are a number of approaches you can take. I've had luck with using Amazon's S3 Authentication mechanism.
This is all very subjective of course. Purity and following REST to the letter can sometimes be impractical. As long as you minimize and isolate such behavior, the core of your application can still be RESTful. I highly recommend RESTful Web Services as a great source of REST information and approaches.
I agree with workmad3, if session life time needs to be maintained you should create a session resource. Post on that resource with user credentials (either basic authentication or credentials in the body content) will return unique session id. Delete on /session/{id} will log out the user.
If you want to control the session expiry time. When creating new session (post on session resource) the server will set a cookie on the response (using standard set-cookie header).
The cookie will contain expiry time. The cookie string should be encrypted on the server, so only the server can open that cookie.
Every consequent request to the server will send the session cookie in the cookie header. (it will be done automatically for you if your client is a browser). The server needs to "renew" the cookie for every request, i.e. create new cookie with new expiry time (extend session's timeout).
Remember to clear the cookie when the user calls delete on the session resource.
If you want your application to be more secured you can store the client IP in the cookie itself, so when a request arrives the server can validate that it was sent from the "original" client. But remember that this solution can be problematic when proxies are involved, because the server might "see" all the requests as coming from the same client.
The rest authentication I've seen treats the sessions as a REST resource for creation, destruction etc. and then the session ID is passed to and fro. The ones I've seen tend to use the session cookie for this as it's the only way to secure it really. If you pass the session id in the URL, you don't have any way of really authenticating it came from the correct client.
Authentication is a tricky problem with REST though, as it requires some form of state to be kept outside the URL which infringes upon REST principles of the URL being all that is required to represent state.