CodeQL 文档

不完整的 HTML 属性清理

ID: js/incomplete-html-attribute-sanitization
Kind: path-problem
Security severity: 6.1
Severity: warning
Precision: high
Tags:
   - security
   - external/cwe/cwe-079
   - external/cwe/cwe-116
   - external/cwe/cwe-020
Query suites:
   - javascript-code-scanning.qls
   - javascript-security-extended.qls
   - javascript-security-and-quality.qls

点击查看 CodeQL 存储库中的查询

清理 HTML 元字符的不可信输入是一种防止跨站点脚本攻击的常见技术。通常,这可以通过转义<>&"来完成。但是,清理后的值的使用上下文决定了需要清理的字符。

因此,某些程序只清理<>,因为它们是最常见的危险字符。当不完全清理的值用作 HTML 属性,并在稍后作为 HTML 解析时,缺少对"的清理会带来问题。

建议

在动态构建 HTML 时清理所有相关的 HTML 元字符,并特别注意清理后的值的使用位置。

更安全的替代方案是设计应用程序,以便无需清理,例如使用明确指定其处理为 HTML 的值的 HTML 模板。

示例

以下示例代码将 HTTP 请求的一部分(由用户控制)写入服务器响应的 HTML 属性。但是,用户控制的值没有对"进行清理。这使得网站容易受到跨站点脚本攻击,因为攻击者可以使用类似" onclick="alert(42)的字符串将 JavaScript 代码注入响应中。

var app = require('express')();

app.get('/user/:id', function(req, res) {
	let id = req.params.id;
	id = id.replace(/<|>/g, ""); // BAD
	let userHtml = `<div data-id="${id}">${getUserName(id) || "Unknown name"}</div>`;
	// ...
	res.send(prefix + userHtml + suffix);
});

清理用户控制的数据以"有助于防止此漏洞

var app = require('express')();

app.get('/user/:id', function(req, res) {
	let id = req.params.id;
	id = id.replace(/<|>|&|"/g, ""); // GOOD
	let userHtml = `<div data-id="${id}">${getUserName(id) || "Unknown name"}</div>`;
	// ...
	res.send(prefix + userHtml + suffix);
});

参考资料

  • ©GitHub, Inc.
  • 条款
  • 隐私