【问题标题】:jQuery html() method a security risk like innerHTML?jQuery html() 方法像innerHTML 一样有安全风险?
【发布时间】:2018-03-21 01:44:34
【问题描述】:

我最近在阅读一本 JavaScript 书籍,发现使用 innerHTML 传递纯文本会带来安全风险,所以我想知道使用 html() jQuery 方法会带来同样的风险吗?我试图研究它,但我找不到任何东西。

例如:

$("#saveContact").html("Save"); //change text to Save

var saveContact = document.getElementById("saveContact");
saveContact.innerHTML = "Save"; //change text to Save

据我所知,它们的作用相同,但它们是否都会带来相同的安全风险,即有人能够注入一些 JavaScript 并执行它?

我对安全知识不是很了解,所以如果有任何不正确或解释不正确,我提前道歉。

【问题讨论】:

  • 您应该在使用.html()(和类似功能)之前对内容进行清理。看看我刚刚创建的示例:jsfiddle.net/ayvx4ew9/6。另外,值得一读 thisthis
  • @Raptor 谢谢,因为我在我的网站上一直在使用html()innerHTML 来传递原始字符串,所以我按照建议切换到text()textContent。与链接中所说的相比,这些似乎也略微提高了性能,总是一个加号。

标签: javascript jquery html security


【解决方案1】:

来自JQuery documentation

附加说明:

根据设计,任何 jQuery 构造函数或方法 接受 HTML 字符串 — jQuery()、.append()、.after() 等。 — can 可能执行代码。这可以通过注入脚本标签来实现 或使用执行代码的 HTML 属性(例如 )。 不要使用这些方法插入从 不受信任的来源,例如 URL 查询参数、cookie 或表单 输入。这样做会引入跨站点脚本 (XSS) 漏洞。在添加内容之前删除或转义任何用户输入 到文档。

因此,例如,如果用户要传递一个包含 <script> 元素的 HTML 字符串,那么该脚本将被执行:

$("#input").focus();
$("#input").on("blur", function(){
  $("#output").html($("#input").val());
});
textarea { width:300px; height: 100px; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<textarea id="input"><script>alert("The HTML in this element contains a script element that was processed! What if the script contained malicious content?!")</script></textarea>
<div id="output">Press TAB</div>

但是,如果我们在传递字符串之前将其内容转义,我们会更安全:

$("#input").focus();
$("#input").on("blur", function(){
  $("#output").html($("#input").val().replace("<", "&lt;").replace(">", "&gt;"));
});
textarea { width:300px; height: 100px; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<textarea id="input"><script>alert("This time the < and > characters (which signify an HTML tag are escaped into their HTML entity codes, so they won't be processed as HTML.")</script></textarea>
<div id="output">Press TAB</div>

最后,避免将字符串作为 HTML 处理的最佳方法是首先不要将其传递给 .innerHTML.html() 这就是我们有 .textContent 和 @987654332 的原因@ - 他们为我们逃跑:

$("#input").focus();
$("#input").on("blur", function(){
  // Using .text() escapes the HTML automatically
  $("#output").text($("#input").val());
});
textarea { width:300px; height: 100px; }
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<textarea id="input"><script>alert("This time nothing will be processed as HTML.")</script></textarea>
<div id="output">Press TAB</div>

【讨论】:

  • “在向文档中添加内容之前删除或转义任何用户输入”是什么意思?
  • @Alec 好吧,remove 只是意味着删除 HTML,“escape”意味着提供字符的代码,而不是实际的字符,这样实际的字符就不会被处理。例如&amp;lt;&lt; 的转义码。
【解决方案2】:

来自.html() 文档:

根据设计,任何接受 HTML 字符串的 jQuery 构造函数或方法(jQuery()、.append()、.after() 等)都可能执行代码。这可以通过注入脚本标签或使用执行代码的 HTML 属性(例如, )来实现。不要使用这些方法插入从 URL 查询参数、cookie 或表单输入等不受信任的来源获得的字符串。这样做可能会引入跨站点脚本 (XSS) 漏洞。在向文档添加内容之前删除或转义任何用户输入。

这就是为什么.innerHTML 不好以及为什么.html() 也不适合用于来自不受信任来源的字符串的原因,例如,如果您发出ajax 请求以从不受信任的第三方获取一些数据。您应该使用众多方法中的一种here,或者更好的是,一种经过验证的库函数。

【讨论】:

    猜你喜欢
    • 2011-04-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-06-25
    • 1970-01-01
    相关资源
    最近更新 更多