2

My application is running an API authentication that uses tokens rather than cookies.

This leads me to ask a few questions :

  • What is the most secure way to store the token ?

By using random tokens you eliminate the issue of CSRF attacks but on the other side there are no Secure and HTTPOnly flags.

I thought of maybe using some kind of trick using the new ECMAScript Harmony Object.freeze() and Object.seal() features but this seems to be more of a hack than something that would be secure.

  • How should I authenticate WebSocket clients like Socket.io on top of HTTPS ?

Most libraries like Socket.io, ws, Sockjs and Faye don't allow to set custom HTTP headers or it's not compatible with the various fallback protocols like Flash sockets.

One possibility would be to send the token as part of the handshake in the URL's query arguments but I don't really like it because it means that :

1) - Tokens will be shown in logs files that log only the URL

2) - I would have to authenticate first during the handshake and then every time I send data which would mean two separate systems.

That's just on top of my head by thinking a little bit about it. There might be some more underlying issues.

  • Am I just too paranoid and this option is actually secure ?

I could also implement some kind of asymmetric scheme using a public / private key system, but this seems just to error prone / complicated to be a reliable solution.

My final question is more of a consequence of the questions above :

  • Is the trade-off of having random tokens rather than cookies worth it ?

On one side you don't have CSRF attack vulnerabilities but on the other side you have a lot of other cases where the answers (for me at least) doesn't seem to be so clear-cut.

Thank you in advance !

1 Answer 1

1

To store the token:

  • For a traditional (non-Ajax) web app you usually store the token in a hidden form field.

  • For a single page app you usually store the token in a JavaScript variable and include it in the JSON data with each request.

This approach avoids the token being in the URL, and it works with WebSockets.

Most applications use a cookie as the main session ID, and have a second token which is purely to prevent CSRF. You can ditch the cookie and solely use the token, as you suggest, but doing this is not standard practice, so you should only do it if you're sure you know what you're doing.

As you mention, cookies have an HttpOnly option that is not possible with tokens. Although tokens don't have a secure flag as such, that is less important, as you can adjust your code so the token is only ever sent over SSL.

One other thing to be aware of is you can now prevent CSRF without using tokens, primarily using the origin header. However, most sites still use tokens.

You can do normal cookie authentication with WebSockets. This question has some information. I don't know what the CSRF implications of this are.

14
  • 1
    @AwakeZoldiek - do you have a specific application in mind, or is this a general question? If there's a specific app, more details would help. If it's a general question, I doubt you will find anything that is better than cookies. You could use HTML 5 web storage, but there's no strong reason to prefer this over cookies. Your thinking that "cookies are often a security issue" is misguided. Anything can be a security issue if done badly. Cookies are ok in principle, you just need to take care to use them correctly.
    – paj28
    Apr 8, 2014 at 14:25
  • 1
    Saying you eliminate CSRF by not using cookies is like saying you eliminate SQL injection by not using a database, cookies are needed to exploit CSRF but they are not the cause of it. In my opinion you should use both cookies and token, because they are 2 different layers of protection. A cookie will make sure your session is valid and a token will make sure the request was intended by the client. By using only a token, IF somehow your implementation is flawed and an attacker somehow gets a valid token, he could do anything. This is not the case if he has the token but not the session
    – Kotzu
    Apr 8, 2014 at 15:05
  • 1
    @AwakeZoldiek - CSRF protection is not particularly difficult to get right. If you can't get it right, I expect you will have other security problems with your app, such as cross-site scripting. Most major websites do have security issues from time to time, just like Twitter. This is why the standard approach is cookies + anti-CSRF tokens.
    – paj28
    Apr 8, 2014 at 15:08
  • 1
    @AwakeZoldiek - I see nothing wrong in principle with using HTML5 storage as you explain. I think most sites avoid it because it's tricky to implement. Of course, if you are an SPA you can implement easily. But it always worries me when someone wants to reject the standard way of doing things because they have another idea that is "more secure". In your case, I would just put the effort into implementing normal CSRF protection correctly.
    – paj28
    Apr 8, 2014 at 15:11
  • 1
    @AwakeZoldiek - paj28 explained perfectly why the cookies are not the cause of CSRF, what I mean is, if your token is compromised you are giving away both the session and your CSRF protection. If you had both and your session cookie was compromised it would be useless without the token, same way the token is useless without a a cookie session. In other words in theory there is nothing wrong with your implementation but it seems to me its easier to get it wrong than doing it the standard way, in short, I can´t see any gain on doing it your way.
    – Kotzu
    Apr 8, 2014 at 16:38

You must log in to answer this question.

Not the answer you're looking for? Browse other questions tagged .