Start · Sprachen · JavaScript · Referenz · RTCRemoteOutboundRtpStreamStats.remoteTimestamp

RTCRemoteOutboundRtpStreamStats.remoteTimestamp

Eigenschaft

Gibt den Zeitpunkt nach der Uhr des entfernten Peers an, zu dem dieser die Statistiken (RTCP Sender Report) gesendet hat, in Millisekunden seit der Unix-Epoche.

seit JavaScript Chrome 97+, Firefox 68+, Safari 15.4+ (Stand: nich Kategorie: webapi

Signatur

RTCRemoteOutboundRtpStreamStats.remoteTimestamp

Beschreibung

Die Eigenschaft remoteTimestamp gehört zu Statistik-Objekten vom Typ "remote-outbound-rtp", die du über RTCPeerConnection.getStats() oder RTCRtpReceiver.getStats() erhältst. Sie beschreibt, wann der entfernte Peer die Statistiken zu seinem ausgehenden RTP-Strom verschickt hat. Der Wert stammt aus dem NTP-Zeitstempel des RTCP-Sender Reports (SR) und wird in einen DOMHighResTimeStamp (Millisekunden seit dem 1. Januar 1970 UTC) umgerechnet.

Im Unterschied dazu gibt die geerbte Eigenschaft timestamp an, wann die Statistiken lokal erzeugt bzw. empfangen wurden. Die Differenz timestamp - remoteTimestamp setzt sich also aus der Übertragungsverzögerung (einseitige Latenz) und dem Uhrenversatz zwischen beiden Rechnern zusammen.

Typische Einsatzzwecke sind die Diagnose von Verbindungsqualität, das Erkennen veralteter Berichte (z. B. wenn keine neuen Sender Reports mehr eintreffen) und die grobe Abschätzung von Uhrenabweichungen zwischen den Peers. Für eine verlässliche Latenzmessung eignet sich dagegen eher roundTripTime aus "remote-inbound-rtp"-Statistiken, da diese nicht von synchronisierten Uhren abhängt.

Rückgabewert

Typ
DOMHighResTimeStamp (number) | undefined
Beschreibung
Zeitpunkt in Millisekunden seit der Unix-Epoche, gemessen mit der Uhr des entfernten Peers. Kann fehlen (undefined), solange noch kein RTCP Sender Report empfangen wurde.

Beispiele

remoteTimestamp aus den Empfangsstatistiken auslesen

// pc ist eine bestehende, verbundene RTCPeerConnection
const logRemoteTimestamps = async (pc) => {
  const report = await pc.getStats();
  report.forEach((stats) => {
    if (stats.type === 'remote-outbound-rtp') {
      const remote = new Date(stats.remoteTimestamp);
      console.log(`${stats.kind}: SR gesendet um ${remote.toISOString()}`);
    }
  });
};

await logRemoteTimestamps(pc);
audio: SR gesendet um 2024-05-14T09:31:22.418Z video: SR gesendet um 2024-05-14T09:31:22.903Z

Alter des Berichts und Uhrenversatz abschätzen

const analyzeSenderReports = async (receiver) => {
  const report = await receiver.getStats();
  for (const stats of report.values()) {
    if (stats.type !== 'remote-outbound-rtp' || stats.remoteTimestamp === undefined) continue;

    // lokale Zeit minus entfernte Zeit = Latenz + Uhrenversatz
    const delta = stats.timestamp - stats.remoteTimestamp;
    console.log(`Delta lokal/entfernt: ${delta.toFixed(1)} ms`);

    // Wie alt ist der Bericht aus lokaler Sicht?
    const age = (performance.timeOrigin + performance.now()) - stats.timestamp;
    console.log(`Bericht ist ${age.toFixed(0)} ms alt`);
  }
};

const [receiver] = pc.getReceivers();
await analyzeSenderReports(receiver);
Delta lokal/entfernt: 47.3 ms Bericht ist 812 ms alt

Ausbleibende Sender Reports überwachen

const watchSenderReports = (pc, timeoutMs = 10000) => {
  const lastSeen = new Map();

  return setInterval(async () => {
    const report = await pc.getStats();
    report.forEach((stats) => {
      if (stats.type !== 'remote-outbound-rtp') return;
      const prev = lastSeen.get(stats.id);
      if (prev && prev.remoteTimestamp === stats.remoteTimestamp) {
        if (Date.now() - prev.seenAt > timeoutMs) {
          console.warn(`Keine neuen Sender Reports für ${stats.kind}`);
        }
        return;
      }
      lastSeen.set(stats.id, { remoteTimestamp: stats.remoteTimestamp, seenAt: Date.now() });
    });
  }, 2000);
};

const timer = watchSenderReports(pc);
// später: clearInterval(timer);
Keine neuen Sender Reports für video

// Wichtig · Fallstricke

  • Uhren nicht synchron: Der Wert basiert auf der Systemuhr des entfernten Peers. Weicht diese ab, kann timestamp - remoteTimestamp sogar negativ werden. Nutze die Differenz nicht als exakte Latenz, sondern verwende roundTripTime aus "remote-inbound-rtp".
  • Kann fehlen: Bevor der erste RTCP Sender Report eintrifft, gibt es entweder kein "remote-outbound-rtp"-Objekt oder remoteTimestamp ist undefined. Immer prüfen, bevor du rechnest.
  • Bezugspunkt: Anders als performance.now() ist der Wert relativ zur Unix-Epoche und kann direkt an new Date() übergeben werden.
  • Aktualisierungsrate: Sender Reports kommen typischerweise nur alle paar Sekunden; mehrere getStats()-Aufrufe hintereinander liefern daher oft denselben Wert.
  • Kompatibilität: Unterstützt in aktuellen Versionen von Chrome, Edge, Firefox und Safari; ältere Browser liefern "remote-outbound-rtp"-Statistiken teilweise gar nicht.