我如何编码和解码HTML实体使用JavaScript或JQuery?
var varTitle = "Chris' corner";
我希望它是:
var varTitle = "Chris' corner";
我如何编码和解码HTML实体使用JavaScript或JQuery?
var varTitle = "Chris' corner";
我希望它是:
var varTitle = "Chris' corner";
当前回答
受Robert K的解决方案的启发,这个版本不剥离HTML标记,而且同样安全。
var decode_entities = (function() {
// Remove HTML Entities
var element = document.createElement('div');
function decode_HTML_entities (str) {
if(str && typeof str === 'string') {
// Escape HTML before decoding for HTML Entities
str = escape(str).replace(/%26/g,'&').replace(/%23/g,'#').replace(/%3B/g,';');
element.innerHTML = str;
if(element.innerText){
str = element.innerText;
element.innerText = '';
}else{
// Firefox support
str = element.textContent;
element.textContent = '';
}
}
return unescape(str);
}
return decode_HTML_entities;
})();
其他回答
我不建议使用jQuery代码作为答案。虽然它不会将要解码的字符串插入到页面中,但它确实会创建脚本和HTML元素等内容。这代码比我们需要的多。相反,我建议使用更安全、更优化的函数。
var decodeEntities = (function() {
// this prevents any overhead from creating the object each time
var element = document.createElement('div');
function decodeHTMLEntities (str) {
if(str && typeof str === 'string') {
// strip script/html tags
str = str.replace(/<script[^>]*>([\S\s]*?)<\/script>/gmi, '');
str = str.replace(/<\/?\w(?:[^"'>]|"[^"]*"|'[^']*')*>/gmi, '');
element.innerHTML = str;
str = element.textContent;
element.textContent = '';
}
return str;
}
return decodeHTMLEntities;
})();
http://jsfiddle.net/LYteC/4/
要使用这个函数,只需调用decodeEntities(“&”),它将使用与jQuery版本相同的底层技术——但是没有jQuery的开销,并且在清除输入中的HTML标记之后。请参阅Mike Samuel关于如何过滤HTML标记的公认答案的评论。
这个函数可以很容易地作为jQuery插件使用,只需在您的项目中添加以下行即可。
jQuery.decodeEntities = decodeEntities;
因为@Robert K和@mattcasey都有很好的代码,我想在这里贡献一个CoffeeScript版本,以防将来有人会使用它:
String::unescape = (strict = false) ->
###
# Take escaped text, and return the unescaped version
#
# @param string str | String to be used
# @param bool strict | Stict mode will remove all HTML
#
# Test it here:
# https://jsfiddle.net/tigerhawkvok/t9pn1dn5/
#
# Code: https://gist.github.com/tigerhawkvok/285b8631ed6ebef4446d
###
# Create a dummy element
element = document.createElement("div")
decodeHTMLEntities = (str) ->
if str? and typeof str is "string"
unless strict is true
# escape HTML tags
str = escape(str).replace(/%26/g,'&').replace(/%23/g,'#').replace(/%3B/g,';')
else
str = str.replace(/<script[^>]*>([\S\s]*?)<\/script>/gmi, '')
str = str.replace(/<\/?\w(?:[^"'>]|"[^"]*"|'[^']*')*>/gmi, '')
element.innerHTML = str
if element.innerText
# Do we support innerText?
str = element.innerText
element.innerText = ""
else
# Firefox
str = element.textContent
element.textContent = ""
unescape(str)
# Remove encoded or double-encoded tags
fixHtmlEncodings = (string) ->
string = string.replace(/\&#/mg, '&#') # The rest, for double-encodings
string = string.replace(/\"/mg, '"')
string = string.replace(/\"e;/mg, '"')
string = string.replace(/\_/mg, '_')
string = string.replace(/\'/mg, "'")
string = string.replace(/\"/mg, '"')
string = string.replace(/\>/mg, '>')
string = string.replace(/\</mg, '<')
string
# Run it
tmp = fixHtmlEncodings(this)
decodeHTMLEntities(tmp)
请参阅https://jsfiddle.net/tigerhawkvok/t9pn1dn5/7/或https://gist.github.com/tigerhawkvok/285b8631ed6ebef4446d(包括编译过的JS,可能比这个答案更新了)
向页面中注入不受信任的HTML是危险的,如如何使用jQuery解码HTML实体中所述。
一种替代方法是使用PHP html_entity_decode的纯javascript实现(来自http://phpjs.org/functions/html_entity_decode:424)。这个例子应该是这样的:
var varTitle = html_entity_decode("Chris' corner");
jQuery提供了一种编码和解码html实体的方法。
如果你使用"<div/>"标签,它会删除所有的html。
function htmlDecode(value) {
return $("<div/>").html(value).text();
}
function htmlEncode(value) {
return $('<div/>').text(value).html();
}
如果你使用"<textarea/>"标签,它将保留html标签。
function htmlDecode(value) {
return $("<textarea/>").html(value).text();
}
function htmlEncode(value) {
return $('<textarea/>').text(value).html();
}
受Robert K的解决方案的启发,剥离html标签,防止执行脚本和事件处理程序,如:<img src=fake onerror="prompt(1)" > 在最新的Chrome, FF, IE上测试(应该可以在IE9上工作,但还没有测试)。
var decodeEntities = (function () {
//create a new html document (doesn't execute script tags in child elements)
var doc = document.implementation.createHTMLDocument("");
var element = doc.createElement('div');
function getText(str) {
element.innerHTML = str;
str = element.textContent;
element.textContent = '';
return str;
}
function decodeHTMLEntities(str) {
if (str && typeof str === 'string') {
var x = getText(str);
while (str !== x) {
str = x;
x = getText(x);
}
return x;
}
}
return decodeHTMLEntities;
})();
简单地调用:
decodeEntities('<img src=fake onerror="prompt(1)">');
decodeEntities("<script>alert('aaa!')</script>");