http://tools.ietf.org/html/draft-ietf-oauth-v2-30#section-10.12 says:
The client MUST implement CSRF protection [...] typically accomplished by requiring any request sent to the redirection URI endpoint to include a value that binds the request to the user-agent's authenticated state (e.g. a hash of the session cookie [...]
It doesn't say much about the implementation, though. It only puts some light on how the CSRF works:
A CSRF attack against the client's redirection URI allows an attacker to inject their own authorization code or access token, which can result in the client using an access token associated with the attacker's protected resources rather than the victim's (e.g. save the victim's bank account information to a protected resource controlled by the attacker)
But use of the word "rather" rather makes the statement worthless.
I am thinking how to implement the "state" in GAE (using Webapp2). It would be easiest starting at how a hacker could use a CSRF against OAuth2. I found only one good article about the matter: http://blog.springsource.org/2011/11/30/10317/
Unfortunately, while this blog post is well written, there's not much info beyond OAuth2 process explained, examples don't work, and I don't know Spring. Still, I found one interesting recommendation there: server connecting to OAuth2 provider, should store "state" as a random session key (e.g. "this_is_the_random_state":"this_doesn't_matter"), not a value under static key (e.g. "state":"random_state_string")
My question is, what's the sane implementation of the "state".
- Should the randomly generated state be hashed or can same value be stored and sent to OAuth2 provider?
- Is there a difference here, if session back-end is secure-cookies or a server-side storage (in GAE Memcache or database)?
- Should state be stored as a key as suggested?
- Should state has validity period, or session (if there is one) lifetime is enough?