Start · Sprachen · JavaScript · Referenz · ServiceWorkerGlobalScope: sync

ServiceWorkerGlobalScope: sync

Ereignis

Wird im Service Worker ausgelöst, sobald eine per <code>SyncManager.register()</code> angemeldete Hintergrund-Synchronisation ausgeführt werden kann, typischerweise sobald wieder Netz da ist.

seit JavaScript Chromium-Browser (Chrome 49+, Edge 79+, Opera); ni Kategorie: webapi

Signatur

self.addEventListener("sync", handler)

Beschreibung

Das sync-Ereignis gehört zur Background Synchronization API. Eine Seite oder ein Worker meldet über registration.sync.register(tag) eine Synchronisation an. Der Browser löst das Ereignis im Service Worker aus, sobald eine Netzwerkverbindung besteht. Ist das Gerät bei der Anmeldung schon online, feuert das Ereignis fast sofort, sonst erst, wenn die Verbindung zurückkommt. Das funktioniert auch dann, wenn der Nutzer die Seite inzwischen geschlossen hat.

Der Handler bekommt ein SyncEvent-Objekt (erweitert ExtendableEvent). Es hat die Eigenschaften tag (der bei der Anmeldung vergebene Name) und lastChance. lastChance ist true, wenn der Browser nach diesem Versuch keinen weiteren mehr startet. Mit event.waitUntil(promise) teilen Sie dem Browser mit, wie lange die Arbeit dauert. Wird das Promise abgelehnt, plant der Browser automatisch einen neuen Versuch mit wachsendem Abstand ein (exponentieller Backoff).

Typische Einsätze sind Offline-First-Anwendungen. Formulardaten, Chat-Nachrichten oder Analysedaten werden offline zuerst in IndexedDB gespeichert und im sync-Handler gesammelt an den Server geschickt. Das Ereignis lässt sich per addEventListener("sync", …) oder über die Eigenschaft self.onsync abonnieren.

Parameter

Name Typ Default Beschreibung
$type Pflicht string Der Ereignisname "sync".
$handler Pflicht (event: SyncEvent) => void Callback, der ein SyncEvent erhält. Wichtige Eigenschaften: event.tag (string), event.lastChance (boolean) und die Methode event.waitUntil(promise).
$options boolean | AddEventListenerOptions false Optionale Listener-Optionen wie once oder signal.

Rückgabewert

Typ
void
Beschreibung
addEventListener gibt nichts zurück. Ob die Synchronisation geklappt hat, bestimmt das Promise, das an event.waitUntil() übergeben wird.

Beispiele

Synchronisation auf der Seite anmelden

// main.js – im Seitenkontext
const sendeSpaeter = async () => {
  const registration = await navigator.serviceWorker.ready;
  if ('sync' in registration) {
    await registration.sync.register('ausgang-senden');
    console.log('Sync registriert');
  } else {
    // Ausweichlösung: direkt senden
    await fetch('/api/nachrichten', { method: 'POST' });
  }
};

sendeSpaeter();
Sync registriert

sync-Ereignis im Service Worker behandeln

// sw.js
const sendeAusgang = async () => {
  const cache = await caches.open('ausgang');
  const anfragen = await cache.keys();
  for (const req of anfragen) {
    const res = await fetch(req.clone());
    if (!res.ok) throw new Error(`HTTP ${res.status}`); // löst einen neuen Versuch aus
    await cache.delete(req);
  }
  console.log(`${anfragen.length} Einträge synchronisiert`);
};

self.addEventListener('sync', (event) => {
  if (event.tag === 'ausgang-senden') {
    event.waitUntil(sendeAusgang());
  }
});
3 Einträge synchronisiert

onsync-Eigenschaft und lastChance auswerten

// sw.js
self.onsync = (event) => {
  event.waitUntil((async () => {
    try {
      await fetch('/api/statistik', { method: 'POST', body: '{}' });
    } catch (err) {
      if (event.lastChance) {
        // Letzter Versuch – Nutzer informieren
        await self.registration.showNotification('Synchronisation fehlgeschlagen');
        return;
      }
      throw err; // Browser versucht es später erneut
    }
  })());
};

// Wichtig · Fallstricke

  • Browser-Unterstützung: Nur Chromium-basierte Browser (Chrome, Edge, Opera, Samsung Internet). Firefox und Safari unterstützen die API nicht. Prüfen Sie das deshalb immer mit 'sync' in registration und halten Sie eine Ausweichlösung bereit, etwa sofort senden oder beim nächsten Seitenaufruf nachholen.
  • Nur in sicheren Kontexten: Die API funktioniert nur über HTTPS (oder localhost) und nur mit einem aktiven Service Worker.
  • Ohne event.waitUntil() kann der Browser den Worker beenden, bevor die asynchrone Arbeit fertig ist. Außerdem gibt es dann keine automatischen Wiederholungen.
  • Browser begrenzen die Laufzeit eines Versuchs (in Chrome einige Minuten) und die Zahl der Wiederholungen (in Chrome standardmäßig drei). Beim letzten Versuch ist lastChance gleich true.
  • Mehrfache Anmeldungen mit demselben tag werden zusammengefasst, solange die Synchronisation noch aussteht. Das eignet sich zum Entprellen.
  • Das Ereignis bekommt keine Nutzdaten. Speichern Sie die zu sendenden Daten vorher in IndexedDB oder in der Cache API.
  • Für regelmäßige Aktualisierungen gibt es die eigene Periodic Background Sync API mit dem Ereignis periodicsync.