Start · Sprachen · JavaScript · Referenz · RTCInboundRtpStreamStats.fecPacketsReceived

RTCInboundRtpStreamStats.fecPacketsReceived

Eigenschaft

Gibt an, wie viele FEC-Pakete (Forward Error Correction) dieser eingehende RTP-Strom bisher vom entfernten Peer empfangen hat.

seit JavaScript Chrome/Edge 80+, Firefox, Safari (teilweise); nich Kategorie: webapi

Signatur

RTCInboundRtpStreamStats.fecPacketsReceived

Beschreibung

Die Eigenschaft fecPacketsReceived des Dictionarys RTCInboundRtpStreamStats ist ein nicht-negativer Zähler (unsigned long long). Er gibt an, wie viele RTP-Pakete mit Forward Error Correction (FEC) für diesen eingehenden Strom empfangen wurden. FEC-Pakete enthalten redundante Daten, mit denen der Empfänger verlorene Mediapakete rekonstruieren kann, ohne sie erneut anfordern zu müssen (z. B. per NACK).

Den Wert erhält man über RTCPeerConnection.getStats() oder RTCRtpReceiver.getStats(). Er steht in den Einträgen mit type === "inbound-rtp". Zusammen mit fecPacketsDiscarded und packetsLost lässt sich ablesen, wie wirksam die Fehlerkorrektur ist und ob der Sender unnötig viel Redundanz schickt.

Wichtig: Der Zähler berücksichtigt nur FEC-Daten, die als eigene Pakete ankommen, z. B. über einen separaten FEC-Strom (FlexFEC) oder als ULPFEC in eigenen RTP-Paketen. In-Band-FEC wie bei Opus, bei dem die Redundanz im selben Paket steckt, wird hier nicht mitgezählt. Bei reinen Opus-Audioströmen bleibt der Wert deshalb oft 0, obwohl Fehlerkorrektur aktiv ist.

Rückgabewert

Typ
number | undefined
Beschreibung
Gesamtzahl der bisher empfangenen FEC-Pakete (ganzzahlig, steigt nur an). Ist undefined, wenn der Browser die Kennzahl nicht liefert.

Beispiele

FEC-Pakete aller eingehenden Ströme auslesen

// pc ist eine bestehende, verbundene RTCPeerConnection
const logFecStats = async (pc) => {
  const report = await pc.getStats();
  report.forEach((stats) => {
    if (stats.type === 'inbound-rtp') {
      console.log(
        `${stats.kind} (SSRC ${stats.ssrc}): ` +
        `${stats.fecPacketsReceived ?? 'n/a'} FEC-Pakete empfangen`
      );
    }
  });
};

await logFecStats(pc);
video (SSRC 1234567890): 412 FEC-Pakete empfangen audio (SSRC 987654321): 0 FEC-Pakete empfangen

FEC-Effizienz eines Video-Empfängers berechnen

const getFecEfficiency = async (receiver) => {
  const report = await receiver.getStats();
  for (const stats of report.values()) {
    if (stats.type !== 'inbound-rtp') continue;
    const received = stats.fecPacketsReceived ?? 0;
    const discarded = stats.fecPacketsDiscarded ?? 0;
    if (received === 0) return null;
    // Anteil der FEC-Pakete, die tatsächlich genutzt wurden
    return 1 - discarded / received;
  }
  return null;
};

const [videoReceiver] = pc.getReceivers().filter((r) => r.track.kind === 'video');
const efficiency = await getFecEfficiency(videoReceiver);
console.log(efficiency === null
  ? 'Keine FEC-Daten'
  : `FEC-Nutzung: ${(efficiency * 100).toFixed(1)} %`);
FEC-Nutzung: 12.4 %

FEC-Rate pro Sekunde überwachen

let lastCount = 0;
let lastTimestamp = 0;

const timer = setInterval(async () => {
  const report = await pc.getStats();
  for (const stats of report.values()) {
    if (stats.type === 'inbound-rtp' && stats.kind === 'video') {
      const count = stats.fecPacketsReceived ?? 0;
      if (lastTimestamp) {
        const seconds = (stats.timestamp - lastTimestamp) / 1000;
        const rate = (count - lastCount) / seconds;
        console.log(`FEC-Pakete/s: ${rate.toFixed(1)}`);
      }
      lastCount = count;
      lastTimestamp = stats.timestamp;
    }
  }
}, 2000);

// Beim Beenden der Verbindung aufräumen
pc.addEventListener('connectionstatechange', () => {
  if (pc.connectionState === 'closed') clearInterval(timer);
});
FEC-Pakete/s: 23.5 FEC-Pakete/s: 19.0

// Wichtig · Fallstricke

  • In-Band-FEC wird nicht gezählt: Opus-FEC steckt im Nutzdatenpaket selbst und erhöht den Zähler nicht. Ein Wert von 0 heißt also nicht, dass keine Fehlerkorrektur aktiv ist.
  • Kumulativer Zähler: Der Wert zählt seit Beginn des Stroms. Für Raten muss man die Differenz zweier Messungen durch die Differenz der timestamp-Werte teilen.
  • Abhängig vom Codec: Ob FEC-Pakete ankommen, hängt vom ausgehandelten SDP ab (z. B. ulpfec, red, flexfec-03). FlexFEC ist in Chrome teilweise nur per Feldversuch aktiv.
  • Browser-Unterstützung: Chromium-Browser liefern den Wert zuverlässig. Firefox und Safari unterstützen ihn teils nur eingeschränkt. Daher immer mit ?? oder einer Prüfung auf undefined absichern.
  • Ältere Codebeispiele nutzen noch die veraltete Callback-Variante von getStats(). Verwende stattdessen die Promise-Variante.