谷歌发布实验性可信类型 API,用于解决跨站点脚本漏洞

阅读数:2358 2019 年 3 月 23 日

谷歌 Chrome 团队发布了实验性可信类API,用以解决 DOM 跨站点脚本(Cross-Site Scripting,简称 XSS)安全漏洞。谷歌的漏洞赏金计划报告说 DOM XSS 是最常见的 XSS 安全变种。

谷歌软件安全工程师 Krzysztof Kotowicz 解释了开发人员在 XSS 方面所面临的挑战:

实践证明,维护无 XSS 的应用程序仍然是个严峻的挑战,尤其是当应用程序很复杂时。尽管防止服务器端 XSS 的解决方法已经是众所周知的,但基于 DOM 的跨站点脚本(DOM XSS)问题却日益严峻。

挑战在于,引入 XSS 十分容易,但难以检测到。

可信类型可以从根源上解决这些 XSS 问题,有助于消除 DOM XSS 漏洞。

可信类型允许开发人员锁定危险的注入池,在默认情况下它们是安全的,而且不能用字符串进行调用。可以通过内容安全策略(Content Security Policy,简称 CSP)HTTP 响应标头 Content-Security-Policy: trusted-types * 来设置可信类型。

这样就避免了 XSS 的常见来源,例如这个来自谷歌的示例:

复制代码
const templateId = location.hash.match(/tplid=([^;&]*)/)[1];
// typeof templateId == "string"
document.head.innerHTML += templateId // Throws a TypeError.

可信类型引入了一个新的全局变量,所以我们可以直接使用这个变量,而不是通过策略来设置:

复制代码
const templatePolicy = TrustedTypes.createPolicy('template', {
createHTML: (templateId) => {
const tpl = templateId;
if (/^[0-9a-z-]$/.test(tpl)) {
return `<link rel="stylesheet" href="./templates/${tpl}/style.css">`;
}
throw new TypeError();
}
});
const html = templatePolicy.createHTML(location.hash.match(/tplid=([^;&]*)/)[1]);
// html instanceof TrustedHTML
document.head.innerHTML += html;

模板策略在创建 HTML 之前会验证传给它的模板 ID 参数。该策略对象将用户定义的 createHTML 函数封装在可信类型对象中 。除了验证 templateId 对修复 XSS 有效外,现在可能引入 DOM XSS 漏洞的代码只有策略代码,从而减少审查代码库中与检测 DOM XSS 安全问题有关的区域。

目前,可信类型包括 HTML、URL、ScriptURL 和 Script。可信类型的 CSP 可能被限制于一个或所有可信类型策略。

开发人员可以在实时网站或 Web 应用程序中尝试可信类型,方法有:注册Trusted Types Origin Trial 、通过命令行
chrome --enable-blink-features=TrustedDOMTypes 在本地安装的 Chrome 中启用该功能、在 Chrome 中打开
chrome://flags/#enable-experimental-web-platform-features。

现在还有可信类型 polyfill,用于在其他浏览器中尝试该功能。polyfill 有两种变体,其中一种只支持 API,包含可信类型的代码库仍然可以在老版本的浏览器中运行;另一种支持基于文档中的 CSP 策略在 DOM 中强制执行类型。这里有一个使用可信类polyfill 的示例。

问题和反馈可以报告给WICG 可信类GitHub 项目,或者在可信类谷歌小组中讨论。欢迎开发者通过WICG 贡献指南对可信类型规范做出贡献。

查看英文原文:Experimental Trusted Types API to Combat Cross-Site Scripting Vulnerabilities