当前位置:  开发笔记 > 程序员 > 正文

如何在RESTful应用程序中阻止CSRF?

如何解决《如何在RESTful应用程序中阻止CSRF?》经验,为你挑选了4个好方法。

通常使用以下方法之一阻止跨站点请求伪造(CSRF):

检查referer - RESTful但不可靠

将令牌插入表单并将令牌存储在服务器会话中 - 而不是真正的RESTful

含糊不清的一次性URI - 由于与令牌相同的原因而不是RESTful

手动为此请求发送密码(不是HTTP身份验证使用的缓存密码) - RESTful但不方便

我的想法是使用用户秘密,一个神秘但静态的表单ID和JavaScript来生成令牌.

...

    GET /usersecret/john_doe 由经过身份验证的用户从JavaScript中获取.

    回复:OK 89070135420357234586534346这个秘密在概念上是静态的,但可以每天/每小时更改......以提高安全性.这是唯一保密的事情.

    使用JavaScript阅读神秘的(但对所有用户都是静态的!)表单id,将其与用户密码一起处理: generateToken(7099879082361234103, 89070135420357234586534346)

    将表单与生成的令牌一起发送到服务器.

    由于服务器知道用户密钥和表单ID,因此可以在发送之前运行与客户端相同的generateToken函数并比较两个结果.只有当两个值相等时,才会授权操作.

这种方法有问题,尽管事实上没有JavaScript它不起作用吗?

附录:

无国籍CSRF保护

Doug.. 26

这里有很多答案,还有很多问题.

你不应该做的事情:

    如果您需要从JavaScript中读取会话令牌,那么您正在做一些可怕的错误.您的会话标识符cookie应始终在其上设置HTTPOnly,因此脚本无法使用它.

    这一保护使得XSS的影响大大减少,因为攻击者将无法再获得登录的用户会话令牌,这对于所有意图和目的而言都等同于应用程序中的凭据.你不希望有一个错误给王国钥匙.

    不应将会话标识符写入页面内容.这与设置HTTPOnly的原因相同.这意味着您的csrf令牌不能是您的会话ID.他们需要不同的价值观.

你应该做的事情:

    遵循OWASP的指导:

    具体来说,如果这是一个REST应用程序,您可以要求提交CSRF令牌的双重提交:

只需创建一些加密随机的东西,将其存储在ASCII Hex或Base64编码中,并在服务器返回页面时将其作为cookie添加到表单中.在服务器端,确保cookie值与表单值匹配.瞧,您已经杀死了CSRF,为您的用户避免了额外的提示,并且没有让自己陷入更多的漏洞.



1> Doug..:

这里有很多答案,还有很多问题.

你不应该做的事情:

    如果您需要从JavaScript中读取会话令牌,那么您正在做一些可怕的错误.您的会话标识符cookie应始终在其上设置HTTPOnly,因此脚本无法使用它.

    这一保护使得XSS的影响大大减少,因为攻击者将无法再获得登录的用户会话令牌,这对于所有意图和目的而言都等同于应用程序中的凭据.你不希望有一个错误给王国钥匙.

    不应将会话标识符写入页面内容.这与设置HTTPOnly的原因相同.这意味着您的csrf令牌不能是您的会话ID.他们需要不同的价值观.

你应该做的事情:

    遵循OWASP的指导:

    具体来说,如果这是一个REST应用程序,您可以要求提交CSRF令牌的双重提交:

只需创建一些加密随机的东西,将其存储在ASCII Hex或Base64编码中,并在服务器返回页面时将其作为cookie添加到表单中.在服务器端,确保cookie值与表单值匹配.瞧,您已经杀死了CSRF,为您的用户避免了额外的提示,并且没有让自己陷入更多的漏洞.


@ghayes我不同意.您的会话令牌比CSRF令牌灵敏得多.使用会话令牌,我可以从我的机器上完全访问应用程序.使用CSRF令牌,我可能会有一个在浏览器中执行的预先编写脚本的敏感操作列表.第二种情况更难以实现,需要了解应用程序,需要更长的时间来执行,并且操作仅限于您事先计划的内容.第一种方案为任何网站提供一行代码,并为攻击者在其计算机上使用Cookie Manager应用程序.

2> antitoxic..:

我是否正确:

您希望通过cookie登录的用户免受CSRF的攻击.

同时,您需要来自应用程序的基本,OAuth和Digest经过身份验证的请求的RESTful接口.

那么,为什么不检查用户是否通过cookie登录仅应用CSRF呢?

我不确定但是其他网站是否有可能伪造像Basic auth或headers这样的东西?

据我所知,CSRF是关于cookie的吗?Cookie不会发生RESTful身份验证.


小心使用基本身份验证 - 它实际上等同于通过cookie登录的用户,因为浏览器将在后续请求中发送提供的Authorization标头,以方便用户.

3> Sripathi Kri..:

您肯定需要服务器上的某些状态来进行身份验证/授权.它不一定是http会话,你可以将它存储在分布式缓存(如memcached)或数据库中.

如果您使用cookie进行身份验证,最简单的解决方案是双重提交cookie值.在提交表单之前,请从cookie中读取会话ID,将其存储在隐藏字段中,然后提交.在服务器端,确认请求中的值与会话ID(您从cookie中获取)相同.来自其他域的邪恶脚本将无法从cookie中读取会话ID,从而阻止了CSRF.

该方案在会话中使用单个标识符.

如果您需要更多保护,请为每个表单生成一个唯一的ID.

另外,不要在JS中生成令牌.任何人都可以复制代码并从其他域运行它来攻击您的站点.


@Sri虽然我同意会话是从安全性和性能各自处理这个问题的最好方法.这不是RESTful,因为它要求服务器跟踪每用户状态,这可能导致可伸缩性问题.

4> Scott Wolcho..:

静态表单ID根本不提供保护; 攻击者可以自己获取它.请记住,攻击者并不局限于在客户端上使用JavaScript; 他可以获取静态表单ID服务器端.

我不确定我完全理解提议的辩护; 它GET /usersecret/john_doe来自哪里?这是JavaScript页面的一部分吗?这是文字提出的URL吗?如果是这样,我假设这username不是秘密,这意味着如果浏览器或插件错误允许跨域GET请求,evil.ru可以恢复用户机密.为什么不在验证时将用户密钥存储在cookie中,而不是让任何可以进行跨域GET的人检索它?

在我实施自己的身份验证系统之前,我会仔细阅读"跨站点伪造的强大防御",我希望能够抵抗CSRF.事实上,我会重新考虑实现我自己的身份验证系统.

推荐阅读
个性2402852463
这个屌丝很懒,什么也没留下!
DevBox开发工具箱 | 专业的在线开发工具网站    京公网安备 11010802040832号  |  京ICP备19059560号-6
Copyright © 1998 - 2020 DevBox.CN. All Rights Reserved devBox.cn 开发工具箱 版权所有