有没有人知道在jQuery中从字符串中轻松转义HTML的方法?我需要能够传递任意字符串并使其正确地转义以在HTML页面中显示(防止JavaScript/HTML注入攻击)。我相信可以扩展jQuery来做到这一点,但是我目前还不了解该框架足够的知识以实现此目标。
有没有人知道在jQuery中从字符串中轻松转义HTML的方法?我需要能够传递任意字符串并使其正确地转义以在HTML页面中显示(防止JavaScript/HTML注入攻击)。我相信可以扩展jQuery来做到这一点,但是我目前还不了解该框架足够的知识以实现此目标。
var entityMap = {
'&': '&',
'<': '<',
'>': '>',
'"': '"',
"'": ''',
'/': '/',
'`': '`',
'=': '='
};
function escapeHtml (string) {
return String(string).replace(/[&<>"'`=\/]/g, function (s) {
return entityMap[s];
});
}
&
,除非它后面跟着 (1-8个字母后面跟着0-2个数字或者 #
后面跟着一个1-4位的十进制或十六进制数字) 再跟着 ;
。
模式:/([<>"'`=\/]|&(?!([a-zA-Z]{1,8}\d{0,2}|#(\d{1,4}|x[a-zA-Z\d]{1,4}));))/g
用法:escapeHtml('"This"	=	a &v3ry; &dumb; quote.')
结果:'"This"	=	a &v3ry; &dumb; quote.'
在 DOM 中:'"This"\t=\ta &v3ry; &dumb; quote.'
页面显示:"This" = a &v3ry; &dumb; quote.
- Travis Bemrose由于您正在使用jQuery,因此您可以直接设置元素的text
属性:
// before:
// <div class="someClass">text</div>
var someHtmlString = "<script>alert('hi!');</script>";
// set a DIV's text:
$("div.someClass").text(someHtmlString);
// after:
// <div class="someClass"><script>alert('hi!');</script></div>
// get the text in a string:
var escaped = $("<div>").text(someHtmlString).html();
// value:
// <script>alert('hi!');</script>
.text()
或.attr()
是安全的,但像示例中那样构建HTML字符串肯定会遇到问题。 - travis$('<div/>').text('This is fun & stuff').html(); // "This is fun & stuff"
来源: http://debuggable.com/posts/encode-html-entities-with-jquery:480f4dd6-13cc-4ce9-8071-4710cbdd56cb
如果您需要对HTML进行转义,我只能想到三个非常必要的字符:
html.replace(/&/g, "&").replace(/</g, "<").replace(/>/g, ">");
根据你的使用情况,你可能还需要做一些像将"
转换为"
之类的事情。如果列表变得足够大,我会使用数组:
var escaped = html;
var findReplace = [[/&/g, "&"], [/</g, "<"], [/>/g, ">"], [/"/g, """]]
for(var item in findReplace)
escaped = escaped.replace(findReplace[item][0], findReplace[item][1]);
encodeURIComponent()
只会将内容进行URL转义,而不是HTML转义。
var
在本地声明item
变量。无论如何,循环数组时不要使用for...in
循环!请改用普通的for
循环。另外,请注意使用encodeURIComponent
而不是escapeURIComponent
。 - Marcel Korpelé
。以下为参考的HTML实体列表:http://www.w3schools.com/tags/ref_entities.asp。 - LoganWolfer使用下划线很容易:
_.escape(string)
Underscore是一个实用程序库,它提供了许多本机js不提供的功能。还有lodash,它与underscore具有相同的API,但被重写为更高效。
_.unescape(string)
。 - qräbnö我写了一个小函数,可以实现以下功能。它只转义"
、&
、<
和>
(但通常这就足够了)。相比之前提出的解决方案,它更加优雅,因为它只使用一个.replace()
来完成所有转换。(编辑2:降低了代码复杂度,使函数变得更小、更简洁。如果您对原始代码感兴趣,请参见本答案结尾。)
function escapeHtml(text) {
'use strict';
return text.replace(/[\"&<>]/g, function (a) {
return { '"': '"', '&': '&', '<': '<', '>': '>' }[a];
});
}
这是纯粹的JavaScript,没有使用jQuery。
/
和 '
针对mklement的评论做出的编辑。
上述函数可以轻松扩展以包括任何字符。要指定更多要转义的字符,只需将它们插入到正则表达式中的字符类中(即在/[...]/g
中)并作为chr
对象的一个条目。(编辑2: 用相同的方式缩短了这个函数。)
function escapeHtml(text) {
'use strict';
return text.replace(/[\"&'\/<>]/g, function (a) {
return {
'"': '"', '&': '&', "'": ''',
'/': '/', '<': '<', '>': '>'
}[a];
});
}
请注意上面使用 '
来代替撇号(也可以使用符号实体 '
,它在 XML 中被定义,但最初并未包含在 HTML 规范中,因此可能不受所有浏览器支持。参见:HTML 字符实体编码的维基百科文章)。我还记得在某处读到过,使用十进制实体比使用十六进制更受广泛支持,但现在似乎找不到这个来源了。(而且几乎没有浏览器不支持十六进制实体的情况。)
注意:将 /
和 '
添加到转义字符列表中并不是特别有用,因为它们在 HTML 中没有任何特殊含义,也不需要被转义。
escapeHtml
函数编辑 2:原始函数使用一个变量(chr
)来存储.replace()
回调所需的对象。该变量还需要一个额外的匿名函数来限定其作用域,使函数(不必要地)变得更大和更复杂。
var escapeHtml = (function () {
'use strict';
var chr = { '"': '"', '&': '&', '<': '<', '>': '>' };
return function (text) {
return text.replace(/[\"&<>]/g, function (a) { return chr[a]; });
};
}());
我还没有测试哪个版本更快。如果您测试了,请随意在此处添加信息和链接。
我意识到我来参加这个派对有点晚了,但我有一个非常简单的解决方案,不需要使用jQuery。
escaped = new Option(unescaped).innerHTML;
编辑:这不会转义引号。唯一需要转义引号的情况是如果内容将被粘贴到HTML字符串内的属性中。很难想象这样做会是一个好的设计。
编辑3:要获得最快的解决方案,请查看Saram上面的答案。这是最短的答案。
这是一个干净、清晰的JavaScript函数。它可以将文本转义,例如将 "a few < many" 转换为 "a few < many"。
function escapeHtmlEntities (str) {
if (typeof jQuery !== 'undefined') {
// Create an empty div to use as a container,
// then put the raw text in and get the HTML
// equivalent out.
return jQuery('<div/>').text(str).html();
}
// No jQuery, so use string replace.
return str
.replace(/&/g, '&')
.replace(/>/g, '>')
.replace(/</g, '<')
.replace(/"/g, '"')
.replace(/'/g, ''');
}
经过最近的测试,我可以推荐最快速且完全跨浏览器兼容的本地JavaScript(DOM)解决方案:fastest和cross browser compatible native javaScript。
function HTMLescape(html){
return document.createElement('div')
.appendChild(document.createTextNode(html))
.parentNode
.innerHTML
}
如果您将其重复多次,可以使用一次准备好的变量完成:
//prepare variables
var DOMtext = document.createTextNode("test");
var DOMnative = document.createElement("span");
DOMnative.appendChild(DOMtext);
//main work for each case
function HTMLescape(html){
DOMtext.nodeValue = html;
return DOMnative.innerHTML
}
var p = document.createElement('p'); p.textContent = html; return p.innerHTML;
- Dan DascalescutextContent
函数仅被Chrome 1+,Firefox 2,IE9,Opera 9.64和Safari 3支持(后两者注明“可能更早”)。因此,它将破坏OP的“完全跨浏览器兼容”的声明。 - zb226p.innerText = html; return p.innerHTML
- Bekim Bacaj_.str.escapeHTML('<div>Blah blah blah</div>')
输出:
'<div>Blah blah blah</div>'