Django不会为csrftoken cookie设置HttpOnly

在我Django的settings.py中有

SESSION_COOKIE_HTTPONLY = True SECURE_CONTENT_TYPE_NOSNIFF = True SECURE_BROWSER_XSS_FILTER = True X_FRAME_OPTIONS = 'DENY' SESSION_COOKIE_SECURE = True CSRF_COOKIE_SECURE = True SECURE_SSL_REDIRECT = True SECURE_HSTS_SECONDS = 15768000 SECURE_HSTS_INCLUDE_SUBDOMAINS = True SECURE_HSTS_PRELOAD = True SESSION_COOKIE_AGE = 2 * 24 * 3600 

但是https://detectify.com发现这个标志没有设置为csrftoken cookie。 我检查了Chrome告诉我的cookie,如果我理解正确,那么空的HTTP列确认这两个cookie不仅仅是HTTP: 在这里输入图像说明

另外,如果我在chrome的控制台中执行document.cookie ,则会显示csrftoken值。

我想知道为什么会这样。 我有Django在uwsgi和nginx上运行。 nginxconfiguration如下,有问题的网站是https://rodichi.net :

 server { listen 443 ssl http2 default_server; server_name rodichi.net; ssl_certificate /etc/letsencrypt/live/rodichi.net/fullchain.pem; ssl_certificate_key /etc/letsencrypt/live/rodichi.net/privkey.pem; ssl_dhparam /etc/ssl/certs/dhparam.pem; ssl_protocols TLSv1.1 TLSv1.2; ssl_prefer_server_ciphers on; ssl_ciphers "EECDH+AESGCM:EDH+AESGCM:AES256+EECDH:AES256+EDH"; ssl_ecdh_curve secp384r1; ssl_session_cache shared:SSL:10m; ssl_session_tickets off; ssl_stapling on; ssl_stapling_verify on; charset utf-8; ... # location settings follow here 

“`

您只配置了CSRF标记设置为安全(即只通过https请求发送),而不是HttpOnly(即不提供给Javascript)。

查看Django文档,您还需要设置CSRF_COOKIE_HTTPONLY 。 但是文件正确地指出:

将CSRF cookie指定为HttpOnly并不能提供任何实际的保护,因为CSRF只是为了防范跨域攻击。 如果攻击者可以通过JavaScript读取cookie,他们就已经在浏览器所知道的相同域中,所以他们可以做任何他们喜欢的事情。 (XSS比CSRF要大得多。)

虽然这个设置提供了很少的实际好处,但有时候还是需要安全审计员。

这也取决于你如何实施CSRF。 基本上有两种形式的方法:

  1. 为每个表单设置一个隐藏的CSRF字段,并使该字段在每次加载表单时生成一个唯一的值。 因此,如果表单提交包含有效的代码,那么您知道请求来自您的域。 这在服务器端很复杂,因为它需要跟踪有效令牌,也意味着每个表单都必须动态生成以包含随机令牌,但在客户端更容易使用标准形式的请求而不是JavaScript。 对于这种保护,CSRF cookie不是必需的,即使它存在也不被使用。

  2. 另一个方法调用设置一个CSRF cookie,然后让Javascript读取并通过HTTP头(通常是X-CSRF-TOKEN)发送。 来自其他域的CSRF请求将无法访问此CSRF Coo​​kie,因此将无法正确设置标头。 由于Cookie也将在所有请求上发送,所以服务器很容易检查HTTP请求中的cookie是否与请求中设置的头匹配。 这意味着请求来自某个可以访问cookie的地方,这意味着它来自同一个域。 这意味着这不是一个CSRF攻击。 这在服务器端更容易实现(因为不需要保留活动令牌的列表),但在前端需要Javascript并且需要CSRF令牌不是HttpOnly – 正是因为令牌应该被客户端读取使用Javascript!

Django文档再次警告 :

如果您启用此功能并需要通过AJAX请求发送CSRF令牌的值,那么您的JavaScript必须从页面上输入隐藏的CSRF令牌表单中提取值,而不是从Cookie中提取值。

所以,总而言之, 建议为这个cookie设置HttpOnly属性。 它限制了你,没有增加真正的保护,并使cookie本身毫无意义。

你会得到它在你的网站上突出显示和钢笔测试报告(包括https://detectify.com的外观),但应该接受,因为你很自在,这是正确的。 不确定是否可以在https://detectify.com中将这个cookie列入白名单,这样每次都不会提醒?