Signatur
Beschreibung
RTCRemoteOutboundRtpStreamStats ist ein Wörterbuch (Dictionary) der WebRTC-Statistik-API. Es taucht als Eintrag in einem RTCStatsReport auf, den RTCPeerConnection.getStats() oder RTCRtpReceiver.getStats() liefern, und hat immer type === "remote-outbound-rtp". Beschrieben wird der RTP-Stream, den die Gegenseite sendet und den Sie lokal empfangen. Die Werte misst Ihr Browser nicht selbst. Sie stammen aus den RTCP-Sender-Reports (SR), die der entfernte Sender regelmäßig schickt.
Zu jedem remote-outbound-rtp-Eintrag gibt es einen lokalen Gegenpart vom Typ "inbound-rtp" (RTCInboundRtpStreamStats). Die beiden sind über localId bzw. remoteId miteinander verknüpft. Vergleichen Sie die vom Sender gemeldeten Zähler (packetsSent, bytesSent) mit den lokal empfangenen Werten (packetsReceived, bytesReceived), dann können Sie Paketverluste und Durchsatz aus Sicht beider Endpunkte einschätzen.
Einige Felder werden geerbt: aus RTCStats (id, timestamp, type), aus RTCRtpStreamStats (ssrc, kind, transportId, codecId) und aus RTCSentRtpStreamStats (packetsSent, bytesSent). Eigene Felder sind localId, remoteTimestamp, reportsSent und die Umlaufzeit-Felder roundTripTime, totalRoundTripTime und roundTripTimeMeasurements.
Typische Einsatzfälle sind Qualitäts-Dashboards, Verbindungsdiagnose und Monitoring in Videokonferenz-Anwendungen. Dort wollen Sie wissen, wie viel die Gegenseite tatsächlich verschickt hat und wie viel davon angekommen ist.
Parameter
| Name | Typ | Default | Beschreibung |
|---|---|---|---|
| $localId | string | Die id des zugehörigen lokalen inbound-rtp-Eintrags im selben RTCStatsReport. |
|
| $remoteTimestamp | number (DOMHighResTimeStamp) | Zeitpunkt, zu dem die Gegenseite den Sender-Report erzeugt hat, gemessen mit ihrer Uhr (in Millisekunden seit der Unix-Epoche). Er ist nicht direkt mit dem lokalen timestamp vergleichbar. |
|
| $reportsSent | number | Anzahl der RTCP-Sender-Reports, die die Gegenseite für diesen SSRC bisher gesendet hat. | |
| $roundTripTime | number | Zuletzt gemessene Umlaufzeit in Sekunden. Sie ist nur vorhanden, wenn RTCP-XR-DLRR-Reports ausgetauscht werden. | |
| $totalRoundTripTime | number | Summe aller Umlaufzeit-Messungen in Sekunden. Geteilt durch roundTripTimeMeasurements ergibt sich die mittlere Umlaufzeit. |
|
| $roundTripTimeMeasurements | number | Anzahl der gültigen Umlaufzeit-Messungen, die in totalRoundTripTime eingeflossen sind. |
|
| $packetsSent | number | Geerbt aus RTCSentRtpStreamStats: Gesamtzahl der RTP-Pakete, die die Gegenseite laut Sender-Report gesendet hat. |
|
| $bytesSent | number | Geerbt aus RTCSentRtpStreamStats: Gesamtzahl der gesendeten Nutzdaten-Bytes laut Sender-Report, ohne Header und Padding. |
Rückgabewert
Map-artigen Struktur RTCStatsReport, die getStats() als Promise liefert.Beispiele
Alle remote-outbound-rtp-Einträge auslesen
// pc ist eine bestehende, verbundene RTCPeerConnection
const logRemoteOutbound = async (pc) => {
const report = await pc.getStats();
report.forEach((stats) => {
if (stats.type !== 'remote-outbound-rtp') return;
console.log(`${stats.kind} (SSRC ${stats.ssrc}):`,
`${stats.packetsSent} Pakete, ${stats.bytesSent} Bytes,`,
`${stats.reportsSent} Sender-Reports`);
});
};
await logRemoteOutbound(pc);
Paketverlust aus Sender- und Empfängersicht berechnen
const getLossPerStream = async (pc) => {
const report = await pc.getStats();
const result = [];
report.forEach((remote) => {
if (remote.type !== 'remote-outbound-rtp') return;
// lokalen inbound-rtp-Gegenpart über localId finden
const inbound = report.get(remote.localId);
if (!inbound) return;
const lost = remote.packetsSent - inbound.packetsReceived;
const lossRate = remote.packetsSent > 0 ? lost / remote.packetsSent : 0;
result.push({ kind: remote.kind, lost, lossRate: (lossRate * 100).toFixed(2) + ' %' });
});
return result;
};
console.table(await getLossPerStream(pc));
Senderate der Gegenseite periodisch überwachen
// Nur auf Audio-Empfänger beschränken
const receiver = pc.getReceivers().find((r) => r.track.kind === 'audio');
let previous = null;
const timer = setInterval(async () => {
const report = await receiver.getStats();
const current = [...report.values()].find((s) => s.type === 'remote-outbound-rtp');
if (!current) return;
// Nur auswerten, wenn ein neuer Sender-Report angekommen ist
if (previous && current.reportsSent > previous.reportsSent) {
const seconds = (current.remoteTimestamp - previous.remoteTimestamp) / 1000;
const kbps = ((current.bytesSent - previous.bytesSent) * 8) / seconds / 1000;
console.log(`Gegenseite sendet ca. ${kbps.toFixed(1)} kbit/s`);
if (current.roundTripTimeMeasurements > 0) {
const avgRtt = current.totalRoundTripTime / current.roundTripTimeMeasurements;
console.log(`Mittlere RTT: ${(avgRtt * 1000).toFixed(0)} ms`);
}
}
previous = current;
}, 2000);
// Später aufräumen: clearInterval(timer);