Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Django csrf token + Angularjs

I have django running on an apache server using mod_wsgi, as well as an angularjs app served directly by apache, not by django. I would like to make POST calls to the django server (running rest_framework) but I am having problems with the csrf token.

Is there someway to set the token from the server without putting {% csrf token %} as part of the template (since these pages aren't going through django)?

  1. I would like to be able to get a csrf token through a GET request as a cookie.
  2. I would like to be able to then make POST requests to the django server with the csrf token cookie value.
like image 461
Preom Avatar asked Aug 09 '13 22:08

Preom


2 Answers

Django and AngularJS both have CSRF support already, your part is quite simple.

First, you need to enable CSRF in Django, I believe you have already done so, if not, follow Django doc https://docs.djangoproject.com/en/1.5/ref/contrib/csrf/#ajax.

Now, Django will set a cookie named csrftoken on the first GET request and expects a custom HTTP header X-CSRFToken on later POST/PUT/DELETE requests.

For Angular, it expects the cookie named XSRF-TOKEN and will do POST/PUT/DELETE requests with X-XSRF-TOKEN header, so you need to do a little bit tweak to make the two go with each other:

$httpProvider.defaults.xsrfCookieName = 'csrftoken'; $httpProvider.defaults.xsrfHeaderName = 'X-CSRFToken'; 

Add above two lines somewhere in your js code, module.config() block is a good place for this.

That's it.

NOTE: This is for angular 1.1.5, older versions might need different approach.

Update:

Since the angular app isn't served by django, in order to let the cookie to be set, angular app needs to do a GET request to django first.

like image 128
Ye Liu Avatar answered Sep 21 '22 09:09

Ye Liu


var foo = angular.module('foo', ['bar']);  foo.config(['$httpProvider', function($httpProvider) {     $httpProvider.defaults.xsrfCookieName = 'csrftoken';     $httpProvider.defaults.xsrfHeaderName = 'X-CSRFToken'; }]); 

And all modules services and controllers, where $http used, will send requests with csrf token.

like image 34
Nikolay Baluk Avatar answered Sep 18 '22 09:09

Nikolay Baluk