Signatur
Beschreibung
Die schreibgeschützte Eigenschaft responseStart gibt den Zeitpunkt in Millisekunden relativ zu performance.timeOrigin an, zu dem der Browser das erste Byte der Antwort erhalten hat. Die Antwort kann vom Server, aus dem HTTP-Cache oder von einer lokalen Ressource kommen, etwa über einen Service Worker.
Zusammen mit requestStart ergibt sich daraus die Time to First Byte (TTFB) einer einzelnen Ressource, also die Wartezeit auf den Server: responseStart - requestStart. Die Differenz responseEnd - responseStart gibt dagegen die reine Download-Dauer an. Mit diesen Werten findest du heraus, ob ein langsamer Request am Backend oder an der Übertragungsgröße bzw. Bandbreite liegt.
Die Werte lassen sich über performance.getEntriesByType("resource") abfragen. Neue Einträge beobachtest du am besten mit einem PerformanceObserver vom Typ "resource". Für das Hauptdokument gibt es PerformanceNavigationTiming, das von PerformanceResourceTiming erbt und ebenfalls responseStart anbietet.
Rückgabewert
performance.timeOrigin. Bei ursprungsübergreifenden Ressourcen ohne Timing-Allow-Origin-Header ist der Wert 0.Beispiele
TTFB und Download-Dauer aller Ressourcen ermitteln
const entries = performance.getEntriesByType("resource");
for (const entry of entries) {
// 0 bedeutet: Zeitwerte nicht verfügbar (Cross-Origin ohne TAO)
if (entry.responseStart === 0) continue;
const ttfb = entry.responseStart - entry.requestStart;
const download = entry.responseEnd - entry.responseStart;
console.log(`${entry.name}: TTFB ${ttfb.toFixed(1)} ms, Download ${download.toFixed(1)} ms`);
}
Neue Ressourcen mit PerformanceObserver überwachen
const observer = new PerformanceObserver((list) => {
for (const entry of list.getEntries()) {
const ttfb = entry.responseStart - entry.requestStart;
if (entry.responseStart > 0 && ttfb > 500) {
console.warn(`Langsamer Server für ${entry.name}: ${Math.round(ttfb)} ms`);
}
}
});
observer.observe({ type: "resource", buffered: true });
Messung für einen einzelnen fetch-Request
const url = "/api/users";
await fetch(url);
const [entry] = performance.getEntriesByName(new URL(url, location.href).href);
if (entry) {
console.log("Erstes Byte nach", Math.round(entry.responseStart - entry.startTime), "ms");
}
// Wichtig · Fallstricke
- Cross-Origin: Liefert der fremde Server keinen passenden
Timing-Allow-Origin-Header, gebenresponseStart,requestStartund die übrigen detaillierten Zeitwerte0zurück. Filtere solche Einträge heraus, sonst bekommst du negative oder unsinnige Differenzen. - Cache-Treffer: Kommt die Ressource aus dem Cache, liegen
requestStartundresponseStartsehr dicht beieinander. Solche Einträge verfälschen Statistiken zur TTFB. Du erkennst sie z. B. antransferSize === 0. - Informative Antworten (1xx): In neueren Browsern kann
responseStartauf eine interim-Antwort wie103 Early Hintszeigen. Dann gibt es zusätzlich die EigenschaftfirstInterimResponseStart. Chromium bietet außerdemfinalResponseHeadersStartfür die endgültige Antwort. - Puffergröße: Der Puffer für Ressourcen-Einträge ist begrenzt, standardmäßig meist auf 250 Einträge. Mit
performance.setResourceTimingBufferSize()kannst du ihn vergrößern, oder du verwendest einenPerformanceObserver. - Die Zeitauflösung wird aus Sicherheitsgründen gegen Timing-Angriffe gerundet, je nach Browser und Isolationsstatus der Seite.