Signatur
Beschreibung
PerformanceNavigationTiming ist der moderne Nachfolger von performance.timing (Navigation Timing Level 1). Für jedes Dokument erzeugt der Browser genau einen Eintrag vom Typ "navigation" in der Performance Timeline. Er beschreibt, wie lange die einzelnen Phasen des Seitenaufrufs gedauert haben. Alle Zeitstempel sind DOMHighResTimeStamp-Werte in Millisekunden relativ zu performance.timeOrigin. Damit lassen sich Werte wie Time to First Byte (TTFB) oder die Dauer bis zum load-Event direkt berechnen.
Das Interface erbt von PerformanceResourceTiming und somit auch von PerformanceEntry. Dadurch stehen Netzwerk-Eigenschaften wie redirectStart, domainLookupStart, connectStart, secureConnectionStart, requestStart, responseStart, responseEnd, transferSize oder nextHopProtocol zur Verfügung. Zusätzlich definiert es dokumentbezogene Eigenschaften:
type– Art der Navigation:"navigate","reload","back_forward"oder"prerender".redirectCount– Anzahl der Weiterleitungen (nur Same-Origin).unloadEventStart/unloadEventEnd– Dauer desunload-Handlers der vorherigen Seite.domInteractive,domContentLoadedEventStart,domContentLoadedEventEnd,domComplete,loadEventStart,loadEventEnd– Meilensteine beim Aufbau des Dokuments.activationStart(Chromium) – Zeitpunkt der Aktivierung einer vorab gerenderten Seite;criticalCHRestart– Neustart wegen Client Hints.
Der Eintrag wird nicht über einen Konstruktor erzeugt, sondern mit performance.getEntriesByType("navigation") abgefragt oder mit einem PerformanceObserver beobachtet. Typische Einsatzgebiete sind Real User Monitoring (RUM), Performance-Budgets und das Erkennen von Neuladen oder Zurück-Navigation.
Rückgabewert
performance.getEntriesByType("navigation")[0] oder über einen PerformanceObserver mit type: "navigation".Beispiele
Navigationseintrag abrufen und Kernmetriken berechnen
window.addEventListener('load', () => {
// Kurz warten, damit loadEventEnd gesetzt ist
setTimeout(() => {
const [nav] = performance.getEntriesByType('navigation');
if (!nav) return;
const metrics = {
typ: nav.type,
dns: Math.round(nav.domainLookupEnd - nav.domainLookupStart),
tcp: Math.round(nav.connectEnd - nav.connectStart),
ttfb: Math.round(nav.responseStart - nav.startTime),
domInteractive: Math.round(nav.domInteractive),
domContentLoaded: Math.round(nav.domContentLoadedEventEnd),
load: Math.round(nav.loadEventEnd),
protokoll: nav.nextHopProtocol
};
console.table(metrics);
}, 0);
});
Mit PerformanceObserver beobachten und an Analytics senden
const observer = new PerformanceObserver((list) => {
for (const entry of list.getEntries()) {
const payload = JSON.stringify({
url: entry.name,
type: entry.type,
ttfb: entry.responseStart - entry.startTime,
duration: entry.duration,
transferSize: entry.transferSize
});
// sendBeacon übersteht auch das Verlassen der Seite
navigator.sendBeacon('/analytics/navigation', payload);
}
});
// buffered: true liefert auch den bereits erzeugten Eintrag
observer.observe({ type: 'navigation', buffered: true });
Neuladen oder Zurück-Navigation erkennen
const [nav] = performance.getEntriesByType('navigation');
switch (nav?.type) {
case 'reload':
console.log('Seite wurde neu geladen – Formularentwurf wiederherstellen');
break;
case 'back_forward':
console.log('Zurück/Vor-Navigation – Scrollposition beibehalten');
break;
case 'prerender':
console.log('Seite wurde vorab gerendert');
break;
default:
console.log('Normale Navigation');
}
Serverzeit über Server-Timing auslesen
const [nav] = performance.getEntriesByType('navigation');
// Header z. B.: Server-Timing: db;dur=53, app;dur=47.2
for (const { name, duration, description } of nav.serverTiming) {
console.log(`${name}: ${duration} ms ${description}`);
}
// Wichtig · Fallstricke
- Zeitpunkt der Abfrage: Vor dem Ende des
load-Events stehenloadEventEndunddurationauf0. Deshalb nachloadmitsetTimeoutabfragen oder einenPerformanceObservermitbuffered: trueverwenden. - Relative Zeitstempel: Anders als bei
performance.timingsind die Werte keine Unix-Zeitstempel, sondern relativ zuperformance.timeOrigin;startTimeist immer0. - Cross-Origin-Einschränkungen: Gab es Weiterleitungen über fremde Origins, sind
redirectStart,redirectEndundredirectCount0.unloadEventStart/Endsind ebenfalls0, wenn die vorherige Seite von einer anderen Origin stammt. - Back/Forward-Cache: Wird eine Seite aus dem bfcache wiederhergestellt, entsteht kein neuer Navigationseintrag. Diese Fälle erkennt man über das
pageshow-Event mitevent.persisted. - Werte 0:
secureConnectionStartist bei HTTP-Verbindungen 0, DNS- und TCP-Phasen sind bei wiederverwendeten Verbindungen oder Antworten aus dem Cache oft 0 bzw. gleichfetchStart. - Veraltet:
performance.timingundperformance.navigation(PerformanceNavigation) sind veraltet; neue Projekte sollten dieses Interface nutzen. - Kompatibilität: Wird von allen modernen Browsern unterstützt (Safari erst ab 15).
activationStart,criticalCHRestartund der Typ"prerender"gibt es derzeit nur in Chromium-Browsern. Auch in Web Workern ist das Interface nicht verfügbar, weil dort keine Dokumentnavigation stattfindet.