Dokument: write()-Methode
Deprecated
Avoid using this feature in new projects.
The dynamic markup insertion API, which includes document.write(), has "very idiosyncratic behavior" which can be difficult to debug.
This feature may be a candidate for removal from web standards or browsers.>
Consider using the following features instead: DOM.>
Warnung:
Von der Verwendung der Methode document.write() wird dringend abgeraten.
Vermeiden Sie ihre Verwendung und ersetzen Sie sie nach Möglichkeit auch in vorhandenem Code.
Wie die HTML-Spezifikation selbst warnt:
Diese Methode verhält sich sehr eigenwillig. In manchen Fällen kann sie den Zustand des HTML-Parsers während der Ausführung beeinflussen. Dadurch kann ein DOM entstehen, das nicht dem Quelldokument entspricht (etwa wenn die geschriebene Zeichenfolge „
<plaintext>“ oder „<!--“ lautet). In anderen Fällen kann der Aufruf zunächst die aktuelle Seite leeren, als wäredocument.open()aufgerufen worden. In wieder anderen Fällen wird die Methode einfach ignoriert oder löst eine Ausnahme aus. User Agents ist es ausdrücklich erlaubt, die Ausführung vonscript-Elementen zu verhindern, die mit dieser Methode eingefügt wurden. Erschwerend kommt hinzu, dass das genaue Verhalten dieser Methode in manchen Fällen von der Netzwerklatenz abhängen kann. Das kann zu Fehlern führen, die sich nur schwer debuggen lassen. Aus all diesen Gründen wird von der Verwendung dieser Methode dringend abgeraten.
Warnung: Diese Methode interpretiert ihre Eingabe als HTML und schreibt das Ergebnis in das DOM. APIs wie diese werden als Injection Sinks bezeichnet. Wenn die Eingabe ursprünglich von einem Angreifer stammt, können sie einen Angriffspunkt für Cross-Site-Scripting-Angriffe (XSS) darstellen.
Sie können dieses Risiko verringern, indem Sie stets TrustedHTML-Objekte statt Zeichenfolgen übergeben und Trusted Types erzwingen.
Weitere Informationen finden Sie unter Sicherheitsaspekte.
Die Methode write() des Document-Interfaces schreibt Text aus einem oder mehreren TrustedHTML-Objekten oder Zeichenfolgen in einen Dokumentstream, der mit document.open() geöffnet wurde.
Syntax
write(markup)
write(markup, markup2)
write(markup, markup2, /* …, */ markupN)
Parameter
markup, …,markupN-
TrustedHTML-Objekte oder Zeichenfolgen mit dem Markup, das in das Dokument geschrieben werden soll.
Rückgabewert
Keiner (undefined).
Ausnahmen
InvalidStateErrorDOMException-
Die Methode wurde für ein XML-Dokument aufgerufen oder während der Parser gerade den Konstruktor eines Custom Elements ausführt.
TypeError-
Eine Zeichenfolge wird als Parameter übergeben, während Trusted Types erzwungen werden und keine Standardrichtlinie definiert wurde, um
TrustedHTML-Objekte zu erstellen.
Beschreibung
document.write() verarbeitet den Markup-Text in den übergebenen Objekten in der Reihenfolge der Parameter und fügt ihn in das Objektmodell (DOM) des geöffneten Dokuments ein.
Da document.write() in den Dokumentstream schreibt, führt ein Aufruf von document.write() für ein geschlossenes (geladenes) Dokument automatisch document.open() aus, sofern Sie document.open() nicht zuvor selbst aufgerufen haben. Dadurch wird das Dokument geleert.
Eine Ausnahme gilt, wenn der Aufruf von document.write() in einem Inline-HTML-<script>-Tag steht: In diesem Fall wird document.open() nicht automatisch aufgerufen.
<script>
document.write("<h1>Main title</h1>");
</script>
document.write() (und document.writeln) kann nicht mit XML oder XHTML verwendet werden. Ein entsprechender Versuch löst eine InvalidStateError-Ausnahme aus.
Das gilt beim Öffnen einer lokalen Datei mit der Dateiendung .xhtml sowie für jedes Dokument, das mit dem MIME-Typ application/xhtml+xml ausgeliefert wird.
Weitere Informationen finden Sie in den W3C XHTML FAQ.
Aufrufe von document.write() in verzögert geladenen oder asynchronen Skripten werden ignoriert. In der Fehlerkonsole erscheint dann eine Meldung wie „A call to document.write() from an asynchronously-loaded external script was ignored“.
Nur in Edge führt ein mehrfacher Aufruf von document.write() innerhalb eines <iframe> zum Fehler „SCRIPT70: Permission denied“.
Sicherheitsaspekte
Die Methode kann einen Angriffspunkt für Cross-Site-Scripting-Angriffe (XSS) darstellen, wenn potenziell unsichere, von Benutzern bereitgestellte Zeichenfolgen ohne vorherige Bereinigung in das DOM eingefügt werden.
Auch wenn die Methode in manchen Browsern möglicherweise verhindert, dass eingefügte <script>-Elemente ausgeführt werden (siehe Intervening against document.write() für Chrome), gibt es viele andere Möglichkeiten, HTML so zu gestalten, dass schädliches JavaScript ausgeführt wird.
Sie können diese Risiken verringern, indem Sie stets TrustedHTML-Objekte statt Zeichenfolgen übergeben und Trusted Types mit der CSP-Direktive require-trusted-types-for erzwingen.
So wird sichergestellt, dass die Eingabe eine Transformationsfunktion durchläuft, die sie bereinigen und potenziell gefährliches Markup (etwa <script>-Elemente und Event-Handler-Attribute) entfernen kann, bevor sie eingefügt wird.
Beispiele
>TrustedHTML schreiben
Dieses Beispiel verwendet die Trusted Types API, um <script>-Elemente aus HTML-Zeichenfolgen zu entfernen, bevor diese in ein Dokument geschrieben werden.
Zunächst zeigt das Beispiel einen Standardtext und eine Schaltfläche an.
Wenn Sie auf die Schaltfläche klicken, wird das aktuelle Dokument geöffnet. Drei HTML-Zeichenfolgen werden in TrustedHTML-Instanzen umgewandelt und in das Dokument geschrieben. Anschließend wird das Dokument geschlossen.
Dadurch wird das Dokument im Beispiel-Frame ersetzt – einschließlich des ursprünglichen HTML für die Schaltfläche und des JavaScripts, das die Aktualisierung ausgelöst hat!
HTML
<p>Some original document content.</p>
<button id="replace" type="button">Replace document content</button>
JavaScript
Zuerst greifen wir über die Eigenschaft Window.trustedTypes auf die globale TrustedTypePolicyFactory zu. Mit ihrer Methode createPolicy() definieren wir eine Richtlinie namens "docPolicy".
Die neue Richtlinie definiert eine Transformationsfunktion createHTML(), mit der die TrustedHTML-Objekte erstellt werden, die wir an die Methode write() übergeben.
Diese Methode kann die Eingabezeichenfolge beliebig verarbeiten: Die Trusted Types API verlangt lediglich, dass die Eingabe eine Transformationsfunktion einer Richtlinie durchläuft – nicht, dass diese Funktion eine bestimmte Verarbeitung vornimmt.
Sie würden die Methode verwenden, um die Eingabe zu bereinigen, indem Sie potenziell unsichere Bestandteile wie <script>-Tags oder Event-Handler-Attribute entfernen.
Eine solche Bereinigung korrekt umzusetzen ist schwierig. Deshalb wird dafür üblicherweise eine bewährte Bibliothek eines Drittanbieters wie DOMPurify verwendet.
Zu Demonstrationszwecken implementieren wir hier einen einfachen „Sanitizer“, der <-Zeichen in öffnenden und schließenden Script-Tags durch < ersetzt.
const policy = trustedTypes.createPolicy("docPolicy", {
createHTML(string) {
return string
.replace("<script", "<script")
.replace("</script", "</script");
},
});
Anschließend können wir mit der Methode TrustedTypePolicy.createHTML() der zurückgegebenen Richtlinie aus unseren ursprünglichen Eingabezeichenfolgen TrustedHTML-Objekte erstellen.
Diese werden an die Funktion write() übergeben, wenn Sie auf die Schaltfläche klicken.
const oneInput = "<h1>Out with the old</h1>";
const twoInput = "<p>in with the new!</p>";
const threeInput = "<script>alert('evil afoot')<" + "/script>";
const replace = document.querySelector("#replace");
replace.addEventListener("click", () => {
document.open();
document.write(
policy.createHTML(oneInput),
policy.createHTML(twoInput),
policy.createHTML(threeInput),
);
document.close();
});
Ergebnisse
Klicken Sie auf die Schaltfläche. Sie sehen, dass die HTML-Elemente, denen wir (in diesem Beispiel) vertrauen, eingefügt werden. Das nicht vertrauenswürdige <script>-Element wird dagegen als einfacher Text dargestellt.
Zeichenfolgen schreiben
Dieses Beispiel entspricht dem vorherigen, allerdings werden Trusted Types weder verwendet noch erzwungen. Wir schreiben unbereinigte Zeichenfolgen, die einen Weg für XSS-Angriffe eröffnen können.
Zunächst zeigt das Beispiel einen Standardtext und eine Schaltfläche an. Wenn Sie auf die Schaltfläche klicken, wird das aktuelle Dokument geöffnet. Drei HTML-Zeichenfolgen werden in das Dokument geschrieben. Anschließend wird das Dokument geschlossen. Dadurch wird das Dokument im Beispiel-Frame ersetzt – einschließlich des ursprünglichen HTML für die Schaltfläche und des JavaScripts, das die Aktualisierung ausgelöst hat.
HTML
<p>Some original document content.</p>
<button id="replace" type="button">Replace document content</button>
JavaScript
const replace = document.querySelector("#replace");
const oneInput = "<h1>Out with the old</h1>";
const twoInput = "<p>in with the new!</p>";
const threeInput = "<script>alert('evil afoot')<" + "/script>";
replace.addEventListener("click", () => {
document.open();
document.write(oneInput, twoInput, threeInput);
document.close();
});
Ergebnisse
Klicken Sie auf die Schaltfläche. Sie sehen, dass alle HTML-Elemente eingefügt werden.
Dazu gehört auch das <script>-Element, das in einer realen Anwendung möglicherweise schädlichen Code ausgeführt hätte.
Spezifikationen
| Spezifikation |
|---|
| HTML> # dom-document-write-dev> |