如果您的网站依赖于设置 document.domain,则您必须采取行动。
具体变化及原因
从 Chrome 115 开始,网站将无法设置 document.domain
:Chrome 会使 document.domain
不可变。如需跨源通信,您需要使用其他方法,例如 postMessage()
或 Channel Messaging API。
请注意,这项变更将逐步实施。
我们预计其他浏览器最终也会废弃并移除此功能。如需了解详情,请参阅浏览器兼容性部分。
为什么要将 document.domain
设为不可变?
document.domain
旨在获取或设置来源的主机名。许多网站会设置 document.domain
,以允许同网站但跨源网页之间进行通信。
虽然这是一种方便的方法,但会引入安全风险,因为它放宽了同源政策。由于存在 document.domain
安全问题,因此规范发生了变化,警告用户避免使用 document.domain
。
详细说明:为什么要将 document.domain 设为不可变?
document.domain
目前的使用方式
许多网站会设置 document.domain
,以允许同网站但跨源网页之间进行通信。
同属一个网站但不同源的网站具有相同的 eTLD+1,但子网域不同。
下面是 document.domain
到目前为止的用量:
假设 https://parent.example.com
上的某个网页嵌入了 https://video.example.com
中的 iframe 页面。这些网页具有相同的 eTLD+1 (example.com
),但子网域不同。当两个网页的 document.domain
都设置为 'example.com'
时,浏览器会将这两个来源视为同源。
为 https://parent.example.com
设置 document.domain
:
// Confirm the current origin of "parent.example.com"
console.log(document.domain);
// Set the document.domain
document.domain = 'example.com';
console.log(document.domain);
为 https://video.example.com
设置 document.domain
:
// Confirm the current origin of "video.example.com"
console.log(document.domain);
// Set the document.domain
document.domain = 'example.com';
console.log(document.domain);
现在,您可以在 https://parent.example.com
上针对 https://video.example.com
创建跨源 DOM 操作。
网站设置 document.domain
是为了让同一网站上的文档能够更轻松地进行通信。由于此更改放宽了同源政策,因此父页面能够访问 iframe 的文档并遍历 DOM 树,反之亦然。
这是一种方便的方法,但会带来安全风险。
document.domain
的安全问题
由于 document.domain
存在安全问题,因此规范已发生变化,提醒用户避免使用 document.domain
。
例如,当两个网页设置 document.domain
时,它们可以假装自己是同源的。如果这些网页使用的是具有不同子网域的共享托管服务,这一点尤为重要。设置 document.domain
会开放对同一服务托管的所有其他网站的访问权限,这会让攻击者更容易访问您的网站。之所以能这么做,是因为 document.domain
会忽略域名的端口号部分。
如需详细了解设置 document.domain
的安全影响,请参阅 MDN 上的“Document.domain”页面。
浏览器兼容性
- HTML 规范规定应移除此功能。
- Mozilla 认为默认停用
document.domain
值得进行原型设计。 - WebKit 表示,他们对废弃
document.domain
Setter 持中立态度。 - 与其他浏览器供应商的讨论
- WHATWG / HTML 工作组拉取请求(待实验体验)
如何判断我的网站是否受到影响?
如果您的网站受到此变更的影响,Chrome 会在 DevTools 的“问题”面板中向您发出警告,该警告是在 2022 年添加的。请注意开发者工具右上角的黄色标志。
您还可以通过 Lighthouse 已废弃的 API 审核运行您的网站,以查找计划从 Chrome 中移除的所有 API。
如果您已设置 Reporting API,Chrome 会向您发送弃用报告,以便您了解即将发生的弃用。详细了解如何将 Reporting API 与现有报告收集服务搭配使用,或通过构建自己的内部解决方案来使用该 API。
如何查看这项更改的实际效果?
此项变更将从 Chrome 115 开始逐步推出。 如需查看这项变更的实际效果(即使它尚未在您的 Chrome 浏览器中推出),您可以按以下步骤开启该功能:
- 打开
chrome://flags/#origin-agent-cluster-default
- 选择启用。
- 重启 Chrome。
我可以使用哪些替代方案?
最佳方案是完全不修改 document.domain
,例如在同一源上托管网页和所有组成框架。此方法适用于所有浏览器的所有版本。不过,这可能需要对应用进行大量重做,因此还值得考虑继续支持跨源访问的替代方案。
使用 postMessage()
或 Channel Messaging API 而非 document.domain
在大多数用例中,跨源 postMessage()
或 Channel Messaging API 可以替代 document.domain
。
在以下示例中:
https://parent.example.com
请求 iframe 中的https://video.example.com
,以便通过postMessage()
发送消息来操控 DOM。https://video.example.com
会在收到消息后立即操控 DOM,并将成功通知返回给父级。https://parent.example.com
确认成功。
在 https://parent.example.com
上:
// Send a message to https://video.example.com
iframe.postMessage('Request DOM manipulation', 'https://video.example.com');
// Receive messages
iframe.addEventListener('message', (event) => {
// Reject all messages except ones from https://video.example.com
if (event.origin !== 'https://video.example.com') return;
// Filter success messages
if (event.data === 'succeeded') {
// DOM manipulation is succeeded
}
});
在 https://video.example.com
上:
// Receive messages
window.addEventListener('message', (event) => {
// Reject all messages except ones from https://parent.example.com
if (event.origin !== 'https://parent.example.com') return;
// Do a DOM manipulation on https://video.example.com.
// Send a success message to https://parent.example.com
event.source.postMessage('succeeded', event.origin);
});
不妨试用一下,看看效果如何。如果您有特定要求不适用于 postMessage()
或 Channel Messaging API,请通过 Twitter 上的 @ChromiumDev 与我们联系,或在 Stack Overflow 上提出问题并使用 document.domain
标记。
万不得已时,发送 Origin-Agent-Cluster: ?0
标头
如果您有充分的理由继续设置 document.domain
,可以随目标文档一起发送 Origin-Agent-Cluster: ?0
响应标头。
Origin-Agent-Cluster: ?0
Origin-Agent-Cluster
标头会指示浏览器是否应由以源为键的代理集群处理文档。如需详细了解 Origin-Agent-Cluster
,请参阅使用 Origin-Agent-Cluster
标头请求性能隔离。
发送此标头后,即使 document.domain
默认变为不可变,文档仍可继续设置 document.domain
。
所有其他需要执行此行为的文档也需要发送 Origin-Agent-Cluster
(请注意,如果只有一个文档设置了 document.domain
,则不会产生任何影响)。
为企业政策配置 OriginAgentClusterDefaultEnabled
管理员可以选择将 OriginAgentClusterDefaultEnabled
政策配置为 false
,以便在组织中的所有 Chrome 实例上默认设置 document.domain
。如需了解详情,请参阅 Chrome 企业版政策列表和管理功能 | 文档。
资源
Document.domain
- Web API | MDN- 源站隔离和弃用
document.domain
- 弃用
document.domain
。· 问题 564 · w3ctag/design-reviews
致谢
照片由 Finan Akbar 拍摄,选自 Unsplash