为什么CSRF令牌应该在元标签和cookie中



<头部>标签使用<meta>喜欢:

例如:

<meta content="authenticity_token" name="csrf-param" />
<meta content="4sWPhTlJAmt1IcyNq1FCyivsAVhHqjiDCKRXOgOQock=" name="csrf-token" />

我读过关于在cookie中保持CSRF值的概念,但不知道为什么要保持在<头部>标签。

为了防止CSRF,您需要一个与恶意站点不能发送的请求一起提交的值。身份验证cookie是不合适的,因为如果攻击者可以让浏览器向受害者网站发送请求,cookie将自动提交。

例如,通过www.evil.com上包含的JavaScript提交表单,攻击用户在www.example.com:上的会话

<form method="post" action="https://www.example.com/executeAction">
<input type="hidden" name="action" value="deleteAllUsers">
</form>
<script>document.forms[0].submit()</script>

OWASP建议在页面中存储反CRSF令牌,以防止其他网站提交表单,因为www.evil.com无法读取用户会话中的随机令牌,因为同源策略阻止www.evil.com上的JavaScript读取www.example.com的页面内容。

这些令牌可以存储在页面中的任何位置。最常见的情况是,它将在隐藏的表单字段中,但它们也可以存储在HTML5数据属性中。使用meta标签似乎只是另一种存储方式,JavaScript可以将其包含在页面提交的任何表单中。

CSRF令牌通常在表单中作为隐藏表单字段。只有在使用JavaScript的情况下,将它们放在元标记中才有意义。JavaScript可以从元标记中读取令牌,并将它们发布到操作中。

你不想在cookie中放入CSRF令牌,因为无论其来源如何,cookie都会针对从网络浏览器发送到特定网站的每个请求发送。唯一的例外是安全cookie,它们应该遵循同源策略。

这是因为没有什么可以阻止违规网站将数据发布到合法网站,其中可能包括您的身份验证票证和CSRF令牌。想象一下这个场景。。。取自ASP。净

  1. 用户使用表单身份验证登录www.siteA.com
  2. 服务器对用户进行身份验证。来自服务器的响应包括一个身份验证cookie
  3. 用户在不注销的情况下访问恶意网站。此恶意网站包含以下HTML表单:

    <h1>You Are a Winner!</h1>
    <form action="http://siteA.com/api/account" method="post">
    <input type="hidden" name="Transaction" value="withdraw" />
    <input type="hidden" name="Amount" value="1000000" />
    <input type="submit" value="Click Me"/>
    </form>
    

请注意,表单操作发布到易受攻击的站点,而不是恶意站点。这是CSRF的"跨站点"部分。

用户单击提交按钮。浏览器在请求中包含身份验证cookie。该请求与用户的身份验证上下文一起在服务器上运行,并且可以执行任何允许经过身份验证的用户执行的操作

因此,基本上,当siteA.com收到CSRF攻击时,它应该将cookie中的CSRF令牌与元标签中的令牌相匹配。合法请求将包括这两者,但是,伪造攻击将只包括cookie中指定的CSRF令牌。

我能想到的唯一选项是让数据可以从JavaScript访问。当然,只是为了防止cookie仅为http。

最新更新