JQuery - 添加常规 HTML 以及转义 HTML
JQuery - Add regular HTML along with escaped HTML
我将一些数据存储在 firebase 中(可以在客户端中检索),然后,我使用 JQuery 将其添加到 HTML。这很简单 - 我只是将数据添加到 DOM 元素。然而,问题是,这个原始代码很容易受到攻击,所以我需要在将它添加到 HTML 之前正确地转义从数据库中获取的数据。我认为以下代码可以完成这项工作:
function escapeHTML(text) {
var map = {
'&': '&',
'<': '<',
'>': '>',
'"': '"',
"'": '''
};
return text.replace(/[&<>"']/g, function(m) { return map[m]; });
}
$('#element').prepend('<h1>Heading</h1><p>' + escapeHTML(data) + '</p>');
当我测试此代码时,通过使数据的值类似于 <script>alert('This should not work');</script>
,我认为它只会将此文本添加到 <p></p>
标记,而不执行 JS,但它实际上 运行 代码。
我知道使用 $('#element').text()
会为我转义文本,但我不希望所有内容都被转义 - 我仍然想添加 <h1></h1>
和 <p></p>
标签,我只需要转义变量 "data" 。我看到了几篇关于类似主题的 Whosebug 帖子,但其中 none 似乎解决了这个问题 - post 1, post 2, post 3.
你问题中的代码不起作用的原因是因为 Javascript 中的 &
等所有实体在 [=30= 中的 JS 时被解析为它们代表的字符] 被解析。如果将代码放在外部 .js
文件中,它会起作用,因为它不会被解析为 HTML。或者您可以对它们进行双重编码:
var map = {
'&': '&amp;',
'<': '&lt;',
'>': '&gt;',
'"': '&quot;',
"'": '&#039;'
};
但更好的方法是分别创建 <h1>
和 <p>
元素,并使用 jQuery 方法将转义文本放入段落中。
const data = '<scr' + 'ipt>alert("foo");</scr' + 'ipt>';
$("#element").prepend("<h1>Heading</h1>", $("<p>", {text: data}));
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="element"></div>
如果要填写数据属性,同样可以:
$("#element").prepend($("<div>", {
data: {
attr: data,
another: someMoreData
},
text: "hello world"
}));
我将一些数据存储在 firebase 中(可以在客户端中检索),然后,我使用 JQuery 将其添加到 HTML。这很简单 - 我只是将数据添加到 DOM 元素。然而,问题是,这个原始代码很容易受到攻击,所以我需要在将它添加到 HTML 之前正确地转义从数据库中获取的数据。我认为以下代码可以完成这项工作:
function escapeHTML(text) {
var map = {
'&': '&',
'<': '<',
'>': '>',
'"': '"',
"'": '''
};
return text.replace(/[&<>"']/g, function(m) { return map[m]; });
}
$('#element').prepend('<h1>Heading</h1><p>' + escapeHTML(data) + '</p>');
当我测试此代码时,通过使数据的值类似于 <script>alert('This should not work');</script>
,我认为它只会将此文本添加到 <p></p>
标记,而不执行 JS,但它实际上 运行 代码。
我知道使用 $('#element').text()
会为我转义文本,但我不希望所有内容都被转义 - 我仍然想添加 <h1></h1>
和 <p></p>
标签,我只需要转义变量 "data" 。我看到了几篇关于类似主题的 Whosebug 帖子,但其中 none 似乎解决了这个问题 - post 1, post 2, post 3.
你问题中的代码不起作用的原因是因为 Javascript 中的 &
等所有实体在 [=30= 中的 JS 时被解析为它们代表的字符] 被解析。如果将代码放在外部 .js
文件中,它会起作用,因为它不会被解析为 HTML。或者您可以对它们进行双重编码:
var map = {
'&': '&amp;',
'<': '&lt;',
'>': '&gt;',
'"': '&quot;',
"'": '&#039;'
};
但更好的方法是分别创建 <h1>
和 <p>
元素,并使用 jQuery 方法将转义文本放入段落中。
const data = '<scr' + 'ipt>alert("foo");</scr' + 'ipt>';
$("#element").prepend("<h1>Heading</h1>", $("<p>", {text: data}));
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<div id="element"></div>
如果要填写数据属性,同样可以:
$("#element").prepend($("<div>", {
data: {
attr: data,
another: someMoreData
},
text: "hello world"
}));