@observertc/client-monitor-js
Version:
ObserveRTC Client Integration Javascript Library
1 lines • 21.6 kB
JavaScript
import t from"eventemitter3";import{Detectors as e}from"../detectors/Detectors";import*as i from"../schema/W3cStatsIdentifiers";import{InboundRtpMonitor as n}from"./InboundRtpMonitor";import{RemoteOutboundRtpMonitor as a}from"./RemoteOutboundRtpMonitor";import{OutboundRtpMonitor as o}from"./OutboundRtpMonitor";import{RemoteInboundRtpMonitor as s}from"./RemoteInboundRtpMonitor";import{MediaSourceMonitor as r}from"./MediaSourceMonitor";import{CodecMonitor as d}from"./CodecMonitor";import{MediaPlayoutMonitor as c}from"./MediaPlayoutMonitor";import{PeerConnectionTransportMonitor as p}from"./PeerConnectionTransportMonitor";import{IceTransportMonitor as h}from"./IceTransportMonitor";import{IceCandidateMonitor as u}from"./IceCandidateMonitor";import{IceCandidatePairMonitor as l}from"./IceCandidatePairMonitor";import{CertificateMonitor as m}from"./CertificateMonitor";import{DataChannelMonitor as M}from"./DataChannelMonitor";import{LongPcConnectionEstablishmentDetector as g}from"../detectors/LongPcConnectionEstablishment";import{CongestionDetector as v}from"../detectors/CongestionDetector";import{InboundTrackMonitor as b}from"./InboundTrackMonitor";import{OutboundTrackMonitor as S}from"./OutboundTrackMonitor";import{IceTupleChangeDetector as I}from"../detectors/IceTupleChangeDetector";import{IceConnectivityDetector as R}from"../detectors/IceConnectivityDetector";import{StatsAdapters as f}from"../adapters/StatsAdapters";import{SelectedIcePath as C}from"./SelectedIcePath";const k="PeerConnectionMonitor";export class PeerConnectionMonitor extends t{peerConnectionId;statsCollector;parent;logger;attachments;statsAdapters;detectors;mappedCodecMonitors=new Map;mappedInboundRtpMonitors=new Map;mappedRemoteOutboundRtpMonitors=new Map;mappedOutboundRtpMonitors=new Map;mappedDataChannelMonitors=new Map;mappedRemoteInboundRtpMonitors=new Map;mappedMediaSourceMonitors=new Map;mappedMediaPlayoutMonitors=new Map;mappedPeerConnectionTransportMonitors=new Map;mappedIceTransportMonitors=new Map;mappedIceCandidateMonitors=new Map;mappedIceCandidatePairMonitors=new Map;mappedCertificateMonitors=new Map;mappedSelectedIcePaths=new Map;_pendingMediaStreamTracks=new Map;mappedInboundTracks=new Map;mappedOutboundTracks=new Map;closed=!1;sendingAudioBitrate=0;sendingVideoBitrate=0;receivingAudioBitrate=0;receivingVideoBitrate=0;outboundFractionLost=0;inboundFractionalLost=0;totalInboundPacketsLost=0;totalInboundPacketsReceived=0;totalOutboundPacketsSent=0;totalOutboundPacketsReceived=0;totalOutboundPacketsLost=0;totalDataChannelBytesSent=0;totalDataChannelBytesReceived=0;totalSentAudioBytes=0;totalSentVideoBytes=0;totalReceivedAudioBytes=0;totalReceivedVideoBytes=0;totalAvailableIncomingBitrate=0;totalAvailableOutgoingBitrate=0;deltaInboundPacketsLost=0;deltaInboundPacketsReceived=0;deltaOutboundPacketsSent=0;deltaOutboundPacketsReceived=0;deltaOutboundPacketsLost=0;deltaAudioBytesSent=0;deltaVideoBytesSent=0;deltaAudioBytesReceived=0;deltaVideoBytesReceived=0;deltaDataChannelBytesReceived=0;deltaDataChannelBytesSent=0;highestSeenSendingBitrate;highestSeenReceivingBitrate;highestSeenAvailableOutgoingBitrate;highestSeenAvailableIncomingBitrate;congested=!1;iceRttInSec;ewmaIceRttInSec;rtcpRttInSec;ewmaRtcpRttInSec;connectingStartedAt;connectedAt;_connectionState;iceState;usingTURN;usingTCP;calculatedStabilityScore={weight:1,value:void 0};appData;constructor(t,i,n,a,o){super(),this.peerConnectionId=t,this.statsCollector=i,this.parent=n,this.logger=a,this.attachments=o,this.statsAdapters=new f(a),this.detectors=new e,null!==n.config.longPcConnectionEstablishmentDetector&&this.detectors.add(new g(this)),null!==n.config.congestionDetector&&this.detectors.add(new v(this)),this.detectors.add(new I(this)),null!==n.config.iceConnectivityDetector&&this.detectors.add(new R(this))}get avgRttInSec(){return this.rtcpRttInSec??this.iceRttInSec}get ewmaRttInSec(){return void 0!==this.rtcpRttInSec?this.ewmaRtcpRttInSec:this.ewmaIceRttInSec}get score(){return this.calculatedStabilityScore.value}get scoreReasons(){return this.calculatedStabilityScore.reasons}get receivingBitrate(){return(this.receivingAudioBitrate??0)+(this.receivingVideoBitrate??0)}get sendingBitrate(){return(this.sendingAudioBitrate??0)+(this.sendingVideoBitrate??0)}get tracks(){return[...this.mappedInboundTracks.values(),...this.mappedOutboundTracks.values()]}on(t,e){return super.on(t,e),this}once(t,e){return super.once(t,e),this}off(t,e){return super.off(t,e),this}emit(t,...e){return super.emit(t,...e)}async collect(){let t=await this.statsCollector.getStats();return t=this.statsAdapters.adapt(t),this.emit("stats",t),this._acceptAdaptedStats(t),t}accept(t){this._acceptAdaptedStats(this.statsAdapters.adapt(t))}_acceptAdaptedStats(t){const e=[],n=[];this.deltaVideoBytesSent=0,this.deltaAudioBytesSent=0,this.deltaVideoBytesReceived=0,this.deltaAudioBytesReceived=0,this.deltaDataChannelBytesReceived=0,this.deltaDataChannelBytesSent=0,this.deltaOutboundPacketsLost=0,this.deltaOutboundPacketsReceived=0,this.deltaOutboundPacketsSent=0,this.deltaInboundPacketsLost=0,this.deltaInboundPacketsReceived=0,this.sendingAudioBitrate=0,this.sendingVideoBitrate=0,this.receivingAudioBitrate=0,this.receivingVideoBitrate=0,this.outboundFractionLost=0,this.inboundFractionalLost=0,this.totalAvailableIncomingBitrate=0,this.totalAvailableOutgoingBitrate=0;for(let a=0,o=t;a<2&&0<o.length;++a){for(const t of o)switch(t.type){case i.StatsType.codec:this._updateCodec(t);break;case i.StatsType.inboundRtp:{const e=this._updateInboundRtp(t);switch(e?.kind){case"audio":this.receivingAudioBitrate+=e?.bitrate??0,this.deltaAudioBytesReceived+=e?.deltaBytesReceived??0;break;case"video":this.receivingVideoBitrate+=e?.bitrate??0,this.deltaVideoBytesReceived+=e?.deltaBytesReceived??0}this.inboundFractionalLost+=e?.deltaFractionLost??0,this.deltaInboundPacketsLost+=e?.deltaPacketsLost??0,this.deltaInboundPacketsReceived+=e?.deltaPacketsReceived??0;break}case i.StatsType.remoteOutboundRtp:{const i=this._updateRemoteOutboundRtp(t);void 0!==i?.roundTripTime&&e.push(i.roundTripTime);break}case i.StatsType.outboundRtp:{const e=this._updateOutboundRtp(t);switch(e?.kind){case"audio":this.sendingAudioBitrate+=e?.bitrate??0,this.deltaAudioBytesSent+=e?.deltaBytesSent??0;break;case"video":this.sendingVideoBitrate+=e?.bitrate??0,this.deltaVideoBytesSent+=e?.deltaBytesSent??0}this.deltaOutboundPacketsSent+=e?.deltaPacketsSent??0;break}case i.StatsType.remoteInboundRtp:{const i=this._updateRemoteInboundRtp(t);void 0!==i?.roundTripTime&&e.push(i.roundTripTime),this.outboundFractionLost+=i?.deltaFractionLost??0,this.deltaOutboundPacketsLost+=i?.deltaPacketsLost??0,this.deltaOutboundPacketsReceived+=i?.deltaPacketsReceived??0;break}case i.StatsType.dataChannel:{const e=this._updateDataChannel(t);this.deltaDataChannelBytesSent+=e?.deltaBytesSent??0,this.deltaDataChannelBytesReceived+=e?.deltaBytesReceived??0;break}case i.StatsType.mediaSource:this._updateMediaSource(t);break;case i.StatsType.mediaPlayout:this._updateMediaPlayout(t);break;case i.StatsType.transport:{const e=this._updateIceTransport(t),i=e?.getSelectedCandidatePair();this.totalAvailableIncomingBitrate+=i?.availableIncomingBitrate??0,this.totalAvailableOutgoingBitrate+=i?.availableOutgoingBitrate??0;const a=i?.avgRoundTripTimeInSec??i?.currentRoundTripTime;void 0!==a&&n.push(a);break}case i.StatsType.peerConnection:this._updatePeerConnectionTransport(t);break;case i.StatsType.localCandidate:case i.StatsType.remoteCandidate:this._updateIceCandidate(t);break;case i.StatsType.candidatePair:this._updateIceCandidatePair(t);break;case i.StatsType.certificate:this._updateCertificate(t);break;default:this.logger.debug(`[${k}]:`,"Unknown stats type",t)}o=this.statsAdapters.postAdapt(o)}this._checkVisited(),0<e.length&&(this.rtcpRttInSec=e.reduce(((t,e)=>t+e),0)/e.length,this.ewmaRtcpRttInSec=void 0!==this.ewmaRtcpRttInSec?.1*this.rtcpRttInSec+.9*this.ewmaRtcpRttInSec:this.rtcpRttInSec),0<n.length&&(this.iceRttInSec=n.reduce(((t,e)=>t+e),0)/n.length,this.ewmaIceRttInSec=void 0!==this.ewmaIceRttInSec?.1*this.iceRttInSec+.9*this.ewmaIceRttInSec:this.iceRttInSec),this.highestSeenAvailableIncomingBitrate=Math.max(this.highestSeenAvailableIncomingBitrate??0,this.totalAvailableIncomingBitrate),this.highestSeenAvailableOutgoingBitrate=Math.max(this.highestSeenAvailableOutgoingBitrate??0,this.totalAvailableOutgoingBitrate),this.highestSeenSendingBitrate=Math.max(this.highestSeenSendingBitrate??0,this.sendingAudioBitrate+this.sendingVideoBitrate),this.highestSeenReceivingBitrate=Math.max(this.highestSeenReceivingBitrate??0,this.receivingAudioBitrate+this.receivingVideoBitrate);const a=this.selectedIceCandidatePairs;this._updateSelectedIcePaths(a),this.usingTCP=a.some((t=>t.usingTcp)),this.usingTURN=a.some((t=>t.usingTurn)),this.iceState=a?.[0]?.getIceTransport()?.iceState,this.totalDataChannelBytesReceived+=this.deltaDataChannelBytesReceived,this.totalDataChannelBytesSent+=this.deltaDataChannelBytesSent,this.totalSentAudioBytes+=this.deltaAudioBytesSent,this.totalSentVideoBytes+=this.deltaVideoBytesSent,this.totalReceivedAudioBytes+=this.deltaAudioBytesReceived,this.totalReceivedVideoBytes+=this.deltaVideoBytesReceived,this.totalOutboundPacketsSent+=this.deltaOutboundPacketsSent,this.totalOutboundPacketsReceived+=this.deltaOutboundPacketsReceived,this.totalOutboundPacketsLost+=this.deltaOutboundPacketsLost,this.totalInboundPacketsLost+=this.deltaInboundPacketsLost,this.totalInboundPacketsReceived+=this.deltaInboundPacketsReceived,this.detectors.update(),this.emit("update")}createSample(){return{peerConnectionId:this.peerConnectionId,attachments:this.attachments,codecs:this.codecs.map((t=>t.createSample())),inboundRtps:this.inboundRtps.map((t=>t.createSample())),remoteOutboundRtps:this.remoteOutboundRtps.map((t=>t.createSample())),outboundRtps:this.outboundRtps.map((t=>t.createSample())),remoteInboundRtps:this.remoteInboundRtps.map((t=>t.createSample())),mediaSources:this.mediaSources.map((t=>t.createSample())),mediaPlayouts:this.mediaPlayouts.map((t=>t.createSample())),peerConnectionTransports:this.peerConnectionTransports.map((t=>t.createSample())),dataChannels:this.dataChannels.map((t=>t.createSample())),iceTransports:this.iceTransports.map((t=>t.createSample())),iceCandidates:this.iceCandidates.map((t=>t.createSample())),iceCandidatePairs:this.iceCandidatePairs.map((t=>t.createSample())),certificates:this.certificates.map((t=>t.createSample())),inboundTracks:[...this.mappedInboundTracks.values()].map((t=>t.createSample())),outboundTracks:[...this.mappedOutboundTracks.values()].map((t=>t.createSample())),score:this.score,scoreReasons:this.parent.scoreCalculator.encodePeerConnectionScoreReasons?.(this.calculatedStabilityScore.reasons)}}addMediaStreamTrack(t,e){if("ended"===t.readyState)return;t.addEventListener("ended",(()=>{this._pendingMediaStreamTracks.delete(t.id),this.mappedInboundTracks.delete(t.id),this.mappedOutboundTracks.delete(t.id)}));const i=this.mediaSources.find((e=>e.trackIdentifier===t.id));if(i)return this._createOutboundTrackMonitor(t,i,e);const n=this.inboundRtps.find((e=>e.trackIdentifier===t.id));if(n)return this._createInboundTrackMonitor(t,n,e);this._pendingMediaStreamTracks.set(t.id,{track:t,attachments:e})}get codecs(){return[...this.mappedCodecMonitors.values()]}get inboundRtps(){return[...this.mappedInboundRtpMonitors.values()]}get remoteOutboundRtps(){return[...this.mappedRemoteOutboundRtpMonitors.values()]}get outboundRtps(){return[...this.mappedOutboundRtpMonitors.values()]}get remoteInboundRtps(){return[...this.mappedRemoteInboundRtpMonitors.values()]}get mediaSources(){return[...this.mappedMediaSourceMonitors.values()]}get mediaPlayouts(){return[...this.mappedMediaPlayoutMonitors.values()]}get dataChannels(){return[...this.mappedDataChannelMonitors.values()]}get peerConnectionTransports(){return[...this.mappedPeerConnectionTransportMonitors.values()]}get iceTransports(){return[...this.mappedIceTransportMonitors.values()]}get iceCandidates(){return[...this.mappedIceCandidateMonitors.values()]}get iceCandidatePairs(){return[...this.mappedIceCandidatePairMonitors.values()]}get certificates(){return[...this.mappedCertificateMonitors.values()]}get selectedIcePaths(){return[...this.mappedSelectedIcePaths.values()]}get selectedIcePath(){for(const t of this.mappedSelectedIcePaths.values())return t}get selectedIceCandidatePairs(){return this.iceTransports.map((t=>t.getSelectedCandidatePair())).filter((t=>void 0!==t))}set connectionState(t){this._connectionState!==t&&(this._connectionState=t,"connecting"===t?this.connectingStartedAt=Date.now():"connected"===t?this.connectedAt=Date.now():(this.connectingStartedAt=void 0,this.connectedAt=void 0))}get connectionState(){return this._connectionState}_updateSelectedIcePaths(t){const e=new Set;for(const i of t){const t=i.pathKey;e.add(t);const n=this.mappedSelectedIcePaths.get(t);if(n){n.update(i);continue}const a=new C(t,i,this);this.mappedSelectedIcePaths.set(t,a),this.parent.emit("new-selected-ice-path",{clientMonitor:this.parent,peerConnectionMonitor:this,selectedIcePath:a}),a.notifyInitialSelection()}for(const[t,i]of[...this.mappedSelectedIcePaths.entries()])e.has(t)||(this.mappedSelectedIcePaths.delete(t),i.close())}_checkVisited(){for(const[t,e]of this.mappedCodecMonitors)e.visited||this.mappedCodecMonitors.delete(t);for(const[t,e]of this.mappedInboundRtpMonitors)e.visited||(this.mappedInboundRtpMonitors.delete(t),this.mappedInboundTracks.delete(e.trackIdentifier??""));for(const[t,e]of this.mappedRemoteOutboundRtpMonitors)e.visited||this.mappedRemoteOutboundRtpMonitors.delete(t);for(const[t,e]of this.mappedOutboundRtpMonitors)e.visited||(this.mappedOutboundRtpMonitors.delete(t),e.getTrack()?.mappedOutboundRtps.delete(e.ssrc));for(const[t,e]of this.mappedRemoteInboundRtpMonitors)e.visited||this.mappedRemoteInboundRtpMonitors.delete(t);for(const[t,e]of this.mappedMediaSourceMonitors)e.visited||(this.mappedMediaSourceMonitors.delete(t),this.mappedOutboundTracks.delete(e.trackIdentifier??""));for(const[t,e]of this.mappedMediaPlayoutMonitors)e.visited||this.mappedMediaPlayoutMonitors.delete(t);for(const[t,e]of this.mappedPeerConnectionTransportMonitors)e.visited||this.mappedPeerConnectionTransportMonitors.delete(t);for(const[t,e]of this.mappedIceTransportMonitors)e.visited||this.mappedIceTransportMonitors.delete(t);for(const[t,e]of this.mappedIceCandidateMonitors)e.visited||this.mappedIceCandidateMonitors.delete(t);for(const[t,e]of this.mappedIceCandidatePairMonitors)e.visited||this.mappedIceCandidatePairMonitors.delete(t);for(const[t,e]of this.mappedCertificateMonitors)e.visited||this.mappedCertificateMonitors.delete(t);for(const[t,e]of this.mappedDataChannelMonitors)e.visited||this.mappedDataChannelMonitors.delete(t)}close(){this.closed||(this.closed=!0,this.mappedSelectedIcePaths.forEach((t=>t.close())),this.mappedSelectedIcePaths.clear(),this._checkVisited(),this._checkVisited(),this.emit("close"))}_updateCodec(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.payloadType||void 0===t.mimeType)return this.logger.warn(`[${k}]:`,"Invalid codec stats",t);const e=t;let i=this.mappedCodecMonitors.get(e.id);i||(i=new d(this,e),this.mappedCodecMonitors.set(e.id,i),this.parent.emit("new-codec-monitor",{clientMonitor:this.parent,codecMonitor:i})),i.accept(e)}_updateInboundRtp(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.ssrc||void 0===t.kind||void 0===t.trackIdentifier)return this.logger.warn(`[${k}]:`,"Invalid inboundRtp stats",t);const e=t;let i=this.mappedInboundRtpMonitors.get(e.ssrc);if(!i&&(i=new n(this,e),this.mappedInboundRtpMonitors.set(e.ssrc,i),this.parent.emit("new-inbound-rtp-monitor",{clientMonitor:this.parent,inboundRtpMonitor:i}),e.trackIdentifier)){const t=this._pendingMediaStreamTracks.get(e.trackIdentifier);t&&this._createInboundTrackMonitor(t.track,i,t.attachments)}return i.accept(e),i}_updateDataChannel(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.label)return this.logger.warn(`[${k}]:`,"Invalid dataChannel stats",t);const e=t;let i=this.mappedDataChannelMonitors.get(e.id);return i||(i=new M(this,e),this.mappedDataChannelMonitors.set(e.id,i),this.parent.emit("new-data-channel-monitor",{clientMonitor:this.parent,dataChannelMonitor:i})),i.accept(e),i}_updateRemoteOutboundRtp(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.ssrc||void 0===t.kind)return this.logger.warn(`[${k}]:`,"Invalid remoteOutboundRtp stats",t);const e=t;let i=this.mappedRemoteOutboundRtpMonitors.get(e.ssrc);return i||(i=new a(this,e),this.mappedRemoteOutboundRtpMonitors.set(e.ssrc,i),this.parent.emit("new-remote-outbound-rtp-monitor",{clientMonitor:this.parent,remoteOutboundRtpMonitor:i})),i.accept(e),i}_updateOutboundRtp(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.ssrc||void 0===t.kind)return this.logger.warn(`[${k}]:`,"Invalid outboundRtp stats",t);const e=t;let i=this.mappedOutboundRtpMonitors.get(e.ssrc);if(!i){i=new o(this,e),this.mappedOutboundRtpMonitors.set(e.ssrc,i),this.parent.emit("new-outbound-rtp-monitor",{clientMonitor:this.parent,outboundRtpMonitor:i});const t=i.getTrack();t&&!t.mappedOutboundRtps.has(e.ssrc)&&t.mappedOutboundRtps.set(e.ssrc,i)}return i.accept(e),i}_updateRemoteInboundRtp(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.ssrc||void 0===t.kind)return this.logger.warn(`[${k}]:`,"Invalid remoteInboundRtp stats",t);const e=t;let i=this.mappedRemoteInboundRtpMonitors.get(e.ssrc);return i||(i=new s(this,e),this.mappedRemoteInboundRtpMonitors.set(e.ssrc,i),this.parent.emit("new-remote-inbound-rtp-monitor",{clientMonitor:this.parent,remoteInboundRtpMonitor:i})),i.accept(e),i}_updateMediaSource(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.trackIdentifier||void 0===t.kind)return this.logger.warn(`[${k}]:`,"Invalid mediaSource stats",t);const e=t;let i=this.mappedMediaSourceMonitors.get(e.id);if(!i&&(i=new r(this,e),this.mappedMediaSourceMonitors.set(e.id,i),this.parent.emit("new-media-source-monitor",{clientMonitor:this.parent,mediaSourceMonitor:i}),e.trackIdentifier)){const t=this._pendingMediaStreamTracks.get(e.trackIdentifier);t&&this._createOutboundTrackMonitor(t.track,i,t.attachments)}return i.accept(e),i}_updateMediaPlayout(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.kind)return this.logger.warn(`[${k}]:`,"Invalid mediaPlayout stats",t);const e=t;let i=this.mappedMediaPlayoutMonitors.get(e.id);return i||(i=new c(this,e),this.mappedMediaPlayoutMonitors.set(e.id,i),this.parent.emit("new-media-playout-monitor",{clientMonitor:this.parent,mediaPlayoutMonitor:i})),i.accept(e),i}_updatePeerConnectionTransport(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.dataChannelsOpened||void 0===t.dataChannelsClosed)return this.logger.warn(`[${k}]:`,"Invalid peerConnectionTransport stats",t);const e=t;let i=this.mappedPeerConnectionTransportMonitors.get(e.id);return i||(i=new p(this,e),this.mappedPeerConnectionTransportMonitors.set(e.id,i),this.parent.emit("new-peer-connection-transport-monitor",{clientMonitor:this.parent,peerConnectionTransportMonitor:i})),i.accept(e),i}_updateIceTransport(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp)return this.logger.warn(`[${k}]:`,"Invalid iceTransport stats",t);const e=t;let i=this.mappedIceTransportMonitors.get(e.id);return i||(i=new h(this,e),this.mappedIceTransportMonitors.set(e.id,i),this.parent.emit("new-ice-transport-monitor",{clientMonitor:this.parent,iceTransportMonitor:i})),i.accept(e),i}_updateIceCandidate(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.protocol)return this.logger.warn(`[${k}]:`,"Invalid iceCandidate stats",t);const e=t;let i=this.mappedIceCandidateMonitors.get(e.id);return i||(i=new u(this,e),this.mappedIceCandidateMonitors.set(e.id,i),this.parent.emit("new-ice-candidate-monitor",{clientMonitor:this.parent,iceCandidateMonitor:i})),i.accept(e),i}_updateIceCandidatePair(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.state)return this.logger.warn(`[${k}]:`,"Invalid iceCandidatePair stats",t);const e=t;let i=this.mappedIceCandidatePairMonitors.get(e.id);return i||(i=new l(this,e),this.mappedIceCandidatePairMonitors.set(e.id,i),this.parent.emit("new-ice-candidate-pair-monitor",{clientMonitor:this.parent,iceCandidatePairMonitor:i})),i.accept(e),i}_updateCertificate(t){if(this.closed)return;if(void 0===t.id||void 0===t.timestamp||void 0===t.fingerprint||void 0===t.fingerprintAlgorithm)return this.logger.warn(`[${k}]:`,"Invalid certificate stats",t);const e=t;let i=this.mappedCertificateMonitors.get(e.id);return i||(i=new m(this,e),this.mappedCertificateMonitors.set(e.id,i),this.parent.emit("new-certificate-monitor",{clientMonitor:this.parent,certificateMonitor:i})),i.accept(e),i}_createOutboundTrackMonitor(t,e,i){if(this.mappedOutboundTracks.has(t.id))return;const n=new S(t,e,i);this._pendingMediaStreamTracks.delete(t.id),this.mappedOutboundTracks.set(t.id,n);for(const e of this.mappedOutboundRtpMonitors.values())e.trackIdentifier===t.id&&n.mappedOutboundRtps.set(e.ssrc,e);this.parent.emit("new-outbound-track-monitor",{clientMonitor:this.parent,outboundTrackMonitor:n})}_createInboundTrackMonitor(t,e,i){if(this.mappedInboundTracks.has(t.id))return;const n=new b(t,e,i);this._pendingMediaStreamTracks.delete(t.id),this.mappedInboundTracks.set(t.id,n),this.parent.emit("new-inbound-track-monitor",{clientMonitor:this.parent,inboundTrackMonitor:n})}}