ShadowRoot: setHTML() Methode
Limited availability
This feature is not Baseline because it does not work in some of the most widely-used browsers.
Experimentell: Dies ist eine experimentelle Technologie
Überprüfen Sie die Browser-Kompatibilitätstabelle sorgfältig vor der Verwendung auf produktiven Webseiten.
Die setHTML()-Methode der ShadowRoot-Schnittstelle bietet eine XSS-sichere Methode zum Parsen und Säubern eines HTML-Strings, der dann den bestehenden Baum im Shadow DOM ersetzt.
Die Methode entfernt alle Elemente und Attribute, die als XSS-gefährlich gelten, selbst wenn sie von einem übergebenen Sanierer erlaubt sind. Insbesondere werden die folgenden Elemente immer entfernt: <script>, <frame>, <iframe>, <embed>, <object>, <use> und Event-Handler-Attribute.
Es wird empfohlen (sofern unterstützt), sie als direkten Ersatz für ShadowRoot.innerHTML zu verwenden, wenn ein benutzerdefinierter HTML-String gesetzt wird.
Syntax
setHTML(input)
setHTML(input, options)
Parameter
input-
Ein String, der HTML definiert, das gesäubert und in den Shadow-Root injiziert werden soll.
optionsOptional-
Ein Optionsobjekt mit den folgenden optionalen Parametern:
sanitizer-
Ein
Sanitizer- oderSanitizerConfig-Objekt, das definiert, welche Elemente des Eingangs erlaubt oder entfernt werden, oder der String"default"für die standardmäßige Konfiguration. Die Methode wird jegliche XSS-unsicheren Elemente und Attribute entfernen, selbst wenn sie vom Sanierer erlaubt sind.Beachten Sie, dass ein
Sanitizerim Allgemeinen effizienter als eineSanitizerConfigist, wenn die Konfiguration wiederverwendet werden soll. Wird kein spezifischer Sanierer angegeben, wird die Standard-Sanierer-Konfiguration verwendet.
Rückgabewert
Keiner (undefined).
Ausnahmen
TypeError-
Diese Ausnahme wird ausgelöst, wenn
options.sanitizerein:- nicht normalisiertes
SanitizerConfig(eines, das sowohl "erlaubte" als auch "entfernte" Konfigurationseinstellungen umfasst) übergeben wird. - String, der nicht den Wert
"default"hat. - Wert, der kein
Sanitizer,SanitizerConfigoder String ist.
- nicht normalisiertes
Beschreibung
Die setHTML()-Methode bietet eine XSS-sichere Methode zum Parsen und Säubern eines HTML-Strings und verwendet diesen, um den bestehenden Baum im Shadow DOM zu ersetzen.
setHTML() entfernt alle HTML-Entitäten, die nicht durch die Saniererkonfiguration zugelassen sind, und entfernt weiter alle XSS-gefährlichen Elemente oder Attribute — unabhängig davon, ob sie durch die Saniererkonfiguration erlaubt sind oder nicht.
Wenn keine Saniererkonfiguration im Parameter options.sanitizer angegeben ist, wird setHTML() mit der Standard-Sanitizer-Konfiguration verwendet. Diese Konfiguration erlaubt alle Elemente und Attribute, die als XSS-sicher gelten, und verbietet dadurch Entitäten, die als unsicher gelten; siehe den Sanitizer()-Konstruktor für weitere Informationen. Ein benutzerdefinierter Sanierer oder eine Saniererkonfiguration kann angegeben werden, um auszuwählen, welche Elemente, Attribute und Kommentare erlaubt oder entfernt werden sollen. Beachten Sie, dass selbst wenn unsichere Optionen durch die Saniererkonfiguration erlaubt sind, sie bei der Verwendung dieser Methode (die implizit Sanitizer.removeUnsafe() aufruft) weiterhin entfernt werden.
setHTML() sollte anstelle von ShadowRoot.innerHTML verwendet werden, um nicht vertrauenswürdige HTML-Strings in das Shadow DOM einzufügen. Es sollte auch anstelle von ShadowRoot.setHTMLUnsafe() verwendet werden, es sei denn, es besteht ein spezifisches Bedürfnis, unsichere Elemente und Attribute zuzulassen.
Da diese Methode stets Eingabestrings von XSS-gefährlichen Entitäten reinigt, wird sie nicht mithilfe der Trusted Types API gesichert oder validiert.
Beispiele
>Grundlegende Nutzung
Dieses Beispiel zeigt einige der Möglichkeiten, wie Sie setHTML() verwenden können, um einen HTML-String zu säubern und zu injizieren.
Zuerst erstellen wir den ShadowRoot, den wir anvisieren wollen. Dies könnte programmgesteuert mit Element.attachShadow() erstellt werden, aber für dieses Beispiel werden wir den Root deklarativ erstellen.
<div id="host">
<template shadowrootmode="open">
<span>A span element in the shadow DOM</span>
</template>
</div>
Wir können einen Zugriff auf den Shadow Root vom #host-Element wie folgt erhalten:
const shadow = document.querySelector("#host").shadowRoot;
Der folgende Code zeigt, wie wir setHTML() mit einem String und unterschiedlichen Sanierern aufrufen können, um das HTML in den Shadow Root zu filtern und zu injizieren.
// Define unsanitized string of HTML
const unsanitizedString = "abc <script>alert(1)<" + "/script> def";
// setHTML() with default sanitizer
shadow.setHTML(unsanitizedString);
// Define custom Sanitizer and use in setHTML()
// This allows only elements: <div>, <p>, <span> (<script> is unsafe and will be removed)
const sanitizer1 = new Sanitizer({ elements: ["div", "p", "span", "script"] });
shadow.setHTML(unsanitizedString, { sanitizer: sanitizer1 });
// Define custom SanitizerConfig within setHTML()
// This removes elements <div>, <p>, <span>, <script>, and any other unsafe elements/attributes
shadow.setHTML(unsanitizedString, {
sanitizer: { removeElements: ["div", "p", "span", "script"] },
});
setHTML() Live-Beispiel
Dieses Beispiel bietet eine "Live"-Demonstration der Methode, wenn sie mit unterschiedlichen Sanierern aufgerufen wird. Der Code definiert Schaltflächen, die Sie anklicken können, um einen HTML-String mit einem Standard- und einem benutzerdefinierten Sanierer zu säubern und zu injizieren. Der Originalstring und das gesäuberte HTML werden protokolliert, damit Sie die Ergebnisse in jedem Fall inspizieren können.
HTML
Das HTML definiert zwei <button>-Elemente für das Anwenden unterschiedlicher Sanierer, eine weitere Schaltfläche zum Zurücksetzen des Beispiels, und ein <div>, das den deklarativen Shadow Root enthält.
<button id="buttonDefault" type="button">Default</button>
<button id="buttonAllowScript" type="button">allowScript</button>
<button id="reload" type="button">Reload</button>
<div id="host">
<template shadowrootmode="open">
<span>I am in the shadow DOM </span>
</template>
</div>
JavaScript
Zuerst definieren wir die Steuerung für die Neustarttaste.
const reload = document.querySelector("#reload");
reload.addEventListener("click", () => document.location.reload());
Dann definieren wir den zu säubernden String, der für alle Fälle derselbe sein wird. Dieser enthält das <script>-Element und den onclick-Handler, die beide als XSS-gefährlich angesehen werden. Wir holen auch die Variable shadow, die unser Zugriffspunkt auf den Shadow Root ist.
// Define unsafe string of HTML
const unsanitizedString = `
<div>
<p>Paragraph to inject into shadow DOM.
<button onclick="alert('You clicked the button!')">Click me</button>
</p>
<script src="path/to/a/module.js" type="module"><\/script>
<p data-id="123">Para with <code>data-</code> attribute</p>
</div>
`;
const shadow = document.querySelector("#host").shadowRoot;
Als nächstes definieren wir den Klick-Handler für die Taste, die den Shadow Root mit dem Standardsanierer setzt. Dies sollte alle unsicheren Entitäten entfernen, bevor der HTML-String eingefügt wird. Beachten Sie, dass Sie genau sehen können, welche Elemente in den Sanitizer()-Konstruktorbeispielen entfernt werden.
const defaultSanitizerButton = document.querySelector("#buttonDefault");
defaultSanitizerButton.addEventListener("click", () => {
// Set the content of the element using the default sanitizer
shadow.setHTML(unsanitizedString);
// Log HTML before sanitization and after being injected
logElement.textContent =
"Default sanitizer: remove script element, onclick attribute, data- attribute\n\n";
log(`\nunsanitized: ${unsanitizedString}`);
log(`\n\nsanitized: ${shadow.innerHTML}`);
});
Der nächste Klick-Handler setzt das Ziel-HTML mithilfe eines benutzerdefinierten Sanierers, der nur <div>, <p> und <script>-Elemente erlaubt. Beachten Sie, dass das <script>-Element auch entfernt wird, da wir die setHTML-Methode verwenden!
const allowScriptButton = document.querySelector("#buttonAllowScript");
allowScriptButton.addEventListener("click", () => {
// Set the content of the element using a custom sanitizer
const sanitizer1 = new Sanitizer({
elements: ["div", "p", "script"],
});
shadow.setHTML(unsanitizedString, { sanitizer: sanitizer1 });
// Log HTML before sanitization and after being injected
logElement.textContent =
"Sanitizer: {elements: ['div', 'p', 'script']}\n Script removed even though allowed\n";
log(`\nunsanitized: ${unsanitizedString}`);
log(`\n\nsanitized: ${shadow.innerHTML}`);
});
Ergebnisse
Klicken Sie auf die Schaltflächen "Default" und "allowScript", um die Effekte des Standard- und benutzerdefinierten Sanierers zu sehen.
Beachten Sie, dass, da wir eine sichere Sanierungsmethode verwenden, in beiden Fällen das <script>-Element und der onclick-Handler entfernt werden, selbst wenn sie explizit durch den Sanierer erlaubt sind. Während das data--Attribut mit dem Standard-Sanierer entfernt wird, ist es erlaubt, wenn wir einen Sanierer übergeben.
Spezifikationen
| Specification |
|---|
| HTML Sanitizer API> # dom-shadowroot-sethtml> |
Browser-Kompatibilität
Loading…