Start · Sprachen · JavaScript · Referenz · WorkerGlobalScope: rejectionhandled

WorkerGlobalScope: rejectionhandled

Ereignis

Wird im Worker-Kontext (<code>WorkerGlobalScope</code>) ausgelöst, wenn ein abgelehnter Promise erst nachträglich einen Ablehnungs-Handler bekommt.

seit JavaScript Baseline 2023: alle modernen Browser (Chrome 49+, Kategorie: webapi

Signatur

self.addEventListener("rejectionhandled", handler)

Beschreibung

Das Ereignis rejectionhandled wird an den globalen Kontext eines Workers (WorkerGlobalScope, also self in Dedicated-, Shared- und Service-Workern) gesendet, wenn ein Promise abgelehnt wurde, dafür zunächst kein Handler existierte und deshalb schon ein unhandledrejection-Ereignis gefeuert wurde. Wird später doch noch per .catch() oder .then(_, onRejected) ein Handler angehängt, folgt rejectionhandled.

Der Handler erhält ein PromiseRejectionEvent mit den Eigenschaften promise (der betroffene Promise) und reason (der Ablehnungsgrund). Das Ereignis lässt sich nicht abbrechen und hat keine Standardaktion.

In der Praxis nutzt man das Ereignispaar unhandledrejection/rejectionhandled für Fehler-Monitoring: Unbehandelte Ablehnungen werden in einer Liste gesammelt und wieder daraus entfernt, sobald sie nachträglich behandelt werden. So meldet man nur Fehler, die wirklich unbehandelt geblieben sind.

Registrieren lässt sich der Handler per self.addEventListener("rejectionhandled", handler) oder über die Eigenschaft self.onrejectionhandled = handler. Im Hauptthread gibt es das gleiche Ereignis auf window.

Parameter

Name Typ Default Beschreibung
$type Pflicht string Der Ereignisname "rejectionhandled".
$handler Pflicht (event: PromiseRejectionEvent) => void Callback, das ein PromiseRejectionEvent mit event.promise und event.reason erhält.
$options boolean | AddEventListenerOptions false Optionale Listener-Optionen wie once oder signal.

Rückgabewert

Typ
void
Beschreibung
addEventListener gibt nichts zurück; der Rückgabewert des Handlers wird ignoriert.

Beispiele

Verspätete Behandlung im Worker erkennen

// worker.js
self.addEventListener("unhandledrejection", (event) => {
  console.log("Unbehandelt:", event.reason.message);
});

self.addEventListener("rejectionhandled", (event) => {
  console.log("Nachträglich behandelt:", event.reason.message);
});

const p = Promise.reject(new Error("Timeout"));

// Handler erst deutlich später anhängen
setTimeout(() => {
  p.catch(() => {});
}, 1000);
Unbehandelt: Timeout Nachträglich behandelt: Timeout

Fehler-Monitoring: nur echte unbehandelte Ablehnungen melden

// worker.js
const offen = new Map();

self.onunhandledrejection = (event) => {
  offen.set(event.promise, event.reason);
};

self.onrejectionhandled = (event) => {
  offen.delete(event.promise);
};

// Alle 5 Sekunden verbleibende Fehler an den Hauptthread melden
setInterval(() => {
  for (const [, reason] of offen) {
    self.postMessage({ typ: "fehler", nachricht: String(reason) });
  }
  offen.clear();
}, 5000);

Listener mit AbortController wieder entfernen

// worker.js
const controller = new AbortController();

self.addEventListener(
  "rejectionhandled",
  (event) => console.log("Behandelt:", event.reason),
  { signal: controller.signal }
);

// Später: Überwachung beenden
controller.abort();

// Alternativ über die on-Property
self.onrejectionhandled = null;

// Wichtig · Fallstricke

  • rejectionhandled feuert nur, wenn vorher unhandledrejection für denselben Promise ausgelöst wurde. Wird ein Handler noch im selben Microtask-Durchlauf angehängt, passiert keines der beiden Ereignisse.
  • Der genaue Zeitpunkt, zu dem ein Promise als „unbehandelt“ gilt, hängt von der Engine ab. Verlass dich nicht auf ein bestimmtes Timing.
  • Wenn du Promises in einer Map sammelst, halten die Einträge diese Objekte im Speicher fest. Leere die Map regelmäßig oder nimm eine WeakMap/WeakRef, falls du nicht über die Einträge iterieren musst.
  • Firefox unterstützt das Ereignis erst ab Version 69. Ob Shared Worker unterstützt werden, ist je nach Browser unterschiedlich.
  • In Node.js heißt das Gegenstück process.on("rejectionHandled") (mit großem H) und hat eine andere Signatur.