Friday, October 31, 2014

Rotate the CSRF token on every request

Hi all,

I am in the process right now of working on a web portal where we want to rotate the csrf token on each request. We intend to have a new token each time for optimal security. I was hoping someone might know more about this than I do because I've run into some difficulties that were not expected. We are using Django 1.5.7. Each request runs through the django.middleware.csrf.py  CsrfViewMIddleware middleware and a middleware we have added which should be rotating the token each time using the rotate_token function from django.middleware.csrf.py. The problem we have observed is that each time the token does rotate but then is reset in the process_view function in CsrfViewMiddleware. I modified the first few lines of CsrfViewMiddleware's process_request function slightly and found the token will now rotate as I had intended for each request.

Modified Code in django.middleware.csrf.py from CsrfViewMiddleware:

   def process_view(self, request, callback, callback_args, callback_kwargs):

        if getattr(request, 'csrf_processing_done', False):
            return None

        csrf_token = request.META['CSRF_COOKIE']     #CSRF_COOKIE is being rotating by our custom middleware
        if csrf_token == None:
            # Generate token and store it in the request, so it's
            # available to the view.
            request.META["CSRF_COOKIE"] = _get_new_csrf_key()


Django's Standard Code:

    def process_view(self, request, callback, callback_args, callback_kwargs):

        if getattr(request, 'csrf_processing_done', False):
            return None

        try:
            csrf_token = _sanitize_token(
                request.COOKIES[settings.CSRF_COOKIE_NAME])
            # Use same token next time
            request.META['CSRF_COOKIE'] = csrf_token
        except KeyError:
            csrf_token = None
            # Generate token and store it in the request, so it's
            # available to the view.
            request.META["CSRF_COOKIE"] = _get_new_csrf_key()


 I think there are a few more things that should be done here like a _sanitize_token call but this is the basic idea. The problem is I can't just modify the Django code because I don't understand the full set of possible side effects.  

Does anyone know:
1. The history of why the Django developers have set up the code in this fashion.
2. Any side effects that should be expected from making a change like the above modified Django code.
3. A way to do this without modifying the Django base code.

Also, it seems like a version of CsrfViewMiddleware that is conducive to rotating on each request would be helpful as part of Django's base code. Is a change like this worth submitting a pull request to the Django repository?

Thanks for any help in advance,
ibrw100000
 

--
You received this message because you are subscribed to the Google Groups "Django users" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-users+unsubscribe@googlegroups.com.
To post to this group, send email to django-users@googlegroups.com.
Visit this group at http://groups.google.com/group/django-users.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-users/4c3234d2-7c2a-4a42-b2b5-fbc4b38567d2%40googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

No comments:

Post a Comment