logo hsb.horse
← Zur Snippets-Übersicht

Snippets

Idempotenter DOM-Observer-Setup über dataset

Ein einfaches Muster mit data-Attributen, um doppelte MutationObserver-Registrierungen zu verhindern. Kein globales Registry erforderlich, hochgradig portierbar.

Veröffentlicht: Aktualisiert:

Wenn MutationObserver mehrfach eingerichtet wird, können doppelte Observer auf demselben Element registriert werden. Eine Verwaltung über ein globales Set oder Map ist möglich, aber das Schreiben eines Beobachtet-Flags in dataset ist leichtgewichtig und leicht portierbar.

Code

const OBSERVE_ID_KEY = 'observeId'
const isElementObserved = <T extends HTMLElement = HTMLElement>(
ele: T
) => Object.hasOwn(ele.dataset, OBSERVE_ID_KEY)
const setObserverId =
(id: string) =>
<T extends HTMLElement = HTMLElement>(ele: T): T => {
ele.dataset[OBSERVE_ID_KEY] = id
return ele
}
export const observeElement = (
observeId: string,
element: HTMLElement | string,
observerCallback: MutationCallback,
options: MutationObserverInit = { childList: true }
) => {
const observedElement =
element instanceof HTMLElement
? element
: document.querySelector<HTMLElement>(element)
if (observedElement && !isElementObserved(observedElement)) {
const observer = new MutationObserver(observerCallback)
observer.observe(observedElement, options)
setObserverId(observeId)(observedElement)
return observer
}
}

Verwendung

// Akzeptiert sowohl einen Selektor-String als auch ein HTMLElement
observeElement(
'my-list-observer',
'#item-list',
(mutations) => {
for (const mutation of mutations) {
console.log('Änderung erkannt:', mutation.type)
}
}
)
// Ein erneuter Aufruf auf demselben Element registriert keinen doppelten Observer
observeElement('my-list-observer', '#item-list', callback)

Funktionsweise

  1. Object.hasOwn(ele.dataset, OBSERVE_ID_KEY) prüft das Vorhandensein des data-observe-id-Attributs
  2. Nur wenn noch nicht registriert, wird ein MutationObserver erstellt und observe() aufgerufen
  3. Nach dem Start der Beobachtung wird das Flag über ele.dataset[OBSERVE_ID_KEY] = id gesetzt
  4. Bei nachfolgenden Aufrufen gibt isElementObserved true zurück und es passiert nichts

Da dataset-Werte direkt in das HTML-data-*-Attribut geschrieben werden, sind sie in den DevTools sichtbar.

Vorteile

  • Kein globales Registry: Der Zustand wird im Element selbst gespeichert, sodass keine separate Map oder Set verwaltet werden muss
  • Hochgradig portierbar: Keine Framework-Abhängigkeiten; funktioniert in jeder Umgebung
  • Leicht debuggbar: Attributwerte können direkt in den DevTools überprüft werden

Hinweise

Wenn ein Element aus dem DOM entfernt wird, gehen die dataset-Informationen verloren. Wird dasselbe Element erneut eingefügt, wird wieder ein Observer registriert. Zum Stoppen eines Observers muss zudem observer.disconnect() separat aufgerufen werden.