1

我的大部分 GET 请求都是由 Angular 触发的,这使得在 header 中设置 CSRF Token 变得很容易。这对于 POST 请求已经是开箱即用的了,但是我想知道我是否也可以对 GET 请求使用 CSRF 保护。

我最初的直觉是@csrf_protect在 View 的 get 方法之前添加,例如:

class ProjectView(View):
    @csrf_protect
    def get(self, request, *args, **kwargs):
        ...

但是,这会产生错误:

AttributeError at /project
'ProjectView' object has no attribute 'COOKIES'

File "c:\Apps\msysgit\simpletask\lib\site-packages\django\middleware\csrf.py" in process_view
  95.                 request.COOKIES[settings.CSRF_COOKIE_NAME])

所以我猜想POST请求提供了一些GET请求没有提供的东西。有一个更好的方法吗?

此外,在任何人提到所有敏感信息都应该通过 POST 请求提取之前(正如我最近几次看到的那样),我尝试坚持使用 GET 的原因是我正在尝试根据 RESTful 指南构建,这意味着 GET 请求用于提取数据,POST 用于新记录,PUT 用于更新,DELETE 用于数据删除。

编辑

由于似乎有一种情绪我不应该尝试上述方法,虽然我现在有点同意,但我试图阻止的漏洞在以下 3 个链接中讨论:

4

2 回答 2

7

我认为您不太了解 CSRF 实际保护的内容。CSRF 利用网站对用户浏览器的信任;通过利用允许攻击者代表用户运行命令的会话 cookie。

该站点信任该请求,因为它尚未使浏览器的会话 cookie 过期。这就是为什么在大多数 CSRF 缓解技术中,会为每个具有副作用的请求生成唯一的 OTP。攻击者不知道为 OTP 生成的密钥,因此无法伪造合法请求。

对于所有具有副作用的 URL(如 POST、PUT、DELETE),您都需要 CSRF。对于 GET 来说,拥有它没有任何意义,因为 GET 请求——如果你正确地执行 REST——应该是幂等的——如果运行多次,它们会返回相同的结果并且它们不应该有任何副作用。

CSRF 保护并不能防止信息泄露或中间人攻击。因此,如果您有想要保护的敏感信息,请使用 HTTPS。为防止对 API 的不规范使用,请使用身份验证和授权。

于 2013-04-02T04:23:07.333 回答
4

你需要使用method_decorator

https://docs.djangoproject.com/en/1.4/topics/class-based-views/#decorating-the-class

所以你的代码将是

class ProjectView(View):`
    @method_decorator(csrf_protect)
    def get(self, request, *args, **kwargs):

[编辑] 但是csrf_protect只会检查 POST 请求(它有 `if request.method == 'POST' 检查)所以你必须自己实现一些东西。

于 2013-04-02T04:07:19.550 回答