使用Django csrf_exempt视图注册Android GCM.最佳实践



在Android GCM(推送通知服务)注册过程中,我的移动客户端必须向Django视图发出POST请求。默认情况下,视图需要csrf_token,但可以使用@csrf_exempt装饰器禁用它。

我的问题是:没有对视图进行csrf检查会有什么后果?如果我从移动客户端(用某种盐)编写一个令牌,这有意义吗?

这实际上取决于视图的性质。

csrf令牌有助于防止在同一台电脑上进行身份验证时调用您不想调用的操作。例如,Django应用程序中存在一个URLhttp://www.example.com/person/delete/356这会在你向其POST时删除ID为356的人。这可能正常,因为它需要身份验证才能启动它。但是,如果你在一个选项卡中登录了Django应用程序,有人向你发送了一封包含链接的钓鱼电子邮件(或类似邮件),该怎么办?"http://www.example.com/person/delete/356"-你点击它,因为你已经在另一个选项卡中进行了身份验证,它就可以工作了。通过让Django期望一个csrf令牌,Django只会对它实际期望的请求进行操作-即Django知道它发出了令牌"12345ab",因此当一个令牌为"345ab"的请求被返回时,如果它丢失了,或者你发送"98765zx"它将失败。点击此处阅读更多关于Django csrf代币的信息,以及维基百科上的跨站点请求伪造信息

如果您没有身份验证,并且视图不执行任何操作(即,它不更改数据,只显示数据),那么生成@csrf_exempt的风险非常低。

同样,如果这种情况发生在移动应用程序内部,并且视图经过了身份验证,那么身份验证将不会像浏览器选项卡那样在应用程序之间共享,因此风险很低。

你也有其他可用的选项,在设置HTTP请求时,如果你能以某种方式获得预期的csrf令牌,那么你就可以设置一个头部,就像在AJAX调用中一样,阅读Django文档这里的

这取决于许多因素,特别是除了注册ID之外,您正在收集什么,以及客户端如何连接到服务器进行POST。

没有CSRF验证的GCM注册的最坏情况

攻击者可以将自己控制的设备注册到受害者的帐户,并接收针对受害者的通知。

根据你正在做的事情,这可能没有那么可怕,尤其是考虑到无论如何,GCM消息不应该包含任何敏感信息,而只是作为在更安全的方法下加载信息的触发器。

(即,如果GCM触发了在客户端设备中加载基于身份验证的新页面的活动,由于攻击者的应用程序不会使用受害者的凭据进行身份验证,因此他们看不到敏感信息)。

这会比其他任何事情都麻烦。

如果你想防范这种情况

  1. 设置Nam提到的令牌——如果您从服务器(即从JavaScript回调)启动GCM注册活动,只需设置客户端需要在注册时传递回的令牌。CSRF请求将与此步骤异步,并且由于缺少令牌而失败。

  2. 如果您的应用程序通过应用程序专有的子域与服务器通信(即在子域级别具有auth cookie的app.site.com),只要应用程序只加载您自己的域(即没有外部网站),并且服务器只允许访问该子域上的注册视图,就很难利用它。浏览器中可能会发生CSRF攻击。

  3. 使用CookieManager从应用程序内的站点cookie中提取CSRF豁免值,并将其作为POST变量添加到请求中。那么您就不需要使视图CSRF豁免。这就是Django处理AJAX CSRF的基本方式。请确保在注册之前使用@ensure_csrf_cookie装饰器,以确保在客户端中设置了CSRF cookie。

结论

老实说,用于GCM注册的CSRF在";让你彻夜难眠的问题;图腾柱。CSRF更多的是账户管理中的一个问题(如更改密码、进行银行交易等)。

最新更新