Using xsrf cookies when all pages are rendered without Tornado

805 views
Skip to first unread message

Chase Lee

unread,
Jan 8, 2012, 9:03:41 PM1/8/12
to python-...@googlegroups.com
Hi,

I'm wondering what the best way would be to use xsrf cookies when Tornado is powering an API, and all actual pages are rendered client-side and served through something like nginx ie no Tornado templates and xsrf_form_html.  

My idea was to provide an API call to trigger the XSRF setting mechanism of Tornado based on the code here: https://github.com/facebook/tornado/blob/master/tornado/web.py#L813

I'm just wondering what an easy way would be to hook into generating an XSRF token like I would a secure user cookie with self.set_secure_cookie.

Much appreciated,
Chase

Ben Darnell

unread,
Jan 9, 2012, 12:43:21 AM1/9/12
to python-...@googlegroups.com
The first question is whether XSRF cookies are even an appropriate
security mechanism for your case. You need XSRF cookies when your
authentication is cookie-based, which it is for traditional web apps,
but generally not for APIs used by non-web clients. Purely
javascript-based apps can go either way. If you are using cookies for
authentication, you'll need to provide the xsrf token either in the
initial page load or as a separate api call. The separate api call
could be a simple as a handler that does
"self.write(dict(xsrf_token=self.xsrf_token))" and then the javascript
would save the value it receives as a cookie named "_xsrf".

-Ben

Chase Lee

unread,
Jan 9, 2012, 1:06:46 AM1/9/12
to python-...@googlegroups.com
Ah, I knew there had to be something simple.  I overlooked that xsrf token gets tacked onto the request handler.  Thanks Ben.

In terms of how I'm using xsrf, I guess I should have explained myself better.  The API works for cookie authentication when cookies are present and uses a custom auth method when they aren't for other clients like an Android app.  So when cookies are present, we use xsrf.  Given I'm moving the front-end out of Tornado templates to be completely client side and served through nginx, we can no longer use {% raw xsrf_form_html %} in conjunction with AJAX requests and will need to feed in the appropriate xsrf value on AJAX posts from now on.  What you wrote should work perfectly.

Thanks again,
Chase

Peter Bengtsson

unread,
Jan 9, 2012, 4:33:21 PM1/9/12
to python-...@googlegroups.com
You can do this:
<script>
var token;
$.getJSON('/xsrf.json', function(r) {
  token = r.token;
});
...

$.post('/api/foo/bar', {'name': 'Chase', '_xsrf': token});
</script>

Chase Lee

unread,
Jan 9, 2012, 5:54:18 PM1/9/12
to python-...@googlegroups.com
Thanks Peter!  That's what I've got going on now, except I store it as a cookie still to persist across pages and browser sessions.
- Chase
Reply all
Reply to author
Forward
0 new messages