Je souhaite afficher un texte en HTML par une fonction javascript. Comment puis-je échapper les caractères spéciaux html dans JS? Existe-t-il une API?
Je souhaite afficher un texte en HTML par une fonction javascript. Comment puis-je échapper les caractères spéciaux html dans JS? Existe-t-il une API?
Réponses:
function escapeHtml(unsafe) {
return unsafe
.replace(/&/g, "&")
.replace(/</g, "<")
.replace(/>/g, ">")
.replace(/"/g, """)
.replace(/'/g, "'");
}
replace()appels ne sont pas nécessaires. De vieilles chaînes simples à caractère unique feraient aussi bien l'affaire.
function escapeHtml(html){
var text = document.createTextNode(html);
var p = document.createElement('p');
p.appendChild(text);
return p.innerHTML;
}
// Escape while typing & print result
document.querySelector('input').addEventListener('input', e => {
console.clear();
console.log( escapeHtml(e.target.value) );
});
<input style='width:90%; padding:6px;' placeholder='<b>cool</b>'>
Vous pouvez utiliser la .text()fonction de jQuery .
Par exemple:
De la documentation jQuery concernant la .text()fonction:
Nous devons être conscients que cette méthode échappe à la chaîne fournie si nécessaire pour qu'elle s'affiche correctement en HTML. Pour ce faire, il appelle la méthode DOM .createTextNode (), n'interprète pas la chaîne comme HTML.
Les versions précédentes de la documentation jQuery le formulaient de cette façon (nous soulignons ):
Nous devons être conscients que cette méthode échappe à la chaîne fournie si nécessaire pour qu'elle s'affiche correctement en HTML. Pour ce faire, il appelle la méthode DOM .createTextNode (), qui remplace les caractères spéciaux par leurs équivalents d'entité HTML (tels que & lt; for <).
const str = "foo<>'\"&"; $('<div>').text(str).html()rendementsfoo<>'"&
Je pense que j'ai trouvé la bonne façon de le faire ...
// Create a DOM Text node:
var text_node = document.createTextNode(unescaped_text);
// Get the HTML element where you want to insert the text into:
var elem = document.getElementById('msg_span');
// Optional: clear its old contents
//elem.innerHTML = '';
// Append the text node into it:
elem.appendChild(text_node);
document.createTextNode("<script>alert('Attack!')</script>").textContent
Utiliser lodash
_.escape('fred, barney, & pebbles');
// => 'fred, barney, & pebbles'
C'est, de loin, le moyen le plus rapide que je connaisse. De plus, il fait tout sans ajouter, supprimer ou modifier des éléments sur la page.
function escapeHTML(unsafeText) {
let div = document.createElement('div');
div.innerText = unsafeText;
return div.innerHTML;
}
var divCode = '<div data-title="' + escapeHTML('Jerry "Bull" Winston') + '">Div content</div>'obtiendrez un code HTML non valide!
Il était intéressant de trouver une meilleure solution:
var escapeHTML = function(unsafe) {
return unsafe.replace(/[&<"']/g, function(m) {
switch (m) {
case '&':
return '&';
case '<':
return '<';
case '"':
return '"';
default:
return ''';
}
});
};
Je n'analyse pas >car il ne casse pas le code XML / HTML dans le résultat.
Voici les repères: http://jsperf.com/regexpairs
Aussi, j'ai créé une escapefonction universelle : http://jsperf.com/regexpairs2
La façon la plus concise et la plus performante d'afficher du texte non codé est d'utiliser la textContentpropriété.
Plus rapide que l'utilisation innerHTML. Et c'est sans prendre en compte l'échappée des frais généraux.
document.body.textContent = 'a <b> c </b>';
</soit respectée.
Les éléments DOM prennent en charge la conversion de texte en HTML en l'attribuant à innerText . innerText n'est pas une fonction mais son affectation fonctionne comme si le texte était échappé.
document.querySelectorAll('#id')[0].innerText = 'unsafe " String >><>';
<br>éléments à la place des sauts de ligne, qui peuvent casser certains éléments, comme les styles ou les scripts. Le createTextNoden'est pas sujet à ce problème.
innerTexta quelques problèmes hérités / spec. Mieux à utiliser textContent.
Vous pouvez encoder chaque caractère de votre chaîne:
function encode(e){return e.replace(/[^]/g,function(e){return"&#"+e.charCodeAt(0)+";"})}
Ou ciblez simplement les personnages principaux dont vous devez vous soucier (&, inebreaks, <,>, "et ') comme:
function encode(r){
return r.replace(/[\x26\x0A\<>'"]/g,function(r){return"&#"+r.charCodeAt(0)+";"})
}
test.value=encode('How to encode\nonly html tags &<>\'" nice & fast!');
/*************
* \x26 is &ersand (it has to be first),
* \x0A is newline,
*************/
<textarea id=test rows="9" cols="55">www.WHAK.com</textarea>
Une doublure (pour ES6 +):
var escapeHtml = s => (s + '').replace(/[&<>"']/g, m => ({
'&': '&', '<': '<', '>': '>',
'"': '"', "'": '''
})[m]);
Pour les anciennes versions:
function escapeHtml(s) {
return (s + '').replace(/[&<>"']/g, function (m) {
return ({
'&': '&', '<': '<', '>': '>',
'"': '"', "'": '''
})[m];
});
}
Nous avons rencontré ce problème lors de la création d'une structure DOM. Cette question m'a aidé à le résoudre. Je voulais utiliser un double chevron comme séparateur de chemin, mais l'ajout d'un nouveau nœud de texte entraînait directement l'affichage du code de caractère d'échappement, plutôt que le caractère lui-même:
var _div = document.createElement('div');
var _separator = document.createTextNode('»');
//_div.appendChild(_separator); /* this resulted in '»' being displayed */
_div.innerHTML = _separator.textContent; /* this was key */
Si vous utilisez déjà des modules dans votre application, vous pouvez utiliser le module escape-html .
import escapeHtml from 'escape-html';
const unsafeString = '<script>alert("XSS");</script>';
const safeString = escapeHtml(unsafeString);
J'ai trouvé cette solution.
Supposons que nous voulons ajouter du code HTML à l'élément avec des données dangereuses de l'utilisateur ou de la base de données.
var unsafe = 'some unsafe data like <script>alert("oops");</script> here';
var html = '';
html += '<div>';
html += '<p>' + unsafe + '</p>';
html += '</div>';
element.html(html);
Ce n'est pas sûr contre les attaques XSS. Maintenant, ajoutez ceci.
$(document.createElement('div')).html(unsafe).text();
Donc c'est
var unsafe = 'some unsafe data like <script>alert("oops");</script> here';
var html = '';
html += '<div>';
html += '<p>' + $(document.createElement('div')).html(unsafe).text(); + '</p>';
html += '</div>';
element.html(html);
Pour moi, c'est beaucoup plus facile que d'utiliser .replace()et cela supprimera !!! toutes les balises html possibles (j'espère).
<script>en <script>.