Die alte getStats()
WebRTC API wird in Chrome 117 entfernt. Apps, die sie verwenden, müssen daher zur Standard API migriert werden. In diesem Artikel erfahren Sie, wie Sie Ihren Code migrieren und was Sie tun können, wenn Sie mehr Zeit für diese Änderung benötigen.
Bisher gab es zwei konkurrierende Versionen der WebRTC getStats()
API. Die alte getStats()-API, die vor dem Standardisierungsprozess datiert ist und ein Callback-Argument annimmt, und die standardisierte und weit verbreitete API, die ein Promise zurückgibt.
Die Standard-API bietet mehr Funktionen und klar definierte Messwerte, die öffentlich in der W3C-Spezifikation Identifiers for WebRTC's Statistics API dokumentiert sind. Die Spezifikation enthält Beschreibungen aller in diesem Handbuch aufgeführten Messwerte und viele weitere.
Ab Chrome 117 löst die alte getStats()
API eine Ausnahme in der stabilen Release-Version aus. Die Ausnahme wird nach und nach eingeführt. Befolgen Sie diese Anleitung, um Ihnen die Umstellung auf die Standard-API zu erleichtern.
Legacy- und Standard-Statistiktypen
Die vollständige Liste der Standard-Statistiktypen findest du unter dem Enum RTCStatsType in der Spezifikation. Dazu gehört auch, welche Statistikwörterbuchdefinition die für jeden Typ erfassten Messwerte beschreibt.
Alle Statistikobjekte haben ein ID-Attribut, das das zugrunde liegende Objekt in mehreren getStats()
-Aufrufen eindeutig identifiziert. Dasselbe Objekt hat bei jedem Aufruf der Methode dieselbe ID. Dies ist nützlich, um die Änderungsrate von Messwerten zu berechnen (ein Beispiel finden Sie im nächsten Abschnitt). Die IDs bilden auch Beziehungen von Referenzen. Das Statistikobjekt outbound-rtp
verweist beispielsweise über das Attribut outbound-rtp.mediaSourceId
auf das zugehörige Statistikobjekt media-source
. Wenn Sie alle ...Id
-Beziehungen zeichnen, erhalten Sie ein Diagramm.
Die Legacy-API hat die folgenden Statistiktypen, die den folgenden Standardtypen entsprechen:
Legacy-Typ |
Standardtyp |
---|---|
ssrc
|
Stellt einen RTP-Stream und Messwerte zur zugehörigen MediaStreamTrack dar.Die Standardtypen hierfür sind inbound-rtp (für RTP-Empfangs-Streams und die zugehörigen Remote-MediaStreamTrack ), outbound-rtp (zum Senden von RTP-Streams) und media-source (für lokale MediaStreamTrack -Messwerte, die mit einem RTP-Stream verknüpft sind). RTP-Stream-Messwerte enthalten auch Informationen zum Encoder oder Decoder, der vom RTP-Stream verwendet wird. |
VideoBwe
|
Messwerte zur Bandbreitenschätzung, Zielbitrate, Encoder-Bitrate und tatsächliche Bitrate. Diese Messwerttypen sind Teil der RTP-Messwerte ( outbound-rtp und inbound-rtp ) und der ICE-Kandidatenpaare (candidate-pair ). |
googComponent
|
Stellt den Transport (ICE und DTLS) dar. Die Standardversion ist transport . |
localcandidate and remotecandidate
|
Stellt einen ICE-Kandidaten dar. Die Standardversion ist local-candidate und remote-candidate . |
googCandidatePair
|
Ein ICE-Kandidatenpaar, das ein Paar aus einem lokalen und einem Remote-Kandidaten ist. Die Standardversion ist candidate-pair . |
googCertificate
|
Stellt ein Zertifikat dar, das vom DTLS-Transport verwendet wird. Die Standardversion ist certificate . |
googLibjingleSession
|
Stellt das RTCPeerConnection dar. Der Inhalt lässt sich zwar nicht mit dem Standard im Standard verknüpfen, der RTCPeerConnection ist jedoch mit einem Typ verknüpft: peer-connection . |
Fehlt in der alten API |
Die folgenden Statistiktypen wurden der Standard-API hinzugefügt, für die es keinen entsprechenden Legacy-Typ gibt: <ph type="x-smartling-placeholder">
|
Zuordnung von Legacy- zu Standard-Messwerten
Diese Zuordnung soll Entwicklern helfen, herauszufinden, welcher alte Messwert zu welchem Standardmesswert gehört. Der entsprechende Messwert kann jedoch andere Einheiten verwenden oder als Summenzähler und nicht als sofortiger Wert ausgedrückt werden. Messwertdefinitionen finden Sie in der Spezifikation.
Bei der Standard-API werden lieber Gesamtzähler anstelle von Raten bereitgestellt. Das bedeutet, dass die App wie bei der Legacy-API die durchschnittliche Rate anhand des Deltas zwischen zwei getStats()
-Aufrufen berechnen muss, um die entsprechende Rate (z. B. Bitrate) zu ermitteln. Beispiel:
// Periodically (e.g. every second or every 10 seconds)...
const currReport = await pc.getStats();
// Calculate bitrate since the last getStats() call.
// Handling of undefined is omitted for clarity.
const currOutboundRtp = currReport.values().find(s => s.type == 'outbound-rtp');
const prevOutboundRtp = prevReport.get(currOutboundRtp.id);
const deltaBits = (currOutboundRtp.bytesSent - prevOutboundRtp.bytesSent) * 8;
const deltaSeconds = (currOutboundRtp.timestamp - prevOutboundRtp.timestamp) / 1000;
logBitrateMeasurement(deltaBits / deltaSeconds);
// Remember the report for next time.
prevReport = currReport;
Raten und Durchschnittswerte selbst so berechnen zu müssen, mag wie ein lästiger zusätzlicher Schritt erscheinen, hat aber den Vorteil, dass Sie Durchschnittswerte für jedes gewünschte Zeitintervall ermitteln können. Wenn Sie die Standard-API seltener aufrufen als mit der Legacy-API, ergeben sich einige Leistungsvorteile.
Alter Messwert
googCertificate |
Standardmäßige Korrespondenz
certificate |
---|---|
.googFingerprint
|
.fingerprint
|
.googFingerprintAlgorithm
|
.fingerprintAlgorithm
|
.googDerBase64
|
.base64Certificate
|
Alter Messwert
googComponent |
Standardmäßige Korrespondenz
transport |
---|---|
.localCertificateId
|
.localCertificateId
|
.remoteCertificateId
|
.remoteCertificateId
|
.selectedCandidatePairId
|
.selectedCandidatePairId
|
.dtlsCipher
|
.dtlsCipher
|
.srtpCipher
|
.srtpCipher
|
Alter Messwert
localcandidate |
Standardmäßige Korrespondenz
local-candidate oder candidate-pair |
---|---|
.stunKeepaliveRequestsSent
|
candidate-pair.requestsSent (Reverse-Lookup candidate-pair über candidate-pair.localCandidateId ) |
.portNumber
|
local-candidate.port
|
.networkType
|
local-candidate.networkType
|
.ipAddress
|
local-candidate.address
|
.stunKeepaliveResponsesReceived
|
candidate-pair.responsesReceived
|
.stunKeepaliveRttTotal
|
candidate-pair.totalRoundTripTime
|
.transport
|
local-candidate.protocol
|
.candidateType
|
local-candidate.candidateType
|
.priority
|
local-candidate.priority
|
Alter Messwert
remotecandidate |
Standardmäßige Korrespondenz
remote-candidate |
---|---|
Wie bei localcandidate oben. |
Wie bei local-candidate oben. |
Alter Messwert
googCandidatePair |
Standardmäßige Korrespondenz
candidate-pair |
---|---|
.responsesSent
|
candidate-pair.responsesSent
|
.requestsReceived
|
candidate-pair.requestsReceived
|
.googRemoteCandidateType
|
remote-candidate.candidateType ( remote-candidate über candidate-pair.remoteCandidateId suchen) |
.googReadable
|
googReadable ist ein boolescher Wert, der angibt, ob candidate-pair.requestsReceived oder candidate-pair.responsesReceived vor Kurzem erhöht wurde
|
.googLocalAddress
|
local-candidate.address ( local-candidate über candidate-pair.localCandidateId suchen) |
.consentRequestsSent
|
candidate-pair.consentRequestsSent
|
.googTransportType
|
Wie bei local-candidate.protocol und remote-candidate.protocol . |
.googChannelId
|
candidate-pair.transportId
|
.googLocalCandidateType
|
local-candidate.candidateType
|
.googWritable
|
googWritable ist ein boolescher Wert, der angibt, ob candidate-pair.responsesReceived vor Kurzem erhöht wurde
|
.googRemoteAddress
|
remote-candidate.address
|
.googRtt
|
candidate-pair.currentRoundTripTime
|
.googActiveConnection
|
Die aktive Verbindung bezieht sich auf das Kandidatenpaar, das derzeit durch den Transport ausgewählt wird, z. B. wenn candidate-pair.id == transport.selectedCandidatePairId |
.packetsDiscardedOnSend
|
candidate-pair.packetsDiscardedOnSend
|
.bytesReceived
|
candidate-pair.bytesReceived
|
.responsesReceived
|
candidate-pair.responsesReceived
|
.remoteCandidateId
|
candidate-pair.remoteCandidateId
|
.localCandidateId
|
candidate-pair.localCandidateId
|
.bytesSent
|
candidate-pair.bytesSent
|
.packetsSent
|
candidate-pair.packetsSent
|
.bytesReceived
|
candidate-pair.bytesReceived
|
.bytesReceived
|
candidate-pair.bytesReceived
|
Alter Messwert
ssrc |
Standardmäßige Korrespondenz
, inbound-rtp , outbound-rtp , media-source |
---|---|
.audioInputLevel
|
media-source.audioLevel . Der Legacy-Messwert liegt im Bereich [0–32768], der Standard-Messwert jedoch im Bereich [0–1]. |
.audioOutputLevel
|
inbound-rtp.audioLevel . Der Legacy-Messwert liegt im Bereich [0...32768], aber der Standard-Messwert liegt im Bereich [0–1]. |
.packetsLost
|
inbound-rtp.packetsLost
|
.googTrackId
|
media-source.trackIdentifier für lokale MediaStreamTrack und inbound-rtp.trackIdentifier für entfernte MediaStreamTrack s |
.googRtt
|
remote-inbound-rtp.roundTripTime (siehe outbound-rtp.remoteId ) |
.googEchoCancellationReturnLossEnhancement
|
inbound-rtp.echoReturnLossEnhancement
|
.googCodecName
|
Der Codec-Name ist der Subtyp von "type/subtype". MIME-Typ, codec.mimeType (siehe inbound-rtp.codecId und outbound-rtp.codecId ) |
.transportId
|
inbound-rtp.transportId und outbound-rtp.transportId |
.mediaType
|
inbound-rtp.kind und outbound-rtp.kind oder media-source.kind
|
.googEchoCancellationReturnLoss
|
inbound-rtp.echoReturnLoss
|
.totalAudioEnergy
|
inbound-rtp.totalAudioEnergy und media-source.totalAudioEnergy
|
ssrc.totalSamplesDuration
|
inbound-rtp.totalSamplesDuration und media-source.totalSamplesDuration
|
.ssrc
|
inbound-rtp.ssrc und outbound-rtp.ssrc
|
.googJitterReceived
|
inbound-rtp.jitter
|
.packetsSent
|
outbound-rtp.packetsSent
|
.bytesSent
|
outbound-rtp.bytesSent
|
.googContentType
|
inbound-rtp.contentType und outbound-rtp.contentType |
.googFrameWidthInput
|
media-source.width
|
.googFrameHeightInput
|
media-source.height
|
.googFrameRateInput
|
media-source.framesPerSecond
|
.googFrameWidthSent
|
outbound-rtp.frameWidth
|
.googFrameHeightSent
|
outbound-rtp.frameHeight
|
.googFrameRateSent
|
Während die Sende-fps die Änderungsrate von outbound-rtp.framesSent ist, wird sie tatsächlich als outbound-rtp.framesPerSecond implementiert, das die Framerate codiert. |
.googFrameWidthReceived
|
inbound-rtp.frameWidth
|
.googFrameHeightReceived
|
inbound-rtp.frameHeight
|
.googFrameRateDecoded
|
Die Änderungsrate von inbound-rtp.framesDecoded |
.googFrameRateOutput
|
Änderungsrate von inbound-rtp.framesDecoded bis inbound-rtp.framesDropped |
.hugeFramesSent
|
outbound-rtp.hugeFramesSent
|
.qpSum
|
|
.framesEncoded
|
outbound-rtp.framesEncoded
|
.googAvgEncodeMs
|
|
.codecImplementationName
|
|
.googCpuLimitedResolution
|
„True“, wenn outbound-rtp.qualityLimitationReason == "cpu" |
.googBandwidthLimitedResolution
|
„True“, wenn outbound-rtp.qualityLimitationReason == "bandwidth" |
.googAdaptationChanges
|
Mit dem alten Messwert wird gezählt, wie oft die Auflösung oder Framerate aus qualityLimitationReason -bezogenen Gründen geändert wurde. Dies könnte aus anderen Messwerten abgeleitet werden (z.B. wenn sich die Auflösung oder Framerate für das Senden von der Auflösung oder Framerate der Quelle unterscheidet), aber die Dauer, die wir beschränkt haben (outbound-rtp.qualityLimitationDurations ), kann nützlicher sein als die Häufigkeit, mit der Auflösung oder Framerate geändert wurde. |
.googNacksReceived
|
inbound-rtp.nackCount
|
.googNacksSent
|
inbound-rtp.nackCount
|
.googPlisReceived
|
inbound-rtp.pliCount
|
.googPlisSent
|
inbound-rtp.pliCount
|
.googFirsReceived
|
inbound-rtp.firCount
|
.googFirsSent
|
inbound-rtp.firCount
|
.googSecondaryDecodedRate
|
Das aktuelle Verhältnis von Paketen mit Fehlerkorrektur: inbound-rtp.fecPacketsReceived –inbound-rtp.fecPacketsDiscarded |
.packetsReceived
|
inbound-rtp.packetsReceived
|
.googJitterBufferMs
|
inbound-rtp.jitterBufferDelay /inbound-rtp.jitterBufferEmittedCount
|
.googTargetDelayMs (Video) |
inbound-rtp.jitterBufferTargetDelay /inbound-rtp.jitterBufferEmittedCount
|
.googPreferredJitterBufferMs (Audio) |
inbound-rtp.jitterBufferTargetDelay /inbound-rtp.jitterBufferEmittedCount
|
.googExpandRate
|
Das aktuelle Verhältnis der ausgeblendeten Stichproben: inbound-rtp.concealedSamples / inbound-rtp.totalSamplesReceived |
.googSpeechExpandRate
|
Das aktuelle Verhältnis der verborgenen Samples, während der Stream nicht stummgeschaltet war: (inbound-rtp.concealedSamples –inbound-rtp.silentConcealedSamples ) / inbound-rtp.concealedSamples |
.googAccelerateRate
|
Das aktuelle Verhältnis der Samples, die verworfen wurden, um die Wiedergabegeschwindigkeit zu erhöhen: inbound-rtp.removedSamplesForAcceleration / inbound-rtp.totalSamplesReceived |
.googPreemptiveExpandRate
|
Das aktuelle Verhältnis von Samples, die synthetisiert wurden, um die Wiedergabegeschwindigkeit zu verlangsamen: inbound-rtp.insertedSamplesForDeceleration / inbound-rtp.totalSamplesReceived |
.googSecondaryDiscardedRate
|
inbound-rtp.fecPacketsDiscarded
|
.bytesReceived
|
inbound-rtp.bytesReceived
|
s.googCurrentDelayMs
|
inbound-rtp.jitterBufferDelay + media-playout.totalPlayoutDelay
|
.googDecodeMs
|
inbound-rtp.totalDecodeTime /inbound-rtp.framesDecoded
|
.googTimingFrameInfo
|
Der einzige verbleibende goog-Messwert. inbound-rtp.googTimingFrameInfo |
.framesDecoded
|
inbound-rtp.framesDecoded
|
Alter Messwert
VideoBwe |
Standardmäßige Korrespondenz
outbound-rtp und candidate-pair |
---|---|
.googTargetEncBitrate
|
outbound-rtp.targetBitrate als momentaner Wert oder outbound-rtp.totalEncodedBytesTarget / outbound-rtp.framesEncoded als Durchschnittswert |
.googActualEncBitrate
|
Die vom Encoder erzeugten Byte sind die Nutzlastbyte ohne erneute Übertragungen: die Änderungsrate von outbound-rtp.bytesSent zu outbound-rtp.retransmittedBytesSent . |
.googBucketDelay
|
outbound-rtp.totalPacketSendDelay /outbound-rtp.packetsSent
|
.googTransmitBitrate
|
Die Änderungsrate von outbound-rtp.headerBytesSent + outbound-rtp.bytesSent für die Bitrate pro RTP-Stream, candidate-pair.bytesSent für die Bitrate pro ICE-Kandidat oder transport.bytesSent für die Bitrate pro Transportunternehmen |
.googRetransmitBitrate
|
Änderungsbereich von outbound-rtp.retransmittedBytesSent |
.googAvailableSendBandwidth
|
candidate-pair.availableOutgoingBitrate
|
.googAvailableReceiveBandwidth
|
candidate-pair.availableIncomingBitrate
|
Die Standard-API ist simulcast-fähig.
Wenn Sie Simulcast verwenden, haben Sie vielleicht bemerkt, dass die alte API nur einen einzelnen SSRC meldet, selbst wenn Sie mithilfe von Simulcast drei RTP-Streams über drei separate SSRCs senden.
Die Standard-API nutzt diese Einschränkung nicht und gibt drei outbound-rtp
-Statistikobjekte zurück, eines für jeden der SSRCs. Das bedeutet, dass Sie jeden RTP-Stream einzeln analysieren können. Es bedeutet aber auch, dass Sie die Gesamtbitrate aller RTP-Sendestreams selbst aggregieren müssen, um die Gesamtbitrate aller RTP-Sendestreams zu ermitteln.
SVC- oder RTP-Streams mit mehreren räumlichen Ebenen, die über die scalabilityMode
API konfiguriert wurden, werden hingegen als eine einzelne outbound-rtp
angezeigt, da sie über einen einzelnen SSRC gesendet werden.
Wenn Sie mehr Zeit für die Migration benötigen
Wenn die alte API in Chrome 117 entfernt wird, wird bei ihrer Verwendung eine Ausnahme generiert. Wenn Sie Ihren Code nicht rechtzeitig migrieren können, gibt der Ursprungstest für die RTCPeerConnection-Callback-basierte getStats() API registrierten Websites mehr Zeit für die Migration. Mit einem Ursprungstesttoken kann die alte getStats() API bis Chrome 121 weiterhin verwendet werden.