Start · Sprachen · JavaScript · Referenz · FileSystemWritableFileStream.seek()

FileSystemWritableFileStream.seek()

Methode

Setzt die Schreibposition (den Dateicursor) eines <code>FileSystemWritableFileStream</code> auf den angegebenen Byte-Offset.

seit JavaScript Chrome/Edge 86+, Firefox 111+, Safari 17+ (nur in Kategorie: webapi

Signatur

FileSystemWritableFileStream.prototype.seek(position)

Beschreibung

Die Methode seek() verschiebt den internen Dateicursor eines FileSystemWritableFileStream auf eine bestimmte Position in Byte. Alle folgenden write()-Aufrufe ohne eigene Positionsangabe schreiben ab dieser Stelle weiter. So lassen sich Dateien gezielt an einer Stelle überschreiben oder ergänzen, statt immer nur hinten anzuhängen.

Intern entspricht seek(position) genau dem Aufruf write({ type: "seek", position }). Die Methode gibt ein Promise zurück, das erfüllt wird, sobald die neue Position übernommen wurde. Da sie in die Schreibwarteschlange des Streams eingereiht wird, sollte man sie mit await aufrufen, bevor man weiterschreibt.

Typische Einsatzfälle sind das Aktualisieren eines Datei-Headers (z. B. Längenfelder in Binärformaten wie WAV), das Fortsetzen abgebrochener Downloads an einer bekannten Position oder das Anhängen an bestehende Dateien. Für Letzteres öffnet man den Stream mit createWritable({ keepExistingData: true }) und springt per seek(file.size) ans Ende.

Wichtig: Alle Änderungen landen zunächst in einer temporären Datei und werden erst beim Aufruf von close() atomar in die Zieldatei übernommen.

Parameter

Name Typ Default Beschreibung
$position Pflicht number Neuer Byte-Offset des Dateicursors, gezählt ab dem Dateianfang (0). Liegt der Wert hinter dem aktuellen Dateiende, wird die Datei beim nächsten Schreiben bis dorthin mit Null-Bytes aufgefüllt.

Rückgabewert

Typ
Promise<undefined>
Beschreibung
Ein Promise, das mit undefined erfüllt wird, sobald die neue Position gesetzt ist.

Beispiele

Text am Dateiende anhängen

// Datei auswählen und neuen Text ans Ende schreiben
const appendLog = async (line) => {
  const [handle] = await window.showOpenFilePicker();
  const file = await handle.getFile();

  // Vorhandene Daten behalten, sonst ist die Datei zunächst leer
  const writable = await handle.createWritable({ keepExistingData: true });
  await writable.seek(file.size); // Cursor ans Ende setzen
  await writable.write(`${line}\n`);
  await writable.close(); // Änderungen übernehmen
  console.log(`Angehängt ab Byte ${file.size}`);
};

document.querySelector('#log-btn').addEventListener('click', () => appendLog('Neuer Eintrag'));
Angehängt ab Byte 1024

Header einer Binärdatei nachträglich überschreiben

// Im Origin Private File System (OPFS) eine Datei mit Platzhalter-Header schreiben
const root = await navigator.storage.getDirectory();
const handle = await root.getFileHandle('daten.bin', { create: true });
const writable = await handle.createWritable();

await writable.write(new Uint8Array(4)); // 4 Byte Platzhalter für die Länge
const payload = new TextEncoder().encode('Hallo Welt');
await writable.write(payload);

// Zurück an den Anfang und die tatsächliche Länge eintragen
const header = new DataView(new ArrayBuffer(4));
header.setUint32(0, payload.byteLength, true);
await writable.seek(0);
await writable.write(header.buffer);
await writable.close();

const file = await handle.getFile();
console.log(file.size, new DataView(await file.arrayBuffer()).getUint32(0, true));
14 10

seek() vs. write() mit type "seek"

const root = await navigator.storage.getDirectory();
const handle = await root.getFileHandle('text.txt', { create: true });
const writable = await handle.createWritable();

await writable.write('Hallo Welt');
await writable.seek(6);                              // Kurzform
// gleichwertig: await writable.write({ type: 'seek', position: 6 });
await writable.write('Mars');
await writable.close();

console.log(await (await handle.getFile()).text());
Hallo Mars

// Wichtig · Fallstricke

  • Stream standardmäßig leer: Ohne keepExistingData: true beginnt createWritable() mit einer leeren temporären Datei. Ein seek() auf eine alte Position führt dann zu mit Null-Bytes aufgefüllten Bereichen statt zu den ursprünglichen Daten.
  • Überschreiben, nicht Einfügen: write() nach seek() überschreibt vorhandene Bytes. Die Datei wird nur länger, wenn man über das Ende hinaus schreibt. Zum Kürzen dient truncate().
  • Byte statt Zeichen: Die Position zählt in Byte. Bei UTF-8-Text mit Umlauten oder Emojis stimmt sie nicht mit dem String-Index überein. Die Byte-Länge erhält man über new TextEncoder().encode(str).byteLength.
  • Fehler: Das Promise wird mit einer Ablehnung beendet, z. B. mit NotAllowedError, wenn die Schreibberechtigung fehlt, oder mit TypeError, wenn der Stream bereits geschlossen ist oder position ungültig ist.
  • Kompatibilität: Nur in sicheren Kontexten (HTTPS) verfügbar. Chromium unterstützt die Methode seit Version 86. Firefox und Safari unterstützen createWritable() neuer und vor allem für das OPFS (navigator.storage.getDirectory()). showOpenFilePicker() gibt es nur in Chromium-Browsern. Für performantes, synchrones Schreiben in Workern eignet sich FileSystemSyncAccessHandle mit der Option at.