CSRF_COOKIE_HTTPONLY is misleading and not useful

1,192 views
Skip to first unread message

Gavin Wahl

unread,
Apr 17, 2015, 4:23:31 PM4/17/15
to django-d...@googlegroups.com
Ticket #15808 added the CSRF_COOKIE_HTTPONLY setting to set the
HttpOnly attribute on the csrftoken cookie. The HttpOnly attribute is
intended to prevent accessing a cookie through the DOM interface, only
sending it over HTTP. This improves security for session cookies
because it prevents XSS attacks from accessing the session id.

The CSRF token is used through the DOM though, by embedding it in the
HTML of a form, so it's always accesible through JavaScript anyway.
The docs even suggest how to negate the effect of the setting:

> This can help prevent malicious JavaScript from bypassing CSRF protection. If you enable this and need to send the value of the CSRF token with Ajax requests, your JavaScript will need to pull the value from a hidden CSRF token form input on the page instead of from the cookie.

The first sentence isn't actually true. HttpOnly can't prevent
JavaScript from obtaining the csrftoken, because the csrftoken has to
be in the DOM anyway. The second sentence suggests doing something
that completely negates the effect of the setting, so why use it at
all?

I understand that this setting may exist only to satisfy misguided
security scanners and not to actually improve security. If that's the
case, the implication that this setting improves security should be
removed from the docs.

Marc Tamlyn

unread,
Apr 19, 2015, 3:42:14 AM4/19/15
to django-d...@googlegroups.com
I'm not a security expert, but one thing I could suggest is that this setting does mean that only javascript on a page with a POST form can access the CSRF token. Depending on the nature of your site, this could be a significant proportion of pages.


--
You received this message because you are subscribed to the Google Groups "Django developers  (Contributions to Django itself)" group.
To unsubscribe from this group and stop receiving emails from it, send an email to django-develop...@googlegroups.com.
To post to this group, send email to django-d...@googlegroups.com.
Visit this group at http://groups.google.com/group/django-developers.
To view this discussion on the web visit https://groups.google.com/d/msgid/django-developers/CACPudh1Nn-Cz5hJivvTVcfD%3DSSB2E9ZC2s-2mnje88kARKjBfA%40mail.gmail.com.
For more options, visit https://groups.google.com/d/optout.

Collin Anderson

unread,
Apr 19, 2015, 8:05:05 AM4/19/15
to django-d...@googlegroups.com
Though it could still ajax-in the token from a page that does have it, right?

Michał Zieliński

unread,
Apr 19, 2015, 8:54:12 AM4/19/15
to django-d...@googlegroups.com
JavaScript on page without a POST form can load a page with a POST form in iframe (or open in a new window) and access CSRF token inside it. 

Gavin Wahl

unread,
Apr 20, 2015, 12:38:55 AM4/20/15
to django-d...@googlegroups.com
> Though it could still ajax-in the token from a page that does have it, right?

Exactly right.

Florian Apolloner

unread,
May 4, 2015, 7:58:19 AM5/4/15
to django-d...@googlegroups.com
On Monday, April 20, 2015 at 6:38:55 AM UTC+2, Gavin Wahl wrote:
> Though it could still ajax-in the token from a page that does have it, right?

Exactly right.

How so? You cannot just ajax-fetch stuff from different domains. The usual security policies will forbid that. If you already injected javascript onto the victims page (XSS) there is no need to fetch the CSRF token, you already got greater control. If you still think you have a valid attack vector there, please send it to secu...@djangoproject.com and add a bit more explanation.

Thanks & cheers,
Florian

Florian Apolloner

unread,
May 4, 2015, 8:05:53 AM5/4/15
to django-d...@googlegroups.com
On a second thought I think I missread what you wrote and you ment all of this within the scope of one domain and not from the perspective of an attacker.

Gavin Wahl

unread,
May 4, 2015, 12:21:54 PM5/4/15
to django-d...@googlegroups.com
> How so? You cannot just ajax-fetch stuff from different domains.

I'm talking about a single domain. Injected javascript on a page that
doesn't contain the CSRF token can fetch a different page on the same
domain to get it.

> If you already injected javascript onto the victims page (XSS) there is no need to fetch the CSRF token, you already got greater control.

Well, the HttpOnly flag is intended to reduce the damage an attacker
can do once the already can inject javascript. But I agree -- hiding
the CSRF token from javascript doesn't increase security in any way,
but the documentation implies it does. I want to make it clear in the
documentation that this setting has no meaningful effect.

> If you still think you have a valid attack vector there, please send it to secu...@djangoproject.com and add a bit more explanation.

There is no attack vector. This is just about misleading documentation.
> --
> You received this message because you are subscribed to a topic in the
> Google Groups "Django developers (Contributions to Django itself)" group.
> To unsubscribe from this topic, visit
> https://groups.google.com/d/topic/django-developers/nXjfLd8ba5k/unsubscribe.
> To unsubscribe from this group and all its topics, send an email to
> django-develop...@googlegroups.com.
> To post to this group, send email to django-d...@googlegroups.com.
> Visit this group at http://groups.google.com/group/django-developers.
> To view this discussion on the web visit
> https://groups.google.com/d/msgid/django-developers/7609a5bf-65d9-468a-8f64-c5e906cf5920%40googlegroups.com.

Tim Graham

unread,
Nov 28, 2016, 4:38:14 PM11/28/16
to Django developers (Contributions to Django itself)
Meanwhile, there's a ticket [0] asking to expand the documentation of the settings.CSRF_COOKIE_HTTPONLY. If this setting doesn't provide any value, then I figure we should remove the system check that suggests to enable it and deemphasize it in the documentation and/or remove it. Is there consensus on this?

[0] https://code.djangoproject.com/ticket/27534

Alasdair Nicol

unread,
Nov 29, 2016, 5:15:24 AM11/29/16
to Django developers (Contributions to Django itself)
On Monday, 28 November 2016 21:38:14 UTC, Tim Graham wrote:
Meanwhile, there's a ticket [0] asking to expand the documentation of the settings.CSRF_COOKIE_HTTPONLY. If this setting doesn't provide any value, then I figure we should remove the system check that suggests to enable it and deemphasize it in the documentation and/or remove it. Is there consensus on this?
 
If CSRF_COOKIE_HTTPONLY isn't effective, then I'm happy for the system check to be removed and the documentation to be clarified. However, as a user of the setting in the past, I don't think it should be removed. Sometimes the functionality is needed to comply with security reports, regardless of whether or not the setting is effective.

Tim Graham

unread,
Dec 16, 2016, 12:24:35 PM12/16/16
to Django developers (Contributions to Django itself)
I've created a pull request to remove the check and update the docs: https://github.com/django/django/pull/7700
Reply all
Reply to author
Forward
0 new messages