@webex/plugin-meetings 3.0.0-beta.13 → 3.0.0-beta.131
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/README.md +45 -1
- package/UPGRADING.md +9 -9
- package/browsers.js +19 -24
- package/dist/annotation/annotation.types.js +7 -0
- package/dist/annotation/annotation.types.js.map +1 -0
- package/dist/annotation/constants.js +48 -0
- package/dist/annotation/constants.js.map +1 -0
- package/dist/annotation/index.js +355 -0
- package/dist/annotation/index.js.map +1 -0
- package/dist/breakouts/breakout.js +193 -0
- package/dist/breakouts/breakout.js.map +1 -0
- package/dist/breakouts/collection.js +23 -0
- package/dist/breakouts/collection.js.map +1 -0
- package/dist/breakouts/edit-lock-error.js +52 -0
- package/dist/breakouts/edit-lock-error.js.map +1 -0
- package/dist/breakouts/events.js +43 -0
- package/dist/breakouts/events.js.map +1 -0
- package/dist/breakouts/index.js +994 -0
- package/dist/breakouts/index.js.map +1 -0
- package/dist/breakouts/request.js +78 -0
- package/dist/breakouts/request.js.map +1 -0
- package/dist/breakouts/utils.js +67 -0
- package/dist/breakouts/utils.js.map +1 -0
- package/dist/common/browser-detection.js +1 -20
- package/dist/common/browser-detection.js.map +1 -1
- package/dist/common/collection.js +5 -20
- package/dist/common/collection.js.map +1 -1
- package/dist/common/config.js +0 -7
- package/dist/common/config.js.map +1 -1
- package/dist/common/errors/captcha-error.js +5 -26
- package/dist/common/errors/captcha-error.js.map +1 -1
- package/dist/common/errors/intent-to-join.js +5 -26
- package/dist/common/errors/intent-to-join.js.map +1 -1
- package/dist/common/errors/join-meeting.js +6 -27
- package/dist/common/errors/join-meeting.js.map +1 -1
- package/dist/common/errors/media.js +5 -26
- package/dist/common/errors/media.js.map +1 -1
- package/dist/common/errors/parameter.js +5 -33
- package/dist/common/errors/parameter.js.map +1 -1
- package/dist/common/errors/password-error.js +5 -26
- package/dist/common/errors/password-error.js.map +1 -1
- package/dist/common/errors/permission.js +4 -25
- package/dist/common/errors/permission.js.map +1 -1
- package/dist/common/errors/reconnection-in-progress.js +0 -17
- package/dist/common/errors/reconnection-in-progress.js.map +1 -1
- package/dist/common/errors/reconnection.js +5 -26
- package/dist/common/errors/reconnection.js.map +1 -1
- package/dist/common/errors/stats.js +5 -26
- package/dist/common/errors/stats.js.map +1 -1
- package/dist/common/errors/webex-errors.js +6 -41
- package/dist/common/errors/webex-errors.js.map +1 -1
- package/dist/common/errors/webex-meetings-error.js +1 -24
- package/dist/common/errors/webex-meetings-error.js.map +1 -1
- package/dist/common/events/events-scope.js +0 -22
- package/dist/common/events/events-scope.js.map +1 -1
- package/dist/common/events/events.js +0 -23
- package/dist/common/events/events.js.map +1 -1
- package/dist/common/events/trigger-proxy.js +0 -12
- package/dist/common/events/trigger-proxy.js.map +1 -1
- package/dist/common/events/util.js +0 -15
- package/dist/common/events/util.js.map +1 -1
- package/dist/common/logs/logger-config.js +0 -4
- package/dist/common/logs/logger-config.js.map +1 -1
- package/dist/common/logs/logger-proxy.js +1 -8
- package/dist/common/logs/logger-proxy.js.map +1 -1
- package/dist/common/logs/request.js +35 -61
- package/dist/common/logs/request.js.map +1 -1
- package/dist/common/queue.js +4 -14
- package/dist/common/queue.js.map +1 -1
- package/dist/config.js +6 -6
- package/dist/config.js.map +1 -1
- package/dist/constants.js +203 -53
- package/dist/constants.js.map +1 -1
- package/dist/controls-options-manager/constants.js +14 -0
- package/dist/controls-options-manager/constants.js.map +1 -0
- package/dist/controls-options-manager/enums.js +27 -0
- package/dist/controls-options-manager/enums.js.map +1 -0
- package/dist/controls-options-manager/index.js +297 -0
- package/dist/controls-options-manager/index.js.map +1 -0
- package/dist/controls-options-manager/types.js +7 -0
- package/dist/controls-options-manager/types.js.map +1 -0
- package/dist/controls-options-manager/util.js +294 -0
- package/dist/controls-options-manager/util.js.map +1 -0
- package/dist/index.js +72 -17
- package/dist/index.js.map +1 -1
- package/dist/locus-info/controlsUtils.js +100 -29
- package/dist/locus-info/controlsUtils.js.map +1 -1
- package/dist/locus-info/embeddedAppsUtils.js +3 -26
- package/dist/locus-info/embeddedAppsUtils.js.map +1 -1
- package/dist/locus-info/fullState.js +0 -15
- package/dist/locus-info/fullState.js.map +1 -1
- package/dist/locus-info/hostUtils.js +4 -12
- package/dist/locus-info/hostUtils.js.map +1 -1
- package/dist/locus-info/index.js +406 -216
- package/dist/locus-info/index.js.map +1 -1
- package/dist/locus-info/infoUtils.js +0 -38
- package/dist/locus-info/infoUtils.js.map +1 -1
- package/dist/locus-info/mediaSharesUtils.js +54 -38
- package/dist/locus-info/mediaSharesUtils.js.map +1 -1
- package/dist/locus-info/parser.js +88 -123
- package/dist/locus-info/parser.js.map +1 -1
- package/dist/locus-info/selfUtils.js +105 -91
- package/dist/locus-info/selfUtils.js.map +1 -1
- package/dist/media/index.js +55 -165
- package/dist/media/index.js.map +1 -1
- package/dist/media/properties.js +71 -117
- package/dist/media/properties.js.map +1 -1
- package/dist/media/util.js +2 -9
- package/dist/media/util.js.map +1 -1
- package/dist/mediaQualityMetrics/config.js +505 -495
- package/dist/mediaQualityMetrics/config.js.map +1 -1
- package/dist/meeting/in-meeting-actions.js +77 -14
- package/dist/meeting/in-meeting-actions.js.map +1 -1
- package/dist/meeting/index.js +2603 -2462
- package/dist/meeting/index.js.map +1 -1
- package/dist/meeting/locusMediaRequest.js +291 -0
- package/dist/meeting/locusMediaRequest.js.map +1 -0
- package/dist/meeting/muteState.js +292 -138
- package/dist/meeting/muteState.js.map +1 -1
- package/dist/meeting/request.js +315 -336
- package/dist/meeting/request.js.map +1 -1
- package/dist/meeting/request.type.js +7 -0
- package/dist/meeting/request.type.js.map +1 -0
- package/dist/meeting/state.js +21 -31
- package/dist/meeting/state.js.map +1 -1
- package/dist/meeting/util.js +463 -583
- package/dist/meeting/util.js.map +1 -1
- package/dist/meeting-info/collection.js +3 -25
- package/dist/meeting-info/collection.js.map +1 -1
- package/dist/meeting-info/index.js +10 -33
- package/dist/meeting-info/index.js.map +1 -1
- package/dist/meeting-info/meeting-info-v2.js +305 -286
- package/dist/meeting-info/meeting-info-v2.js.map +1 -1
- package/dist/meeting-info/request.js +1 -16
- package/dist/meeting-info/request.js.map +1 -1
- package/dist/meeting-info/util.js +98 -183
- package/dist/meeting-info/util.js.map +1 -1
- package/dist/meeting-info/utilv2.js +156 -232
- package/dist/meeting-info/utilv2.js.map +1 -1
- package/dist/meetings/collection.js +24 -20
- package/dist/meetings/collection.js.map +1 -1
- package/dist/meetings/index.js +692 -593
- package/dist/meetings/index.js.map +1 -1
- package/dist/meetings/request.js +23 -42
- package/dist/meetings/request.js.map +1 -1
- package/dist/meetings/util.js +186 -155
- package/dist/meetings/util.js.map +1 -1
- package/dist/member/index.js +89 -88
- package/dist/member/index.js.map +1 -1
- package/dist/member/types.js +15 -0
- package/dist/member/types.js.map +1 -0
- package/dist/member/util.js +101 -69
- package/dist/member/util.js.map +1 -1
- package/dist/members/collection.js +12 -12
- package/dist/members/collection.js.map +1 -1
- package/dist/members/index.js +166 -205
- package/dist/members/index.js.map +1 -1
- package/dist/members/request.js +120 -85
- package/dist/members/request.js.map +1 -1
- package/dist/members/types.js +15 -0
- package/dist/members/types.js.map +1 -0
- package/dist/members/util.js +314 -260
- package/dist/members/util.js.map +1 -1
- package/dist/metrics/config.js +50 -16
- package/dist/metrics/config.js.map +1 -1
- package/dist/metrics/constants.js +4 -7
- package/dist/metrics/constants.js.map +1 -1
- package/dist/metrics/index.js +93 -162
- package/dist/metrics/index.js.map +1 -1
- package/dist/multistream/mediaRequestManager.js +167 -50
- package/dist/multistream/mediaRequestManager.js.map +1 -1
- package/dist/multistream/receiveSlot.js +58 -65
- package/dist/multistream/receiveSlot.js.map +1 -1
- package/dist/multistream/receiveSlotManager.js +74 -93
- package/dist/multistream/receiveSlotManager.js.map +1 -1
- package/dist/multistream/remoteMedia.js +55 -74
- package/dist/multistream/remoteMedia.js.map +1 -1
- package/dist/multistream/remoteMediaGroup.js +6 -40
- package/dist/multistream/remoteMediaGroup.js.map +1 -1
- package/dist/multistream/remoteMediaManager.js +466 -442
- package/dist/multistream/remoteMediaManager.js.map +1 -1
- package/dist/networkQualityMonitor/index.js +32 -59
- package/dist/networkQualityMonitor/index.js.map +1 -1
- package/dist/personal-meeting-room/index.js +10 -45
- package/dist/personal-meeting-room/index.js.map +1 -1
- package/dist/personal-meeting-room/request.js +2 -33
- package/dist/personal-meeting-room/request.js.map +1 -1
- package/dist/personal-meeting-room/util.js +0 -13
- package/dist/personal-meeting-room/util.js.map +1 -1
- package/dist/reachability/index.js +190 -199
- package/dist/reachability/index.js.map +1 -1
- package/dist/reachability/request.js +14 -23
- package/dist/reachability/request.js.map +1 -1
- package/dist/reactions/constants.js +13 -0
- package/dist/reactions/constants.js.map +1 -0
- package/dist/reactions/reactions.js +2 -4
- package/dist/reactions/reactions.js.map +1 -1
- package/dist/reactions/reactions.type.js +19 -23
- package/dist/reactions/reactions.type.js.map +1 -1
- package/dist/reconnection-manager/index.js +326 -465
- package/dist/reconnection-manager/index.js.map +1 -1
- package/dist/recording-controller/enums.js +17 -0
- package/dist/recording-controller/enums.js.map +1 -0
- package/dist/recording-controller/index.js +343 -0
- package/dist/recording-controller/index.js.map +1 -0
- package/dist/recording-controller/util.js +63 -0
- package/dist/recording-controller/util.js.map +1 -0
- package/dist/roap/index.js +31 -75
- package/dist/roap/index.js.map +1 -1
- package/dist/roap/request.js +129 -136
- package/dist/roap/request.js.map +1 -1
- package/dist/roap/turnDiscovery.js +143 -103
- package/dist/roap/turnDiscovery.js.map +1 -1
- package/dist/statsAnalyzer/global.js +1 -95
- package/dist/statsAnalyzer/global.js.map +1 -1
- package/dist/statsAnalyzer/index.js +369 -461
- package/dist/statsAnalyzer/index.js.map +1 -1
- package/dist/statsAnalyzer/mqaUtil.js +144 -94
- package/dist/statsAnalyzer/mqaUtil.js.map +1 -1
- package/dist/transcription/index.js +13 -45
- package/dist/transcription/index.js.map +1 -1
- package/dist/types/annotation/annotation.types.d.ts +35 -0
- package/dist/types/annotation/constants.d.ts +31 -0
- package/dist/types/annotation/index.d.ts +124 -0
- package/dist/types/breakouts/breakout.d.ts +8 -0
- package/dist/types/breakouts/collection.d.ts +5 -0
- package/dist/types/breakouts/edit-lock-error.d.ts +15 -0
- package/dist/types/breakouts/events.d.ts +2 -0
- package/dist/types/breakouts/index.d.ts +5 -0
- package/dist/types/breakouts/request.d.ts +22 -0
- package/dist/types/breakouts/utils.d.ts +15 -0
- package/dist/types/common/browser-detection.d.ts +9 -0
- package/dist/types/common/collection.d.ts +48 -0
- package/dist/types/common/config.d.ts +2 -0
- package/dist/types/common/errors/captcha-error.d.ts +15 -0
- package/dist/types/common/errors/intent-to-join.d.ts +16 -0
- package/dist/types/common/errors/join-meeting.d.ts +17 -0
- package/dist/types/common/errors/media.d.ts +15 -0
- package/dist/types/common/errors/parameter.d.ts +15 -0
- package/dist/types/common/errors/password-error.d.ts +15 -0
- package/dist/types/common/errors/permission.d.ts +14 -0
- package/dist/types/common/errors/reconnection-in-progress.d.ts +9 -0
- package/dist/types/common/errors/reconnection.d.ts +15 -0
- package/dist/types/common/errors/stats.d.ts +15 -0
- package/dist/types/common/errors/webex-errors.d.ts +69 -0
- package/dist/types/common/errors/webex-meetings-error.d.ts +20 -0
- package/dist/types/common/events/events-scope.d.ts +17 -0
- package/dist/types/common/events/events.d.ts +12 -0
- package/dist/types/common/events/trigger-proxy.d.ts +2 -0
- package/dist/types/common/events/util.d.ts +2 -0
- package/dist/types/common/logs/logger-config.d.ts +2 -0
- package/dist/types/common/logs/logger-proxy.d.ts +2 -0
- package/dist/types/common/logs/request.d.ts +34 -0
- package/dist/types/common/queue.d.ts +32 -0
- package/dist/types/config.d.ts +78 -0
- package/dist/types/constants.d.ts +993 -0
- package/dist/types/controls-options-manager/constants.d.ts +4 -0
- package/dist/types/controls-options-manager/enums.d.ts +15 -0
- package/dist/types/controls-options-manager/index.d.ts +136 -0
- package/dist/types/controls-options-manager/types.d.ts +43 -0
- package/dist/types/controls-options-manager/util.d.ts +1 -0
- package/dist/types/index.d.ts +7 -0
- package/dist/types/locus-info/controlsUtils.d.ts +2 -0
- package/dist/types/locus-info/embeddedAppsUtils.d.ts +2 -0
- package/dist/types/locus-info/fullState.d.ts +2 -0
- package/dist/types/locus-info/hostUtils.d.ts +2 -0
- package/dist/types/locus-info/index.d.ts +315 -0
- package/dist/types/locus-info/infoUtils.d.ts +2 -0
- package/dist/types/locus-info/mediaSharesUtils.d.ts +2 -0
- package/dist/types/locus-info/parser.d.ts +212 -0
- package/dist/types/locus-info/selfUtils.d.ts +2 -0
- package/dist/types/media/index.d.ts +34 -0
- package/dist/types/media/properties.d.ts +108 -0
- package/dist/types/media/util.d.ts +2 -0
- package/dist/types/mediaQualityMetrics/config.d.ts +365 -0
- package/dist/types/meeting/in-meeting-actions.d.ts +147 -0
- package/dist/types/meeting/index.d.ts +1762 -0
- package/dist/types/meeting/locusMediaRequest.d.ts +70 -0
- package/dist/types/meeting/muteState.d.ts +186 -0
- package/dist/types/meeting/request.d.ts +269 -0
- package/dist/types/meeting/request.type.d.ts +11 -0
- package/dist/types/meeting/state.d.ts +9 -0
- package/dist/types/meeting/util.d.ts +76 -0
- package/dist/types/meeting-info/collection.d.ts +20 -0
- package/dist/types/meeting-info/index.d.ts +57 -0
- package/dist/types/meeting-info/meeting-info-v2.d.ts +122 -0
- package/dist/types/meeting-info/request.d.ts +22 -0
- package/dist/types/meeting-info/util.d.ts +2 -0
- package/dist/types/meeting-info/utilv2.d.ts +2 -0
- package/dist/types/meetings/collection.d.ts +31 -0
- package/dist/types/meetings/index.d.ts +345 -0
- package/dist/types/meetings/request.d.ts +27 -0
- package/dist/types/meetings/util.d.ts +18 -0
- package/dist/types/member/index.d.ts +157 -0
- package/dist/types/member/types.d.ts +21 -0
- package/dist/types/member/util.d.ts +2 -0
- package/dist/types/members/collection.d.ts +29 -0
- package/dist/types/members/index.d.ts +353 -0
- package/dist/types/members/request.d.ts +114 -0
- package/dist/types/members/types.d.ts +24 -0
- package/dist/types/members/util.d.ts +210 -0
- package/dist/types/metrics/config.d.ts +195 -0
- package/dist/types/metrics/constants.d.ts +55 -0
- package/dist/types/metrics/index.d.ts +169 -0
- package/dist/types/multistream/mediaRequestManager.d.ts +101 -0
- package/dist/types/multistream/receiveSlot.d.ts +68 -0
- package/dist/types/multistream/receiveSlotManager.d.ts +56 -0
- package/dist/types/multistream/remoteMedia.d.ts +72 -0
- package/dist/types/multistream/remoteMediaGroup.d.ts +47 -0
- package/dist/types/multistream/remoteMediaManager.d.ts +263 -0
- package/dist/types/networkQualityMonitor/index.d.ts +70 -0
- package/dist/types/personal-meeting-room/index.d.ts +47 -0
- package/dist/types/personal-meeting-room/request.d.ts +14 -0
- package/dist/types/personal-meeting-room/util.d.ts +2 -0
- package/dist/types/reachability/index.d.ts +152 -0
- package/dist/types/reachability/request.d.ts +37 -0
- package/dist/types/reactions/constants.d.ts +3 -0
- package/dist/types/reactions/reactions.d.ts +4 -0
- package/dist/types/reactions/reactions.type.d.ts +52 -0
- package/dist/types/reconnection-manager/index.d.ts +126 -0
- package/dist/types/recording-controller/enums.d.ts +7 -0
- package/dist/types/recording-controller/index.d.ts +193 -0
- package/dist/types/recording-controller/util.d.ts +13 -0
- package/dist/types/roap/index.d.ts +77 -0
- package/dist/types/roap/request.d.ts +36 -0
- package/dist/types/roap/turnDiscovery.d.ts +91 -0
- package/dist/types/statsAnalyzer/global.d.ts +36 -0
- package/dist/types/statsAnalyzer/index.d.ts +200 -0
- package/dist/types/statsAnalyzer/mqaUtil.d.ts +24 -0
- package/dist/types/transcription/index.d.ts +64 -0
- package/internal-README.md +7 -6
- package/package.json +28 -21
- package/src/annotation/annotation.types.ts +42 -0
- package/src/annotation/constants.ts +36 -0
- package/src/annotation/index.ts +339 -0
- package/src/breakouts/README.md +220 -0
- package/src/breakouts/breakout.ts +163 -0
- package/src/breakouts/collection.ts +19 -0
- package/src/breakouts/edit-lock-error.ts +25 -0
- package/src/breakouts/events.ts +37 -0
- package/src/breakouts/index.ts +860 -0
- package/src/breakouts/request.ts +55 -0
- package/src/breakouts/utils.ts +57 -0
- package/src/common/browser-detection.ts +9 -6
- package/src/common/collection.ts +3 -1
- package/src/common/errors/captcha-error.ts +6 -6
- package/src/common/errors/intent-to-join.ts +6 -6
- package/src/common/errors/join-meeting.ts +12 -8
- package/src/common/errors/media.ts +6 -6
- package/src/common/errors/parameter.ts +9 -6
- package/src/common/errors/password-error.ts +6 -6
- package/src/common/errors/permission.ts +5 -5
- package/src/common/errors/reconnection.ts +6 -6
- package/src/common/errors/stats.ts +6 -6
- package/src/common/errors/webex-errors.ts +7 -5
- package/src/common/errors/webex-meetings-error.ts +1 -1
- package/src/common/events/events-scope.ts +5 -1
- package/src/common/events/events.ts +5 -1
- package/src/common/events/trigger-proxy.ts +8 -3
- package/src/common/events/util.ts +1 -2
- package/src/common/logs/logger-proxy.ts +21 -10
- package/src/common/logs/request.ts +11 -8
- package/src/config.ts +16 -12
- package/src/constants.ts +153 -7
- package/src/controls-options-manager/constants.ts +5 -0
- package/src/controls-options-manager/enums.ts +18 -0
- package/src/controls-options-manager/index.ts +278 -0
- package/src/controls-options-manager/types.ts +59 -0
- package/src/controls-options-manager/util.ts +281 -0
- package/src/index.ts +33 -0
- package/src/locus-info/controlsUtils.ts +142 -24
- package/src/locus-info/fullState.ts +15 -11
- package/src/locus-info/hostUtils.ts +4 -3
- package/src/locus-info/index.ts +346 -55
- package/src/locus-info/infoUtils.ts +12 -4
- package/src/locus-info/mediaSharesUtils.ts +52 -4
- package/src/locus-info/parser.ts +46 -68
- package/src/locus-info/selfUtils.ts +195 -56
- package/src/media/index.ts +139 -196
- package/src/media/properties.ts +43 -36
- package/src/media/util.ts +1 -1
- package/src/mediaQualityMetrics/config.ts +380 -378
- package/src/meeting/in-meeting-actions.ts +159 -3
- package/src/meeting/index.ts +2803 -1584
- package/src/meeting/locusMediaRequest.ts +309 -0
- package/src/meeting/muteState.ts +290 -72
- package/src/meeting/request.ts +247 -178
- package/src/meeting/request.type.ts +13 -0
- package/src/meeting/state.ts +45 -30
- package/src/meeting/util.ts +445 -395
- package/src/meeting-info/collection.ts +2 -1
- package/src/meeting-info/index.ts +32 -30
- package/src/meeting-info/meeting-info-v2.ts +235 -116
- package/src/meeting-info/request.ts +9 -3
- package/src/meeting-info/util.ts +54 -46
- package/src/meeting-info/utilv2.ts +71 -55
- package/src/meetings/collection.ts +21 -1
- package/src/meetings/index.ts +772 -437
- package/src/meetings/request.ts +29 -25
- package/src/meetings/util.ts +132 -33
- package/src/member/index.ts +95 -49
- package/src/member/types.ts +24 -0
- package/src/member/util.ts +106 -13
- package/src/members/collection.ts +8 -1
- package/src/members/index.ts +288 -130
- package/src/members/request.ts +144 -31
- package/src/members/types.ts +28 -0
- package/src/members/util.ts +316 -235
- package/src/metrics/config.ts +302 -90
- package/src/metrics/constants.ts +2 -6
- package/src/metrics/index.ts +124 -95
- package/src/multistream/mediaRequestManager.ts +203 -45
- package/src/multistream/receiveSlot.ts +69 -26
- package/src/multistream/receiveSlotManager.ts +62 -38
- package/src/multistream/remoteMedia.ts +30 -4
- package/src/multistream/remoteMediaGroup.ts +4 -3
- package/src/multistream/remoteMediaManager.ts +230 -66
- package/src/networkQualityMonitor/index.ts +24 -27
- package/src/personal-meeting-room/index.ts +12 -16
- package/src/personal-meeting-room/request.ts +10 -3
- package/src/personal-meeting-room/util.ts +3 -3
- package/src/reachability/index.ts +131 -79
- package/src/reachability/request.ts +43 -34
- package/src/reactions/constants.ts +4 -0
- package/src/reactions/reactions.ts +8 -8
- package/src/reactions/reactions.type.ts +31 -5
- package/src/reconnection-manager/index.ts +193 -111
- package/src/recording-controller/enums.ts +8 -0
- package/src/recording-controller/index.ts +315 -0
- package/src/recording-controller/util.ts +58 -0
- package/src/roap/index.ts +53 -53
- package/src/roap/request.ts +77 -64
- package/src/roap/turnDiscovery.ts +101 -48
- package/src/statsAnalyzer/global.ts +8 -104
- package/src/statsAnalyzer/index.ts +624 -376
- package/src/statsAnalyzer/mqaUtil.ts +203 -90
- package/src/transcription/index.ts +34 -32
- package/test/integration/spec/converged-space-meetings.js +177 -0
- package/test/integration/spec/journey.js +670 -466
- package/test/integration/spec/space-meeting.js +320 -204
- package/test/integration/spec/transcription.js +7 -8
- package/test/unit/spec/annotation/index.ts +433 -0
- package/test/unit/spec/breakouts/breakout.ts +203 -0
- package/test/unit/spec/breakouts/collection.ts +15 -0
- package/test/unit/spec/breakouts/edit-lock-error.ts +30 -0
- package/test/unit/spec/breakouts/events.ts +77 -0
- package/test/unit/spec/breakouts/index.ts +1609 -0
- package/test/unit/spec/breakouts/request.ts +104 -0
- package/test/unit/spec/breakouts/utils.js +72 -0
- package/test/unit/spec/common/browser-detection.js +9 -28
- package/test/unit/spec/controls-options-manager/index.js +287 -0
- package/test/unit/spec/controls-options-manager/util.js +504 -0
- package/test/unit/spec/fixture/locus.js +93 -90
- package/test/unit/spec/locus-info/controlsUtils.js +305 -32
- package/test/unit/spec/locus-info/embeddedAppsUtils.js +8 -6
- package/test/unit/spec/locus-info/index.js +636 -5
- package/test/unit/spec/locus-info/infoUtils.js +26 -33
- package/test/unit/spec/locus-info/lib/BasicSeqCmp.json +88 -430
- package/test/unit/spec/locus-info/lib/SeqCmp.json +513 -685
- package/test/unit/spec/locus-info/mediaSharesUtils.ts +22 -0
- package/test/unit/spec/locus-info/parser.js +3 -9
- package/test/unit/spec/locus-info/selfConstant.js +110 -103
- package/test/unit/spec/locus-info/selfUtils.js +252 -12
- package/test/unit/spec/media/index.ts +104 -8
- package/test/unit/spec/media/properties.ts +9 -9
- package/test/unit/spec/meeting/in-meeting-actions.ts +76 -3
- package/test/unit/spec/meeting/index.js +3112 -921
- package/test/unit/spec/meeting/locusMediaRequest.ts +436 -0
- package/test/unit/spec/meeting/muteState.js +421 -94
- package/test/unit/spec/meeting/request.js +421 -79
- package/test/unit/spec/meeting/utils.js +326 -189
- package/test/unit/spec/meeting-info/meetinginfov2.js +481 -76
- package/test/unit/spec/meeting-info/request.js +7 -9
- package/test/unit/spec/meeting-info/util.js +11 -12
- package/test/unit/spec/meeting-info/utilv2.js +131 -74
- package/test/unit/spec/meetings/collection.js +15 -1
- package/test/unit/spec/meetings/index.js +1126 -328
- package/test/unit/spec/meetings/utils.js +220 -14
- package/test/unit/spec/member/index.js +24 -1
- package/test/unit/spec/member/util.js +383 -32
- package/test/unit/spec/members/index.js +424 -55
- package/test/unit/spec/members/request.js +228 -40
- package/test/unit/spec/members/utils.js +191 -4
- package/test/unit/spec/metrics/index.js +113 -20
- package/test/unit/spec/multistream/mediaRequestManager.ts +650 -105
- package/test/unit/spec/multistream/receiveSlot.ts +76 -17
- package/test/unit/spec/multistream/receiveSlotManager.ts +69 -39
- package/test/unit/spec/multistream/remoteMedia.ts +32 -2
- package/test/unit/spec/multistream/remoteMediaGroup.ts +5 -5
- package/test/unit/spec/multistream/remoteMediaManager.ts +549 -65
- package/test/unit/spec/networkQualityMonitor/index.js +24 -18
- package/test/unit/spec/personal-meeting-room/personal-meeting-room.js +2 -7
- package/test/unit/spec/reachability/index.ts +176 -27
- package/test/unit/spec/reachability/request.js +66 -0
- package/test/unit/spec/reconnection-manager/index.js +62 -31
- package/test/unit/spec/recording-controller/index.js +231 -0
- package/test/unit/spec/recording-controller/util.js +102 -0
- package/test/unit/spec/roap/index.ts +19 -49
- package/test/unit/spec/roap/request.ts +187 -0
- package/test/unit/spec/roap/turnDiscovery.ts +92 -50
- package/test/unit/spec/stats-analyzer/index.js +116 -60
- package/test/utils/cmr.js +44 -42
- package/test/utils/constants.js +9 -0
- package/test/utils/integrationTestUtils.js +64 -0
- package/test/utils/testUtils.js +63 -99
- package/test/utils/webex-config.js +22 -18
- package/test/utils/webex-test-users.js +57 -50
- package/tsconfig.json +6 -0
- package/dist/media/internal-media-core-wrapper.js +0 -22
- package/dist/media/internal-media-core-wrapper.js.map +0 -1
- package/dist/meeting/effectsState.js +0 -334
- package/dist/meeting/effectsState.js.map +0 -1
- package/dist/multistream/multistreamMedia.js +0 -116
- package/dist/multistream/multistreamMedia.js.map +0 -1
- package/src/index.js +0 -15
- package/src/media/internal-media-core-wrapper.ts +0 -9
- package/src/meeting/effectsState.ts +0 -211
- package/src/multistream/multistreamMedia.ts +0 -92
- package/test/unit/spec/meeting/effectsState.js +0 -291
|
@@ -1,9 +1,24 @@
|
|
|
1
|
+
/* eslint-disable prefer-destructuring */
|
|
2
|
+
|
|
1
3
|
import {cloneDeep} from 'lodash';
|
|
2
|
-
import {
|
|
4
|
+
import {ConnectionState} from '@webex/internal-media-core';
|
|
3
5
|
|
|
4
6
|
import EventsScope from '../common/events/events-scope';
|
|
5
|
-
import {
|
|
6
|
-
|
|
7
|
+
import {
|
|
8
|
+
DEFAULT_GET_STATS_FILTER,
|
|
9
|
+
STATS,
|
|
10
|
+
MQA_INTEVAL,
|
|
11
|
+
NETWORK_TYPE,
|
|
12
|
+
MEDIA_DEVICES,
|
|
13
|
+
_UNKNOWN_,
|
|
14
|
+
} from '../constants';
|
|
15
|
+
import {
|
|
16
|
+
emptyAudioReceive,
|
|
17
|
+
emptyAudioTransmit,
|
|
18
|
+
emptyMqaInterval,
|
|
19
|
+
emptyVideoReceive,
|
|
20
|
+
emptyVideoTransmit,
|
|
21
|
+
} from '../mediaQualityMetrics/config';
|
|
7
22
|
import LoggerProxy from '../common/logs/logger-proxy';
|
|
8
23
|
|
|
9
24
|
import defaultStats from './global';
|
|
@@ -11,8 +26,9 @@ import {
|
|
|
11
26
|
getAudioSenderMqa,
|
|
12
27
|
getAudioReceiverMqa,
|
|
13
28
|
getVideoSenderMqa,
|
|
14
|
-
getVideoReceiverMqa
|
|
29
|
+
getVideoReceiverMqa,
|
|
15
30
|
} from './mqaUtil';
|
|
31
|
+
import {ReceiveSlot} from '../multistream/receiveSlot';
|
|
16
32
|
|
|
17
33
|
export const EVENTS = {
|
|
18
34
|
MEDIA_QUALITY: 'MEDIA_QUALITY',
|
|
@@ -22,6 +38,24 @@ export const EVENTS = {
|
|
|
22
38
|
REMOTE_MEDIA_STOPPED: 'REMOTE_MEDIA_STOPPED',
|
|
23
39
|
};
|
|
24
40
|
|
|
41
|
+
const emptySender = {
|
|
42
|
+
trackLabel: '',
|
|
43
|
+
maxPacketLossRatio: 0,
|
|
44
|
+
availableBandwidth: 0,
|
|
45
|
+
bytesSent: 0,
|
|
46
|
+
meanRemoteJitter: [],
|
|
47
|
+
meanRoundTripTime: [],
|
|
48
|
+
};
|
|
49
|
+
|
|
50
|
+
const emptyReceiver = {
|
|
51
|
+
availableBandwidth: 0,
|
|
52
|
+
bytesReceived: 0,
|
|
53
|
+
meanRtpJitter: [],
|
|
54
|
+
meanRoundTripTime: [],
|
|
55
|
+
};
|
|
56
|
+
|
|
57
|
+
type ReceiveSlotCallback = (csi: number) => ReceiveSlot | undefined;
|
|
58
|
+
|
|
25
59
|
/**
|
|
26
60
|
* Stats Analyzer class that will emit events based on detected quality
|
|
27
61
|
*
|
|
@@ -35,7 +69,6 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
35
69
|
lastEmittedStartStopEvent: any;
|
|
36
70
|
lastMqaDataSent: any;
|
|
37
71
|
lastStatsResults: any;
|
|
38
|
-
localMQEStats: any;
|
|
39
72
|
meetingMediaStatus: any;
|
|
40
73
|
mqaInterval: NodeJS.Timeout;
|
|
41
74
|
mqaSentCount: any;
|
|
@@ -44,16 +77,23 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
44
77
|
statsInterval: NodeJS.Timeout;
|
|
45
78
|
statsResults: any;
|
|
46
79
|
statsStarted: any;
|
|
80
|
+
receiveSlotCallback: ReceiveSlotCallback;
|
|
47
81
|
|
|
48
82
|
/**
|
|
49
83
|
* Creates a new instance of StatsAnalyzer
|
|
50
84
|
* @constructor
|
|
51
85
|
* @public
|
|
52
86
|
* @param {Object} config SDK Configuration Object
|
|
87
|
+
* @param {Function} receiveSlotCallback Callback used to access receive slots.
|
|
53
88
|
* @param {Object} networkQualityMonitor class for assessing network characteristics (jitter, packetLoss, latency)
|
|
54
89
|
* @param {Object} statsResults Default properties for stats
|
|
55
90
|
*/
|
|
56
|
-
constructor(
|
|
91
|
+
constructor(
|
|
92
|
+
config: any,
|
|
93
|
+
receiveSlotCallback: ReceiveSlotCallback = () => undefined,
|
|
94
|
+
networkQualityMonitor: object = {},
|
|
95
|
+
statsResults: object = defaultStats
|
|
96
|
+
) {
|
|
57
97
|
super();
|
|
58
98
|
this.statsStarted = false;
|
|
59
99
|
this.statsResults = statsResults;
|
|
@@ -62,120 +102,29 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
62
102
|
this.networkQualityMonitor = networkQualityMonitor;
|
|
63
103
|
this.correlationId = config.correlationId;
|
|
64
104
|
this.mqaSentCount = -1;
|
|
65
|
-
this.lastMqaDataSent = {
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
audio: {send: {}, recv: {}},
|
|
69
|
-
share: {send: {}, recv: {}}
|
|
70
|
-
};
|
|
71
|
-
this.localMQEStats = {
|
|
72
|
-
audio: {
|
|
73
|
-
RX: {
|
|
74
|
-
packetsLost: [],
|
|
75
|
-
jitter: [],
|
|
76
|
-
latency: [],
|
|
77
|
-
bitRate: []
|
|
78
|
-
},
|
|
79
|
-
TX: {
|
|
80
|
-
packetsLost: [],
|
|
81
|
-
jitter: [],
|
|
82
|
-
latency: [],
|
|
83
|
-
bitRate: []
|
|
84
|
-
}
|
|
85
|
-
},
|
|
86
|
-
video: {
|
|
87
|
-
RX: {
|
|
88
|
-
packetsLost: [],
|
|
89
|
-
jitter: [],
|
|
90
|
-
latency: [],
|
|
91
|
-
bitRate: [],
|
|
92
|
-
frameRate: [],
|
|
93
|
-
resolutionWidth: [],
|
|
94
|
-
resolutionHeight: [],
|
|
95
|
-
requestedKeyFrame: [],
|
|
96
|
-
receivedKeyFrame: []
|
|
97
|
-
},
|
|
98
|
-
TX: {
|
|
99
|
-
packetsLost: [],
|
|
100
|
-
jitter: [],
|
|
101
|
-
latency: [],
|
|
102
|
-
bitRate: [],
|
|
103
|
-
frameRate: [],
|
|
104
|
-
resolutionWidth: [],
|
|
105
|
-
resolutionHeight: [],
|
|
106
|
-
requestedKeyFrame: [],
|
|
107
|
-
receivedKeyFrame: []
|
|
108
|
-
}
|
|
109
|
-
}
|
|
110
|
-
};
|
|
111
|
-
this.lastEmittedStartStopEvent = {
|
|
112
|
-
audio: {
|
|
113
|
-
local: undefined,
|
|
114
|
-
remote: undefined,
|
|
115
|
-
},
|
|
116
|
-
video: {
|
|
117
|
-
local: undefined,
|
|
118
|
-
remote: undefined,
|
|
119
|
-
},
|
|
120
|
-
share: {
|
|
121
|
-
local: undefined,
|
|
122
|
-
remote: undefined,
|
|
123
|
-
},
|
|
124
|
-
};
|
|
125
|
-
}
|
|
126
|
-
|
|
127
|
-
populateResults(lastMqa) {
|
|
128
|
-
// Audio
|
|
129
|
-
|
|
130
|
-
this.localMQEStats.audio.RX.packetsLost.push(lastMqa.audioReceive[0].common.mediaHopByHopLost);
|
|
131
|
-
this.localMQEStats.audio.RX.jitter.push(lastMqa.audioReceive[0].streams[0].common.rtpJitter);
|
|
132
|
-
this.localMQEStats.audio.RX.latency.push(lastMqa.audioReceive[0].common.roundTripTime);
|
|
133
|
-
this.localMQEStats.audio.RX.bitRate.push(lastMqa.audioReceive[0].streams[0].common.receivedBitrate);
|
|
134
|
-
|
|
135
|
-
this.localMQEStats.audio.TX.packetsLost.push(lastMqa.audioTransmit[0].common.remoteLossRate);
|
|
136
|
-
this.localMQEStats.audio.TX.jitter.push(lastMqa.audioTransmit[0].common.remoteJitter);
|
|
137
|
-
this.localMQEStats.audio.TX.latency.push(lastMqa.audioTransmit[0].common.roundTripTime);
|
|
138
|
-
this.localMQEStats.audio.TX.bitRate.push(lastMqa.audioTransmit[0].streams[0].common.transmittedBitrate);
|
|
139
|
-
|
|
140
|
-
// Video
|
|
141
|
-
|
|
142
|
-
this.localMQEStats.video.RX.packetsLost.push(lastMqa.videoReceive[0].common.mediaHopByHopLost);
|
|
143
|
-
this.localMQEStats.video.RX.jitter.push(lastMqa.videoReceive[0].streams[0].common.rtpJitter);
|
|
144
|
-
this.localMQEStats.video.RX.latency.push(lastMqa.videoReceive[0].streams[0].common.roundTripTime);
|
|
145
|
-
this.localMQEStats.video.RX.bitRate.push(lastMqa.videoReceive[0].streams[0].common.receivedBitrate);
|
|
146
|
-
this.localMQEStats.video.RX.frameRate.push(lastMqa.videoReceive[0].streams[0].common.receivedFrameRate);
|
|
147
|
-
this.localMQEStats.video.RX.resolutionWidth.push(lastMqa.videoReceive[0].streams[0].receivedWidth);
|
|
148
|
-
this.localMQEStats.video.RX.resolutionHeight.push(lastMqa.videoReceive[0].streams[0].receivedHeight);
|
|
149
|
-
this.localMQEStats.video.RX.requestedKeyFrame.push();
|
|
150
|
-
this.localMQEStats.video.RX.receivedKeyFrame.push();
|
|
151
|
-
|
|
152
|
-
this.localMQEStats.video.TX.packetsLost.push(lastMqa.videoTransmit[0].common.remoteLossRate);
|
|
153
|
-
this.localMQEStats.video.TX.jitter.push(lastMqa.videoTransmit[0].common.remoteJitter);
|
|
154
|
-
this.localMQEStats.video.TX.latency.push(lastMqa.videoTransmit[0].common.roundTripTime);
|
|
155
|
-
this.localMQEStats.video.TX.bitRate.push(lastMqa.videoTransmit[0].streams[0].common.transmittedBitrate);
|
|
156
|
-
this.localMQEStats.video.TX.frameRate.push(lastMqa.videoTransmit[0].streams[0].common.transmittedFrameRate);
|
|
157
|
-
this.localMQEStats.video.TX.resolutionWidth.push(lastMqa.videoTransmit[0].streams[0].transmittedWidth);
|
|
158
|
-
this.localMQEStats.video.TX.resolutionHeight.push(lastMqa.videoTransmit[0].streams[0].transmittedHeight);
|
|
159
|
-
this.localMQEStats.video.TX.requestedKeyFrame.push(lastMqa.videoTransmit[0].streams[0].requestedKeyFrames);
|
|
160
|
-
this.localMQEStats.video.TX.receivedKeyFrame.push();
|
|
105
|
+
this.lastMqaDataSent = {};
|
|
106
|
+
this.lastEmittedStartStopEvent = {};
|
|
107
|
+
this.receiveSlotCallback = receiveSlotCallback;
|
|
161
108
|
}
|
|
162
109
|
|
|
163
|
-
|
|
110
|
+
/**
|
|
111
|
+
* Resets cumulative stats arrays.
|
|
112
|
+
*
|
|
113
|
+
* @public
|
|
114
|
+
* @memberof StatsAnalyzer
|
|
115
|
+
* @returns {void}
|
|
116
|
+
*/
|
|
164
117
|
resetStatsResults() {
|
|
165
|
-
this.statsResults.
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
this.statsResults.audio.recv.meanRtpJitter = [];
|
|
170
|
-
|
|
171
|
-
// TODO: currently no values are present
|
|
172
|
-
this.statsResults.video.recv.meanRtpJitter = [];
|
|
173
|
-
this.statsResults.share.recv.meanRtpJitter = [];
|
|
118
|
+
Object.keys(this.statsResults).forEach((mediaType) => {
|
|
119
|
+
if (mediaType.includes('recv')) {
|
|
120
|
+
this.statsResults[mediaType].recv.meanRtpJitter = [];
|
|
121
|
+
}
|
|
174
122
|
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
123
|
+
if (mediaType.includes('send')) {
|
|
124
|
+
this.statsResults[mediaType].send.meanRemoteJitter = [];
|
|
125
|
+
this.statsResults[mediaType].send.meanRoundTripTime = [];
|
|
126
|
+
}
|
|
127
|
+
});
|
|
179
128
|
}
|
|
180
129
|
|
|
181
130
|
/**
|
|
@@ -197,85 +146,90 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
197
146
|
* @memberof StatsAnalyzer
|
|
198
147
|
* @returns {void}
|
|
199
148
|
*/
|
|
200
|
-
|
|
201
|
-
const
|
|
202
|
-
const audioSender = mqaData.intervals[0].audioTransmit[0];
|
|
203
|
-
const videoReceiver = mqaData.intervals[0].videoReceive[0];
|
|
204
|
-
const videoSender = mqaData.intervals[0].videoTransmit[0];
|
|
205
|
-
const shareSender = mqaData.intervals[0].videoTransmit[1];
|
|
206
|
-
const shareReceiver = mqaData.intervals[0].videoReceive[1];
|
|
207
|
-
|
|
208
|
-
getAudioSenderMqa({
|
|
209
|
-
audioSender,
|
|
210
|
-
statsResults: this.statsResults,
|
|
211
|
-
lastMqaDataSent: this.lastMqaDataSent
|
|
212
|
-
});
|
|
213
|
-
getAudioReceiverMqa({
|
|
214
|
-
audioReceiver,
|
|
215
|
-
statsResults: this.statsResults,
|
|
216
|
-
lastMqaDataSent: this.lastMqaDataSent
|
|
217
|
-
});
|
|
149
|
+
sendMqaData() {
|
|
150
|
+
const newMqa = cloneDeep(emptyMqaInterval);
|
|
218
151
|
|
|
219
|
-
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
lastMqaDataSent: this.lastMqaDataSent
|
|
223
|
-
});
|
|
224
|
-
getVideoSenderMqa({
|
|
225
|
-
videoSender,
|
|
226
|
-
statsResults: this.statsResults,
|
|
227
|
-
lastMqaDataSent: this.lastMqaDataSent
|
|
228
|
-
});
|
|
152
|
+
Object.keys(this.statsResults).forEach((mediaType) => {
|
|
153
|
+
if (mediaType.includes('audio-send') || mediaType.includes('audio-share-send')) {
|
|
154
|
+
const audioSender = cloneDeep(emptyAudioTransmit);
|
|
229
155
|
|
|
230
|
-
|
|
231
|
-
|
|
232
|
-
|
|
233
|
-
|
|
234
|
-
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
|
|
242
|
-
|
|
243
|
-
|
|
156
|
+
getAudioSenderMqa({
|
|
157
|
+
audioSender,
|
|
158
|
+
statsResults: this.statsResults,
|
|
159
|
+
lastMqaDataSent: this.lastMqaDataSent,
|
|
160
|
+
mediaType,
|
|
161
|
+
});
|
|
162
|
+
newMqa.audioTransmit.push(audioSender);
|
|
163
|
+
} else if (mediaType.includes('audio-recv') || mediaType.includes('audio-share-recv')) {
|
|
164
|
+
const audioReceiver = cloneDeep(emptyAudioReceive);
|
|
165
|
+
|
|
166
|
+
getAudioReceiverMqa({
|
|
167
|
+
audioReceiver,
|
|
168
|
+
statsResults: this.statsResults,
|
|
169
|
+
lastMqaDataSent: this.lastMqaDataSent,
|
|
170
|
+
mediaType,
|
|
171
|
+
});
|
|
172
|
+
newMqa.audioReceive.push(audioReceiver);
|
|
173
|
+
} else if (mediaType.includes('video-send') || mediaType.includes('video-share-send')) {
|
|
174
|
+
const videoSender = cloneDeep(emptyVideoTransmit);
|
|
175
|
+
|
|
176
|
+
getVideoSenderMqa({
|
|
177
|
+
videoSender,
|
|
178
|
+
statsResults: this.statsResults,
|
|
179
|
+
lastMqaDataSent: this.lastMqaDataSent,
|
|
180
|
+
mediaType,
|
|
181
|
+
});
|
|
182
|
+
newMqa.videoTransmit.push(videoSender);
|
|
183
|
+
} else if (mediaType.includes('video-recv') || mediaType.includes('video-share-recv')) {
|
|
184
|
+
const videoReceiver = cloneDeep(emptyVideoReceive);
|
|
185
|
+
|
|
186
|
+
getVideoReceiverMqa({
|
|
187
|
+
videoReceiver,
|
|
188
|
+
statsResults: this.statsResults,
|
|
189
|
+
lastMqaDataSent: this.lastMqaDataSent,
|
|
190
|
+
mediaType,
|
|
191
|
+
});
|
|
192
|
+
newMqa.videoReceive.push(videoReceiver);
|
|
193
|
+
}
|
|
244
194
|
});
|
|
245
195
|
|
|
246
|
-
|
|
196
|
+
newMqa.intervalMetadata.peerReflexiveIP = this.statsResults.connectionType.local.ipAddress[0];
|
|
247
197
|
|
|
248
198
|
// Adding peripheral information
|
|
249
|
-
|
|
250
|
-
mqaData.intervals[0].intervalMetadata.peripherals.push({information: _UNKNOWN_, name: MEDIA_DEVICES.SPEAKER});
|
|
251
|
-
mqaData.intervals[0].intervalMetadata.peripherals.push({information: this.statsResults[STATS.AUDIO_CORRELATE][STATS.SEND_DIRECTION].trackLabel || _UNKNOWN_, name: MEDIA_DEVICES.MICROPHONE});
|
|
252
|
-
mqaData.intervals[0].intervalMetadata.peripherals.push({information: this.statsResults[STATS.VIDEO_CORRELATE][STATS.SEND_DIRECTION].trackLabel || _UNKNOWN_, name: MEDIA_DEVICES.CAMERA});
|
|
199
|
+
newMqa.intervalMetadata.peripherals = [];
|
|
253
200
|
|
|
201
|
+
newMqa.intervalMetadata.peripherals.push({information: _UNKNOWN_, name: MEDIA_DEVICES.SPEAKER});
|
|
202
|
+
if (this.statsResults['audio-send']) {
|
|
203
|
+
newMqa.intervalMetadata.peripherals.push({
|
|
204
|
+
information: this.statsResults['audio-send']?.trackLabel,
|
|
205
|
+
name: MEDIA_DEVICES.MICROPHONE,
|
|
206
|
+
});
|
|
207
|
+
}
|
|
208
|
+
if (this.statsResults['video-send']) {
|
|
209
|
+
newMqa.intervalMetadata.peripherals.push({
|
|
210
|
+
information: this.statsResults['video-send']?.trackLabel,
|
|
211
|
+
name: MEDIA_DEVICES.CAMERA,
|
|
212
|
+
});
|
|
213
|
+
}
|
|
254
214
|
|
|
255
|
-
|
|
256
|
-
mqaData.networkType = this.statsResults.connectionType.local.networkType;
|
|
215
|
+
newMqa.networkType = this.statsResults.connectionType.local.networkType;
|
|
257
216
|
|
|
258
217
|
this.mqaSentCount += 1;
|
|
259
218
|
|
|
260
|
-
|
|
261
|
-
|
|
262
|
-
// DO Deep copy, for some reason it takes the reference all the time rather then old value set
|
|
263
|
-
this.lastMqaDataSent = cloneDeep(this.statsResults);
|
|
264
|
-
|
|
265
|
-
this.populateResults(mqaData.intervals[0]);
|
|
219
|
+
newMqa.intervalNumber = this.mqaSentCount;
|
|
266
220
|
|
|
267
221
|
this.resetStatsResults();
|
|
268
222
|
|
|
269
223
|
this.emit(
|
|
270
224
|
{
|
|
271
225
|
file: 'statsAnalyzer',
|
|
272
|
-
function: 'sendMqaData'
|
|
226
|
+
function: 'sendMqaData',
|
|
273
227
|
},
|
|
274
228
|
EVENTS.MEDIA_QUALITY,
|
|
275
229
|
{
|
|
276
|
-
data:
|
|
230
|
+
data: newMqa,
|
|
277
231
|
// @ts-ignore
|
|
278
|
-
networkType:
|
|
232
|
+
networkType: newMqa.networkType,
|
|
279
233
|
}
|
|
280
234
|
);
|
|
281
235
|
}
|
|
@@ -285,7 +239,7 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
285
239
|
*
|
|
286
240
|
* @private
|
|
287
241
|
* @memberof StatsAnalyzer
|
|
288
|
-
* @param {
|
|
242
|
+
* @param {RoapMediaConnection} mediaConnection
|
|
289
243
|
* @returns {void}
|
|
290
244
|
*/
|
|
291
245
|
updateMediaConnection(mediaConnection: any) {
|
|
@@ -297,7 +251,7 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
297
251
|
*
|
|
298
252
|
* @public
|
|
299
253
|
* @memberof StatsAnalyzer
|
|
300
|
-
* @param {
|
|
254
|
+
* @param {RoapMediaConnection} mediaConnection
|
|
301
255
|
* @returns {Promise}
|
|
302
256
|
*/
|
|
303
257
|
public startAnalyzer(mediaConnection: any) {
|
|
@@ -305,17 +259,16 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
305
259
|
this.statsStarted = true;
|
|
306
260
|
this.mediaConnection = mediaConnection;
|
|
307
261
|
|
|
308
|
-
return this.getStatsAndParse()
|
|
309
|
-
.
|
|
310
|
-
this.
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
262
|
+
return this.getStatsAndParse().then(() => {
|
|
263
|
+
this.statsInterval = setInterval(() => {
|
|
264
|
+
this.getStatsAndParse();
|
|
265
|
+
}, this.config.analyzerInterval);
|
|
266
|
+
// Trigger initial fetch
|
|
267
|
+
this.sendMqaData();
|
|
268
|
+
this.mqaInterval = setInterval(() => {
|
|
314
269
|
this.sendMqaData();
|
|
315
|
-
|
|
316
|
-
|
|
317
|
-
}, MQA_INTEVAL);
|
|
318
|
-
});
|
|
270
|
+
}, MQA_INTEVAL);
|
|
271
|
+
});
|
|
319
272
|
}
|
|
320
273
|
|
|
321
274
|
return Promise.resolve();
|
|
@@ -367,6 +320,37 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
367
320
|
return;
|
|
368
321
|
}
|
|
369
322
|
|
|
323
|
+
// Generate empty stats results
|
|
324
|
+
if (!this.statsResults[type]) {
|
|
325
|
+
this.statsResults[type] = {};
|
|
326
|
+
}
|
|
327
|
+
|
|
328
|
+
if (isSender && !this.statsResults[type].send) {
|
|
329
|
+
this.statsResults[type].send = cloneDeep(emptySender);
|
|
330
|
+
} else if (!isSender && !this.statsResults[type].recv) {
|
|
331
|
+
this.statsResults[type].recv = cloneDeep(emptyReceiver);
|
|
332
|
+
}
|
|
333
|
+
|
|
334
|
+
if (!this.statsResults.resolutions[type]) {
|
|
335
|
+
this.statsResults.resolutions[type] = {};
|
|
336
|
+
}
|
|
337
|
+
|
|
338
|
+
if (isSender && !this.statsResults.resolutions[type].send) {
|
|
339
|
+
this.statsResults.resolutions[type].send = cloneDeep(emptySender);
|
|
340
|
+
} else if (!isSender && !this.statsResults.resolutions[type].recv) {
|
|
341
|
+
this.statsResults.resolutions[type].recv = cloneDeep(emptyReceiver);
|
|
342
|
+
}
|
|
343
|
+
|
|
344
|
+
if (!this.statsResults.internal[type]) {
|
|
345
|
+
this.statsResults.internal[type] = {};
|
|
346
|
+
}
|
|
347
|
+
|
|
348
|
+
if (isSender && !this.statsResults.internal[type].send) {
|
|
349
|
+
this.statsResults.internal[type].send = cloneDeep(emptySender);
|
|
350
|
+
} else if (!isSender && !this.statsResults.internal[type].recv) {
|
|
351
|
+
this.statsResults.internal[type].recv = cloneDeep(emptyReceiver);
|
|
352
|
+
}
|
|
353
|
+
|
|
370
354
|
switch (getStatsResult.type) {
|
|
371
355
|
case 'outbound-rtp':
|
|
372
356
|
this.processOutboundRTPResult(getStatsResult, type);
|
|
@@ -401,19 +385,25 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
401
385
|
/**
|
|
402
386
|
* Filters the get stats results for types
|
|
403
387
|
* @private
|
|
404
|
-
* @param {Array}
|
|
388
|
+
* @param {Array} statsItem
|
|
405
389
|
* @param {String} type
|
|
406
390
|
* @param {boolean} isSender
|
|
407
391
|
* @returns {void}
|
|
408
392
|
*/
|
|
409
|
-
|
|
393
|
+
filterAndParseGetStatsResults(statsItem: any, type: string, isSender: boolean) {
|
|
410
394
|
const {types} = DEFAULT_GET_STATS_FILTER;
|
|
411
395
|
|
|
412
|
-
|
|
396
|
+
statsItem.report.forEach((result) => {
|
|
413
397
|
if (types.includes(result.type)) {
|
|
414
398
|
this.parseGetStatsResult(result, type, isSender);
|
|
415
399
|
}
|
|
416
400
|
});
|
|
401
|
+
|
|
402
|
+
if (this.statsResults[type]) {
|
|
403
|
+
this.statsResults[type].direction = statsItem.currentDirection;
|
|
404
|
+
this.statsResults[type].trackLabel = statsItem.localTrackLabel;
|
|
405
|
+
this.statsResults[type].csi = statsItem.csi;
|
|
406
|
+
}
|
|
417
407
|
}
|
|
418
408
|
|
|
419
409
|
/**
|
|
@@ -427,7 +417,7 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
427
417
|
return;
|
|
428
418
|
}
|
|
429
419
|
|
|
430
|
-
if (type
|
|
420
|
+
if (type.includes('audio-send')) {
|
|
431
421
|
this.statsResults[type].send.audioLevel = result.audioLevel;
|
|
432
422
|
this.statsResults[type].send.totalAudioEnergy = result.totalAudioEnergy;
|
|
433
423
|
}
|
|
@@ -447,7 +437,12 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
447
437
|
* @memberof StatsAnalyzer
|
|
448
438
|
* @returns {void}
|
|
449
439
|
*/
|
|
450
|
-
emitStartStopEvents = (
|
|
440
|
+
emitStartStopEvents = (
|
|
441
|
+
mediaType: string,
|
|
442
|
+
previousValue: number,
|
|
443
|
+
currentValue: number,
|
|
444
|
+
isLocal: boolean
|
|
445
|
+
) => {
|
|
451
446
|
if (mediaType !== 'audio' && mediaType !== 'video' && mediaType !== 'share') {
|
|
452
447
|
throw new Error(`Unsupported mediaType: ${mediaType}`);
|
|
453
448
|
}
|
|
@@ -457,32 +452,36 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
457
452
|
// eslint-disable-next-line no-param-reassign
|
|
458
453
|
if (currentValue === undefined) currentValue = 0;
|
|
459
454
|
|
|
460
|
-
|
|
455
|
+
if (!this.lastEmittedStartStopEvent[mediaType]) {
|
|
456
|
+
this.lastEmittedStartStopEvent[mediaType] = {};
|
|
457
|
+
}
|
|
458
|
+
|
|
459
|
+
const lastEmittedEvent = isLocal
|
|
460
|
+
? this.lastEmittedStartStopEvent[mediaType].local
|
|
461
|
+
: this.lastEmittedStartStopEvent[mediaType].remote;
|
|
461
462
|
|
|
462
463
|
let newEvent;
|
|
463
464
|
|
|
464
|
-
if (
|
|
465
|
+
if (currentValue - previousValue > 0) {
|
|
465
466
|
newEvent = isLocal ? EVENTS.LOCAL_MEDIA_STARTED : EVENTS.REMOTE_MEDIA_STARTED;
|
|
466
|
-
}
|
|
467
|
-
else if ((currentValue === previousValue) && currentValue > 0) {
|
|
467
|
+
} else if (currentValue === previousValue && currentValue > 0) {
|
|
468
468
|
newEvent = isLocal ? EVENTS.LOCAL_MEDIA_STOPPED : EVENTS.REMOTE_MEDIA_STOPPED;
|
|
469
469
|
}
|
|
470
470
|
|
|
471
471
|
if (newEvent && lastEmittedEvent !== newEvent) {
|
|
472
472
|
if (isLocal) {
|
|
473
473
|
this.lastEmittedStartStopEvent[mediaType].local = newEvent;
|
|
474
|
-
}
|
|
475
|
-
else {
|
|
474
|
+
} else {
|
|
476
475
|
this.lastEmittedStartStopEvent[mediaType].remote = newEvent;
|
|
477
476
|
}
|
|
478
477
|
this.emit(
|
|
479
478
|
{
|
|
480
479
|
file: 'statsAnalyzer/index',
|
|
481
|
-
function: 'compareLastStatsResult'
|
|
480
|
+
function: 'compareLastStatsResult',
|
|
482
481
|
},
|
|
483
482
|
newEvent,
|
|
484
483
|
{
|
|
485
|
-
type: mediaType
|
|
484
|
+
type: mediaType,
|
|
486
485
|
}
|
|
487
486
|
);
|
|
488
487
|
}
|
|
@@ -497,145 +496,289 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
497
496
|
*/
|
|
498
497
|
private compareLastStatsResult() {
|
|
499
498
|
if (this.lastStatsResults !== null && this.meetingMediaStatus) {
|
|
500
|
-
|
|
501
|
-
|
|
502
|
-
|
|
503
|
-
|
|
504
|
-
|
|
505
|
-
|
|
506
|
-
|
|
507
|
-
|
|
508
|
-
|
|
509
|
-
|
|
510
|
-
|
|
511
|
-
|
|
512
|
-
|
|
513
|
-
|
|
514
|
-
|
|
499
|
+
const getCurrentStatsTotals = (keyPrefix: string, value: string): number =>
|
|
500
|
+
Object.keys(this.statsResults)
|
|
501
|
+
.filter((key) => key.startsWith(keyPrefix))
|
|
502
|
+
.reduce((prev, cur) => prev + (this.statsResults[cur]?.recv[value] || 0), 0);
|
|
503
|
+
|
|
504
|
+
const getPreviousStatsTotals = (keyPrefix: string, value: string): number =>
|
|
505
|
+
Object.keys(this.statsResults)
|
|
506
|
+
.filter((key) => key.startsWith(keyPrefix))
|
|
507
|
+
.reduce((prev, cur) => prev + (this.lastStatsResults[cur]?.recv[value] || 0), 0);
|
|
508
|
+
|
|
509
|
+
const getCurrentResolutionsStatsTotals = (keyPrefix: string, value: string): number =>
|
|
510
|
+
Object.keys(this.statsResults)
|
|
511
|
+
.filter((key) => key.startsWith(keyPrefix))
|
|
512
|
+
.reduce((prev, cur) => prev + (this.statsResults.resolutions[cur]?.recv[value] || 0), 0);
|
|
513
|
+
|
|
514
|
+
const getPreviousResolutionsStatsTotals = (keyPrefix: string, value: string): number =>
|
|
515
|
+
Object.keys(this.statsResults)
|
|
516
|
+
.filter((key) => key.startsWith(keyPrefix))
|
|
517
|
+
.reduce(
|
|
518
|
+
(prev, cur) => prev + (this.lastStatsResults.resolutions[cur]?.recv[value] || 0),
|
|
519
|
+
0
|
|
520
|
+
);
|
|
521
|
+
|
|
522
|
+
if (this.meetingMediaStatus.expected.sendAudio && this.lastStatsResults['audio-send']) {
|
|
523
|
+
// compare audio stats sent
|
|
524
|
+
// NOTE: relies on there being only one sender.
|
|
525
|
+
const currentStats = this.statsResults['audio-send'].send;
|
|
526
|
+
const previousStats = this.lastStatsResults['audio-send'].send;
|
|
527
|
+
|
|
528
|
+
if (
|
|
529
|
+
currentStats.totalPacketsSent === previousStats.totalPacketsSent ||
|
|
530
|
+
currentStats.totalPacketsSent === 0
|
|
531
|
+
) {
|
|
532
|
+
LoggerProxy.logger.info(
|
|
533
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No audio RTP packets sent`,
|
|
534
|
+
currentStats.totalPacketsSent
|
|
535
|
+
);
|
|
536
|
+
} else {
|
|
537
|
+
if (
|
|
538
|
+
currentStats.totalAudioEnergy === previousStats.totalAudioEnergy ||
|
|
539
|
+
currentStats.totalAudioEnergy === 0
|
|
540
|
+
) {
|
|
541
|
+
LoggerProxy.logger.info(
|
|
542
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No audio Energy present`,
|
|
543
|
+
currentStats.totalAudioEnergy
|
|
544
|
+
);
|
|
515
545
|
}
|
|
516
546
|
|
|
517
547
|
if (currentStats.audioLevel === 0) {
|
|
518
|
-
LoggerProxy.logger.info(
|
|
548
|
+
LoggerProxy.logger.info(
|
|
549
|
+
`StatsAnalyzer:index#compareLastStatsResult --> audio level is 0 for the user`
|
|
550
|
+
);
|
|
519
551
|
}
|
|
520
552
|
}
|
|
521
553
|
|
|
522
|
-
this.emitStartStopEvents(
|
|
554
|
+
this.emitStartStopEvents(
|
|
555
|
+
'audio',
|
|
556
|
+
previousStats.totalPacketsSent,
|
|
557
|
+
currentStats.totalPacketsSent,
|
|
558
|
+
true
|
|
559
|
+
);
|
|
523
560
|
}
|
|
524
561
|
|
|
525
562
|
if (this.meetingMediaStatus.expected.receiveAudio) {
|
|
526
|
-
|
|
527
|
-
|
|
528
|
-
|
|
563
|
+
// compare audio stats received
|
|
564
|
+
const currentPacketsReceived = getCurrentStatsTotals('audio-recv', 'totalPacketsReceived');
|
|
565
|
+
const previousPacketsReceived = getPreviousStatsTotals(
|
|
566
|
+
'audio-recv',
|
|
567
|
+
'totalPacketsReceived'
|
|
568
|
+
);
|
|
569
|
+
const currentSamplesReceived = getCurrentStatsTotals('audio-recv', 'totalSamplesReceived');
|
|
570
|
+
const previousSamplesReceived = getPreviousStatsTotals(
|
|
571
|
+
'audio-recv',
|
|
572
|
+
'totalSamplesReceived'
|
|
573
|
+
);
|
|
529
574
|
|
|
530
|
-
if (
|
|
531
|
-
LoggerProxy.logger.info(
|
|
532
|
-
|
|
533
|
-
|
|
534
|
-
|
|
535
|
-
|
|
575
|
+
if (currentPacketsReceived === previousPacketsReceived || currentPacketsReceived === 0) {
|
|
576
|
+
LoggerProxy.logger.info(
|
|
577
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No audio RTP packets received`,
|
|
578
|
+
currentPacketsReceived
|
|
579
|
+
);
|
|
580
|
+
} else if (
|
|
581
|
+
currentSamplesReceived === previousSamplesReceived ||
|
|
582
|
+
currentSamplesReceived === 0
|
|
583
|
+
) {
|
|
584
|
+
LoggerProxy.logger.info(
|
|
585
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No audio samples received`,
|
|
586
|
+
currentSamplesReceived
|
|
587
|
+
);
|
|
536
588
|
}
|
|
537
589
|
|
|
538
|
-
this.emitStartStopEvents(
|
|
590
|
+
this.emitStartStopEvents('audio', previousPacketsReceived, currentPacketsReceived, false);
|
|
539
591
|
}
|
|
540
592
|
|
|
541
|
-
|
|
542
|
-
|
|
543
|
-
|
|
544
|
-
|
|
545
|
-
|
|
546
|
-
|
|
547
|
-
|
|
548
|
-
|
|
549
|
-
|
|
550
|
-
|
|
551
|
-
|
|
552
|
-
|
|
593
|
+
if (this.meetingMediaStatus.expected.sendVideo && this.lastStatsResults['video-send']) {
|
|
594
|
+
// compare video stats sent
|
|
595
|
+
const currentStats = this.statsResults['video-send'].send;
|
|
596
|
+
const previousStats = this.lastStatsResults['video-send'].send;
|
|
597
|
+
|
|
598
|
+
if (
|
|
599
|
+
currentStats.totalPacketsSent === previousStats.totalPacketsSent ||
|
|
600
|
+
currentStats.totalPacketsSent === 0
|
|
601
|
+
) {
|
|
602
|
+
LoggerProxy.logger.info(
|
|
603
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video RTP packets sent`,
|
|
604
|
+
currentStats.totalPacketsSent
|
|
605
|
+
);
|
|
606
|
+
} else {
|
|
607
|
+
if (
|
|
608
|
+
currentStats.framesEncoded === previousStats.framesEncoded ||
|
|
609
|
+
currentStats.framesEncoded === 0
|
|
610
|
+
) {
|
|
611
|
+
LoggerProxy.logger.info(
|
|
612
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video Frames Encoded`,
|
|
613
|
+
currentStats.framesEncoded
|
|
614
|
+
);
|
|
553
615
|
}
|
|
554
616
|
|
|
555
|
-
if (
|
|
556
|
-
|
|
617
|
+
if (
|
|
618
|
+
this.statsResults.resolutions['video-send'].send.framesSent ===
|
|
619
|
+
this.lastStatsResults.resolutions['video-send'].send.framesSent ||
|
|
620
|
+
this.statsResults.resolutions['video-send'].send.framesSent === 0
|
|
621
|
+
) {
|
|
622
|
+
LoggerProxy.logger.info(
|
|
623
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video Frames sent`,
|
|
624
|
+
this.statsResults.resolutions['video-send'].send.framesSent
|
|
625
|
+
);
|
|
557
626
|
}
|
|
558
627
|
}
|
|
559
628
|
|
|
560
|
-
this.emitStartStopEvents(
|
|
561
|
-
mediaType,
|
|
562
|
-
previousStats.framesSent,
|
|
563
|
-
currentStats.framesSent,
|
|
564
|
-
true
|
|
565
|
-
);
|
|
629
|
+
this.emitStartStopEvents('video', previousStats.framesSent, currentStats.framesSent, true);
|
|
566
630
|
}
|
|
567
631
|
|
|
568
|
-
|
|
569
632
|
if (this.meetingMediaStatus.expected.receiveVideo) {
|
|
570
|
-
|
|
571
|
-
|
|
572
|
-
|
|
573
|
-
|
|
633
|
+
// compare video stats received
|
|
634
|
+
const currentPacketsReceived = getCurrentStatsTotals('video-recv', 'totalPacketsReceived');
|
|
635
|
+
const previousPacketsReceived = getPreviousStatsTotals(
|
|
636
|
+
'video-recv',
|
|
637
|
+
'totalPacketsReceived'
|
|
638
|
+
);
|
|
639
|
+
const currentFramesReceived = getCurrentResolutionsStatsTotals(
|
|
640
|
+
'video-recv',
|
|
641
|
+
'framesReceived'
|
|
642
|
+
);
|
|
643
|
+
const previousFramesReceived = getPreviousResolutionsStatsTotals(
|
|
644
|
+
'video-recv',
|
|
645
|
+
'framesReceived'
|
|
646
|
+
);
|
|
647
|
+
const currentFramesDecoded = getCurrentStatsTotals('video-recv', 'framesDecoded');
|
|
648
|
+
const previousFramesDecoded = getPreviousStatsTotals('video-recv', 'framesDecoded');
|
|
649
|
+
const currentFramesDropped = getCurrentResolutionsStatsTotals(
|
|
650
|
+
'video-recv',
|
|
651
|
+
'framesDropped'
|
|
652
|
+
);
|
|
653
|
+
const previousFramesDropped = getPreviousResolutionsStatsTotals(
|
|
654
|
+
'video-recv',
|
|
655
|
+
'framesDropped'
|
|
656
|
+
);
|
|
574
657
|
|
|
575
|
-
if (
|
|
576
|
-
LoggerProxy.logger.info(
|
|
577
|
-
|
|
578
|
-
|
|
579
|
-
|
|
580
|
-
|
|
658
|
+
if (currentPacketsReceived === previousPacketsReceived || currentPacketsReceived === 0) {
|
|
659
|
+
LoggerProxy.logger.info(
|
|
660
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video RTP packets received`,
|
|
661
|
+
currentPacketsReceived
|
|
662
|
+
);
|
|
663
|
+
} else {
|
|
664
|
+
if (currentFramesReceived === previousFramesReceived || currentFramesReceived === 0) {
|
|
665
|
+
LoggerProxy.logger.info(
|
|
666
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video frames received`,
|
|
667
|
+
currentFramesReceived
|
|
668
|
+
);
|
|
581
669
|
}
|
|
582
670
|
|
|
583
|
-
if (
|
|
584
|
-
LoggerProxy.logger.info(
|
|
671
|
+
if (currentFramesDecoded === previousFramesDecoded || currentFramesDecoded === 0) {
|
|
672
|
+
LoggerProxy.logger.info(
|
|
673
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No video frames decoded`,
|
|
674
|
+
currentFramesDecoded
|
|
675
|
+
);
|
|
585
676
|
}
|
|
586
677
|
|
|
587
|
-
if (
|
|
588
|
-
LoggerProxy.logger.info(
|
|
678
|
+
if (currentFramesDropped - previousFramesDropped > 10) {
|
|
679
|
+
LoggerProxy.logger.info(
|
|
680
|
+
`StatsAnalyzer:index#compareLastStatsResult --> video frames are getting dropped`,
|
|
681
|
+
currentFramesDropped - previousFramesDropped
|
|
682
|
+
);
|
|
589
683
|
}
|
|
590
684
|
}
|
|
591
685
|
|
|
592
|
-
this.emitStartStopEvents(
|
|
593
|
-
mediaType,
|
|
594
|
-
previousStats.framesDecoded,
|
|
595
|
-
currentStats.framesDecoded,
|
|
596
|
-
false
|
|
597
|
-
);
|
|
686
|
+
this.emitStartStopEvents('video', previousFramesDecoded, currentFramesDecoded, false);
|
|
598
687
|
}
|
|
599
688
|
|
|
600
|
-
|
|
601
|
-
|
|
602
|
-
|
|
603
|
-
|
|
604
|
-
|
|
605
|
-
|
|
606
|
-
|
|
607
|
-
|
|
608
|
-
|
|
609
|
-
|
|
610
|
-
|
|
611
|
-
|
|
612
|
-
|
|
689
|
+
if (this.meetingMediaStatus.expected.sendShare && this.lastStatsResults['video-share-send']) {
|
|
690
|
+
// compare share stats sent
|
|
691
|
+
|
|
692
|
+
const currentStats = this.statsResults['video-share-send'].send;
|
|
693
|
+
const previousStats = this.lastStatsResults['video-share-send'].send;
|
|
694
|
+
|
|
695
|
+
if (
|
|
696
|
+
currentStats.totalPacketsSent === previousStats.totalPacketsSent ||
|
|
697
|
+
currentStats.totalPacketsSent === 0
|
|
698
|
+
) {
|
|
699
|
+
LoggerProxy.logger.info(
|
|
700
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share RTP packets sent`,
|
|
701
|
+
currentStats.totalPacketsSent
|
|
702
|
+
);
|
|
703
|
+
} else {
|
|
704
|
+
if (
|
|
705
|
+
currentStats.framesEncoded === previousStats.framesEncoded ||
|
|
706
|
+
currentStats.framesEncoded === 0
|
|
707
|
+
) {
|
|
708
|
+
LoggerProxy.logger.info(
|
|
709
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share frames getting encoded`,
|
|
710
|
+
currentStats.framesEncoded
|
|
711
|
+
);
|
|
613
712
|
}
|
|
614
713
|
|
|
615
|
-
if (
|
|
616
|
-
|
|
714
|
+
if (
|
|
715
|
+
this.statsResults.resolutions['video-share-send'].send.framesSent ===
|
|
716
|
+
this.lastStatsResults.resolutions['video-share-send'].send.framesSent ||
|
|
717
|
+
this.statsResults.resolutions['video-share-send'].send.framesSent === 0
|
|
718
|
+
) {
|
|
719
|
+
LoggerProxy.logger.info(
|
|
720
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share frames sent`,
|
|
721
|
+
this.statsResults.resolutions['video-share-send'].send.framesSent
|
|
722
|
+
);
|
|
617
723
|
}
|
|
618
724
|
}
|
|
725
|
+
}
|
|
619
726
|
|
|
727
|
+
if (this.meetingMediaStatus.expected.sendShare) {
|
|
620
728
|
// TODO:need to check receive share value
|
|
621
|
-
// compare share stats
|
|
622
|
-
|
|
623
|
-
|
|
729
|
+
// compare share stats received
|
|
730
|
+
const currentPacketsReceived = getCurrentStatsTotals(
|
|
731
|
+
'video-share-recv',
|
|
732
|
+
'totalPacketsReceived'
|
|
733
|
+
);
|
|
734
|
+
const previousPacketsReceived = getPreviousStatsTotals(
|
|
735
|
+
'video-share-recv',
|
|
736
|
+
'totalPacketsReceived'
|
|
737
|
+
);
|
|
738
|
+
const currentFramesReceived = getCurrentResolutionsStatsTotals(
|
|
739
|
+
'video-share-recv',
|
|
740
|
+
'framesReceived'
|
|
741
|
+
);
|
|
742
|
+
const previousFramesReceived = getPreviousResolutionsStatsTotals(
|
|
743
|
+
'video-share-recv',
|
|
744
|
+
'framesReceived'
|
|
745
|
+
);
|
|
746
|
+
const currentFramesDecoded = getCurrentStatsTotals('video-share-recv', 'framesDecoded');
|
|
747
|
+
const previousFramesDecoded = getPreviousStatsTotals('video-share-recv', 'framesDecoded');
|
|
748
|
+
const currentFramesDropped = getCurrentResolutionsStatsTotals(
|
|
749
|
+
'video-share-recv',
|
|
750
|
+
'framesDropped'
|
|
751
|
+
);
|
|
752
|
+
const previousFramesDropped = getPreviousResolutionsStatsTotals(
|
|
753
|
+
'video-share-recv',
|
|
754
|
+
'framesDropped'
|
|
755
|
+
);
|
|
624
756
|
|
|
625
|
-
if (
|
|
626
|
-
LoggerProxy.logger.info(
|
|
627
|
-
|
|
628
|
-
|
|
629
|
-
|
|
630
|
-
|
|
757
|
+
if (currentPacketsReceived === previousPacketsReceived || currentPacketsReceived === 0) {
|
|
758
|
+
LoggerProxy.logger.info(
|
|
759
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share RTP packets received`,
|
|
760
|
+
currentPacketsReceived
|
|
761
|
+
);
|
|
762
|
+
} else {
|
|
763
|
+
if (currentFramesReceived === previousFramesReceived || currentFramesReceived === 0) {
|
|
764
|
+
LoggerProxy.logger.info(
|
|
765
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share frames received`,
|
|
766
|
+
currentFramesReceived
|
|
767
|
+
);
|
|
631
768
|
}
|
|
632
769
|
|
|
633
|
-
if (
|
|
634
|
-
LoggerProxy.logger.info(
|
|
770
|
+
if (currentFramesDecoded === previousFramesDecoded || currentFramesDecoded === 0) {
|
|
771
|
+
LoggerProxy.logger.info(
|
|
772
|
+
`StatsAnalyzer:index#compareLastStatsResult --> No share frames decoded`,
|
|
773
|
+
currentFramesDecoded
|
|
774
|
+
);
|
|
635
775
|
}
|
|
636
776
|
|
|
637
|
-
if (
|
|
638
|
-
LoggerProxy.logger.info(
|
|
777
|
+
if (currentFramesDropped - previousFramesDropped > 10) {
|
|
778
|
+
LoggerProxy.logger.info(
|
|
779
|
+
`StatsAnalyzer:index#compareLastStatsResult --> share frames are getting dropped`,
|
|
780
|
+
currentFramesDropped - previousFramesDropped
|
|
781
|
+
);
|
|
639
782
|
}
|
|
640
783
|
}
|
|
641
784
|
|
|
@@ -658,8 +801,13 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
658
801
|
return Promise.resolve();
|
|
659
802
|
}
|
|
660
803
|
|
|
661
|
-
if (
|
|
662
|
-
|
|
804
|
+
if (
|
|
805
|
+
this.mediaConnection &&
|
|
806
|
+
this.mediaConnection.getConnectionState() === ConnectionState.Failed
|
|
807
|
+
) {
|
|
808
|
+
LoggerProxy.logger.trace(
|
|
809
|
+
'StatsAnalyzer:index#getStatsAndParse --> media connection is in failed state'
|
|
810
|
+
);
|
|
663
811
|
|
|
664
812
|
return Promise.resolve();
|
|
665
813
|
}
|
|
@@ -667,20 +815,43 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
667
815
|
LoggerProxy.logger.trace('StatsAnalyzer:index#getStatsAndParse --> Collecting Stats');
|
|
668
816
|
|
|
669
817
|
return this.mediaConnection.getTransceiverStats().then((transceiverStats) => {
|
|
670
|
-
|
|
671
|
-
|
|
672
|
-
|
|
673
|
-
|
|
674
|
-
|
|
675
|
-
|
|
676
|
-
|
|
677
|
-
|
|
678
|
-
|
|
679
|
-
|
|
680
|
-
|
|
818
|
+
transceiverStats.video.receivers.forEach((receiver, i) =>
|
|
819
|
+
this.filterAndParseGetStatsResults(receiver, `video-recv-${i}`, false)
|
|
820
|
+
);
|
|
821
|
+
transceiverStats.audio.receivers.forEach((receiver, i) =>
|
|
822
|
+
this.filterAndParseGetStatsResults(receiver, `audio-recv-${i}`, false)
|
|
823
|
+
);
|
|
824
|
+
transceiverStats.screenShareVideo.receivers.forEach((receiver, i) =>
|
|
825
|
+
this.filterAndParseGetStatsResults(receiver, `video-share-recv-${i}`, false)
|
|
826
|
+
);
|
|
827
|
+
transceiverStats.screenShareAudio.receivers.forEach((receiver, i) =>
|
|
828
|
+
this.filterAndParseGetStatsResults(receiver, `audio-share-recv-${i}`, false)
|
|
829
|
+
);
|
|
681
830
|
|
|
682
|
-
|
|
683
|
-
|
|
831
|
+
transceiverStats.video.senders.forEach((sender, i) => {
|
|
832
|
+
if (i > 0) {
|
|
833
|
+
throw new Error('Stats Analyzer does not support multiple senders.');
|
|
834
|
+
}
|
|
835
|
+
this.filterAndParseGetStatsResults(sender, 'video-send', true);
|
|
836
|
+
});
|
|
837
|
+
transceiverStats.audio.senders.forEach((sender, i) => {
|
|
838
|
+
if (i > 0) {
|
|
839
|
+
throw new Error('Stats Analyzer does not support multiple senders.');
|
|
840
|
+
}
|
|
841
|
+
this.filterAndParseGetStatsResults(sender, 'audio-send', true);
|
|
842
|
+
});
|
|
843
|
+
transceiverStats.screenShareVideo.senders.forEach((sender, i) => {
|
|
844
|
+
if (i > 0) {
|
|
845
|
+
throw new Error('Stats Analyzer does not support multiple senders.');
|
|
846
|
+
}
|
|
847
|
+
this.filterAndParseGetStatsResults(sender, 'video-share-send', true);
|
|
848
|
+
});
|
|
849
|
+
transceiverStats.screenShareAudio.senders.forEach((sender, i) => {
|
|
850
|
+
if (i > 0) {
|
|
851
|
+
throw new Error('Stats Analyzer does not support multiple senders.');
|
|
852
|
+
}
|
|
853
|
+
this.filterAndParseGetStatsResults(sender, 'audio-share-send', true);
|
|
854
|
+
});
|
|
684
855
|
|
|
685
856
|
this.compareLastStatsResult();
|
|
686
857
|
|
|
@@ -688,7 +859,9 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
688
859
|
// DO Deep copy, for some reason it takes the reference all the time rather then old value set
|
|
689
860
|
this.lastStatsResults = JSON.parse(JSON.stringify(this.statsResults));
|
|
690
861
|
|
|
691
|
-
LoggerProxy.logger.trace(
|
|
862
|
+
LoggerProxy.logger.trace(
|
|
863
|
+
'StatsAnalyzer:index#getStatsAndParse --> Finished Collecting Stats'
|
|
864
|
+
);
|
|
692
865
|
});
|
|
693
866
|
}
|
|
694
867
|
|
|
@@ -696,16 +869,23 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
696
869
|
* Processes OutboundRTP stats result and stores
|
|
697
870
|
* @private
|
|
698
871
|
* @param {*} result
|
|
699
|
-
* @param {*}
|
|
872
|
+
* @param {*} mediaType
|
|
700
873
|
* @returns {void}
|
|
701
874
|
*/
|
|
702
|
-
private processOutboundRTPResult(result: any,
|
|
703
|
-
const mediaType = type || STATS.AUDIO_CORRELATE;
|
|
875
|
+
private processOutboundRTPResult(result: any, mediaType: any) {
|
|
704
876
|
const sendrecvType = STATS.SEND_DIRECTION;
|
|
705
877
|
|
|
706
878
|
if (result.bytesSent) {
|
|
707
879
|
let kilobytes = 0;
|
|
708
880
|
|
|
881
|
+
if (result.frameWidth && result.frameHeight) {
|
|
882
|
+
this.statsResults.resolutions[mediaType][sendrecvType].width = result.frameWidth;
|
|
883
|
+
this.statsResults.resolutions[mediaType][sendrecvType].height = result.frameHeight;
|
|
884
|
+
this.statsResults.resolutions[mediaType][sendrecvType].framesSent = result.framesSent;
|
|
885
|
+
this.statsResults.resolutions[mediaType][sendrecvType].hugeFramesSent =
|
|
886
|
+
result.hugeFramesSent;
|
|
887
|
+
}
|
|
888
|
+
|
|
709
889
|
if (!this.statsResults.internal[mediaType][sendrecvType].prevBytesSent) {
|
|
710
890
|
this.statsResults.internal[mediaType][sendrecvType].prevBytesSent = result.bytesSent;
|
|
711
891
|
}
|
|
@@ -713,10 +893,12 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
713
893
|
this.statsResults.internal[mediaType][sendrecvType].framesEncoded = result.framesEncoded;
|
|
714
894
|
}
|
|
715
895
|
if (!this.statsResults.internal[mediaType][sendrecvType].keyFramesEncoded) {
|
|
716
|
-
this.statsResults.internal[mediaType][sendrecvType].keyFramesEncoded =
|
|
896
|
+
this.statsResults.internal[mediaType][sendrecvType].keyFramesEncoded =
|
|
897
|
+
result.keyFramesEncoded;
|
|
717
898
|
}
|
|
718
899
|
|
|
719
|
-
const bytes =
|
|
900
|
+
const bytes =
|
|
901
|
+
result.bytesSent - this.statsResults.internal[mediaType][sendrecvType].prevBytesSent;
|
|
720
902
|
|
|
721
903
|
this.statsResults.internal[mediaType][sendrecvType].prevBytesSent = result.bytesSent;
|
|
722
904
|
|
|
@@ -725,15 +907,19 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
725
907
|
this.statsResults[mediaType][sendrecvType].availableBandwidth = kilobytes.toFixed(1);
|
|
726
908
|
this.statsResults[mediaType].bytesSent = kilobytes;
|
|
727
909
|
|
|
728
|
-
this.statsResults[mediaType][sendrecvType].framesEncoded =
|
|
729
|
-
|
|
910
|
+
this.statsResults[mediaType][sendrecvType].framesEncoded =
|
|
911
|
+
result.framesEncoded - this.statsResults.internal[mediaType][sendrecvType].framesEncoded;
|
|
912
|
+
this.statsResults[mediaType][sendrecvType].keyFramesEncoded =
|
|
913
|
+
result.keyFramesEncoded -
|
|
914
|
+
this.statsResults.internal[mediaType][sendrecvType].keyFramesEncoded;
|
|
730
915
|
this.statsResults.internal[mediaType].outboundRtpId = result.id;
|
|
731
916
|
|
|
732
917
|
if (!this.statsResults.internal[mediaType][sendrecvType].packetsSent) {
|
|
733
918
|
this.statsResults.internal[mediaType][sendrecvType].packetsSent = result.packetsSent;
|
|
734
919
|
}
|
|
735
920
|
|
|
736
|
-
this.statsResults[mediaType][sendrecvType].packetsSent =
|
|
921
|
+
this.statsResults[mediaType][sendrecvType].packetsSent =
|
|
922
|
+
result.packetsSent - this.statsResults.internal[mediaType][sendrecvType].packetsSent;
|
|
737
923
|
this.statsResults.internal[mediaType][sendrecvType].packetsSent = result.packetsSent;
|
|
738
924
|
|
|
739
925
|
// Data saved to send MQA metrics
|
|
@@ -745,33 +931,48 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
745
931
|
this.statsResults[mediaType][sendrecvType].totalFirCount = result.firCount;
|
|
746
932
|
this.statsResults[mediaType][sendrecvType].framesSent = result.framesSent;
|
|
747
933
|
this.statsResults[mediaType][sendrecvType].framesEncoded = result.framesEncoded;
|
|
748
|
-
this.statsResults[mediaType][sendrecvType].encoderImplementation =
|
|
749
|
-
|
|
750
|
-
this.statsResults[mediaType][sendrecvType].
|
|
751
|
-
|
|
934
|
+
this.statsResults[mediaType][sendrecvType].encoderImplementation =
|
|
935
|
+
result.encoderImplementation;
|
|
936
|
+
this.statsResults[mediaType][sendrecvType].qualityLimitationReason =
|
|
937
|
+
result.qualityLimitationReason;
|
|
938
|
+
this.statsResults[mediaType][sendrecvType].qualityLimitationResolutionChanges =
|
|
939
|
+
result.qualityLimitationResolutionChanges;
|
|
940
|
+
this.statsResults[mediaType][sendrecvType].retransmittedPacketsSent =
|
|
941
|
+
result.retransmittedPacketsSent;
|
|
752
942
|
this.statsResults[mediaType][sendrecvType].totalBytesSent = result.bytesSent;
|
|
753
943
|
this.statsResults[mediaType][sendrecvType].headerBytesSent = result.headerBytesSent;
|
|
754
|
-
this.statsResults[mediaType][sendrecvType].retransmittedBytesSent =
|
|
944
|
+
this.statsResults[mediaType][sendrecvType].retransmittedBytesSent =
|
|
945
|
+
result.retransmittedBytesSent;
|
|
755
946
|
}
|
|
756
947
|
}
|
|
757
948
|
|
|
758
|
-
|
|
759
949
|
/**
|
|
760
950
|
* Processes InboundRTP stats result and stores
|
|
761
951
|
* @private
|
|
762
952
|
* @param {*} result
|
|
763
|
-
* @param {*}
|
|
953
|
+
* @param {*} mediaType
|
|
764
954
|
* @returns {void}
|
|
765
955
|
*/
|
|
766
|
-
private processInboundRTPResult(result: any,
|
|
767
|
-
const mediaType = type || STATS.AUDIO_CORRELATE;
|
|
956
|
+
private processInboundRTPResult(result: any, mediaType: any) {
|
|
768
957
|
const sendrecvType = STATS.RECEIVE_DIRECTION;
|
|
769
958
|
|
|
770
959
|
if (result.bytesReceived) {
|
|
771
960
|
let kilobytes = 0;
|
|
961
|
+
const receiveSlot = this.receiveSlotCallback(result.ssrc);
|
|
962
|
+
const idAndCsi = receiveSlot
|
|
963
|
+
? `id: "${receiveSlot.id || ''}"${receiveSlot.csi ? ` and csi: ${receiveSlot.csi}` : ''}`
|
|
964
|
+
: '';
|
|
965
|
+
|
|
966
|
+
if (result.frameWidth && result.frameHeight) {
|
|
967
|
+
this.statsResults.resolutions[mediaType][sendrecvType].width = result.frameWidth;
|
|
968
|
+
this.statsResults.resolutions[mediaType][sendrecvType].height = result.frameHeight;
|
|
969
|
+
this.statsResults.resolutions[mediaType][sendrecvType].framesReceived =
|
|
970
|
+
result.framesReceived;
|
|
971
|
+
}
|
|
772
972
|
|
|
773
973
|
if (!this.statsResults.internal[mediaType][sendrecvType].prevBytesReceived) {
|
|
774
|
-
this.statsResults.internal[mediaType][sendrecvType].prevBytesReceived =
|
|
974
|
+
this.statsResults.internal[mediaType][sendrecvType].prevBytesReceived =
|
|
975
|
+
result.bytesReceived;
|
|
775
976
|
}
|
|
776
977
|
|
|
777
978
|
if (!this.statsResults.internal[mediaType][sendrecvType].pliCount) {
|
|
@@ -783,14 +984,18 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
783
984
|
}
|
|
784
985
|
|
|
785
986
|
if (!this.statsResults.internal[mediaType][sendrecvType].totalPacketsReceived) {
|
|
786
|
-
this.statsResults.internal[mediaType][sendrecvType].totalPacketsReceived =
|
|
987
|
+
this.statsResults.internal[mediaType][sendrecvType].totalPacketsReceived =
|
|
988
|
+
result.packetsReceived;
|
|
787
989
|
}
|
|
788
990
|
|
|
789
991
|
if (!this.statsResults.internal[mediaType][sendrecvType].lastPacketReceivedTimestamp) {
|
|
790
|
-
this.statsResults.internal[mediaType][sendrecvType].lastPacketReceivedTimestamp =
|
|
992
|
+
this.statsResults.internal[mediaType][sendrecvType].lastPacketReceivedTimestamp =
|
|
993
|
+
result.lastPacketReceivedTimestamp;
|
|
791
994
|
}
|
|
792
995
|
|
|
793
|
-
const bytes =
|
|
996
|
+
const bytes =
|
|
997
|
+
result.bytesReceived -
|
|
998
|
+
this.statsResults.internal[mediaType][sendrecvType].prevBytesReceived;
|
|
794
999
|
|
|
795
1000
|
this.statsResults.internal[mediaType][sendrecvType].prevBytesReceived = result.bytesReceived;
|
|
796
1001
|
|
|
@@ -798,35 +1003,54 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
798
1003
|
this.statsResults[mediaType][sendrecvType].availableBandwidth = kilobytes.toFixed(1);
|
|
799
1004
|
this.statsResults[mediaType].bytesReceived = kilobytes.toFixed(1);
|
|
800
1005
|
|
|
801
|
-
this.statsResults[mediaType][sendrecvType].pliCount =
|
|
802
|
-
|
|
1006
|
+
this.statsResults[mediaType][sendrecvType].pliCount =
|
|
1007
|
+
result.pliCount - this.statsResults.internal[mediaType][sendrecvType].pliCount;
|
|
1008
|
+
this.statsResults[mediaType][sendrecvType].currentPacketsLost =
|
|
1009
|
+
result.packetsLost - this.statsResults.internal[mediaType][sendrecvType].packetsLost;
|
|
803
1010
|
if (this.statsResults[mediaType][sendrecvType].currentPacketsLost < 0) {
|
|
804
1011
|
this.statsResults[mediaType][sendrecvType].currentPacketsLost = 0;
|
|
805
1012
|
}
|
|
806
1013
|
|
|
807
|
-
this.statsResults[mediaType][sendrecvType].packetsReceived =
|
|
808
|
-
|
|
1014
|
+
this.statsResults[mediaType][sendrecvType].packetsReceived =
|
|
1015
|
+
result.packetsReceived -
|
|
1016
|
+
this.statsResults.internal[mediaType][sendrecvType].totalPacketsReceived;
|
|
1017
|
+
this.statsResults.internal[mediaType][sendrecvType].totalPacketsReceived =
|
|
1018
|
+
result.packetsReceived;
|
|
809
1019
|
|
|
810
1020
|
if (this.statsResults[mediaType][sendrecvType].packetsReceived === 0) {
|
|
811
|
-
|
|
1021
|
+
if (receiveSlot) {
|
|
1022
|
+
LoggerProxy.logger.info(
|
|
1023
|
+
`StatsAnalyzer:index#processInboundRTPResult --> No packets received for receive slot ${idAndCsi}`,
|
|
1024
|
+
this.statsResults[mediaType][sendrecvType].packetsReceived
|
|
1025
|
+
);
|
|
1026
|
+
}
|
|
812
1027
|
}
|
|
813
1028
|
|
|
814
1029
|
// Check the over all packet Lost ratio
|
|
815
|
-
this.statsResults[mediaType][sendrecvType].currentPacketLossRatio =
|
|
1030
|
+
this.statsResults[mediaType][sendrecvType].currentPacketLossRatio =
|
|
1031
|
+
this.statsResults[mediaType][sendrecvType].currentPacketsLost > 0
|
|
1032
|
+
? this.statsResults[mediaType][sendrecvType].currentPacketsLost /
|
|
1033
|
+
(this.statsResults[mediaType][sendrecvType].packetsReceived +
|
|
1034
|
+
this.statsResults[mediaType][sendrecvType].currentPacketsLost)
|
|
1035
|
+
: 0;
|
|
816
1036
|
if (this.statsResults[mediaType][sendrecvType].currentPacketLossRatio > 3) {
|
|
817
|
-
LoggerProxy.logger.info(
|
|
1037
|
+
LoggerProxy.logger.info(
|
|
1038
|
+
`StatsAnalyzer:index#processInboundRTPResult --> Packets getting lost from the receiver with slot ${idAndCsi}`,
|
|
1039
|
+
this.statsResults[mediaType][sendrecvType].currentPacketLossRatio
|
|
1040
|
+
);
|
|
818
1041
|
}
|
|
819
1042
|
|
|
820
1043
|
// TODO: check the packet loss value is negative values here
|
|
821
1044
|
|
|
822
1045
|
if (result.packetsLost) {
|
|
823
|
-
this.statsResults[mediaType][sendrecvType].totalPacketsLost =
|
|
824
|
-
|
|
825
|
-
else {
|
|
1046
|
+
this.statsResults[mediaType][sendrecvType].totalPacketsLost =
|
|
1047
|
+
result.packetsLost > 0 ? result.packetsLost : -result.packetsLost;
|
|
1048
|
+
} else {
|
|
826
1049
|
this.statsResults[mediaType][sendrecvType].totalPacketsLost = 0;
|
|
827
1050
|
}
|
|
828
1051
|
|
|
829
|
-
this.statsResults[mediaType][sendrecvType].lastPacketReceivedTimestamp =
|
|
1052
|
+
this.statsResults[mediaType][sendrecvType].lastPacketReceivedTimestamp =
|
|
1053
|
+
result.lastPacketReceivedTimestamp;
|
|
830
1054
|
|
|
831
1055
|
// From Thin
|
|
832
1056
|
this.statsResults[mediaType][sendrecvType].totalNackCount = result.nackCount;
|
|
@@ -834,10 +1058,10 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
834
1058
|
this.statsResults[mediaType][sendrecvType].framesDecoded = result.framesDecoded;
|
|
835
1059
|
this.statsResults[mediaType][sendrecvType].keyFramesDecoded = result.keyFramesDecoded;
|
|
836
1060
|
|
|
837
|
-
this.statsResults[mediaType][sendrecvType].decoderImplementation =
|
|
1061
|
+
this.statsResults[mediaType][sendrecvType].decoderImplementation =
|
|
1062
|
+
result.decoderImplementation;
|
|
838
1063
|
this.statsResults[mediaType][sendrecvType].totalPacketsReceived = result.packetsReceived;
|
|
839
1064
|
|
|
840
|
-
|
|
841
1065
|
this.statsResults[mediaType][sendrecvType].fecPacketsDiscarded = result.fecPacketsDiscarded;
|
|
842
1066
|
this.statsResults[mediaType][sendrecvType].fecPacketsReceived = result.fecPacketsReceived;
|
|
843
1067
|
this.statsResults[mediaType][sendrecvType].totalBytesReceived = result.bytesReceived;
|
|
@@ -849,8 +1073,10 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
849
1073
|
|
|
850
1074
|
this.statsResults[mediaType][sendrecvType].audioLevel = result.audioLevel;
|
|
851
1075
|
this.statsResults[mediaType][sendrecvType].totalAudioEnergy = result.totalAudioEnergy;
|
|
852
|
-
this.statsResults[mediaType][sendrecvType].totalSamplesReceived =
|
|
853
|
-
|
|
1076
|
+
this.statsResults[mediaType][sendrecvType].totalSamplesReceived =
|
|
1077
|
+
result.totalSamplesReceived || 0;
|
|
1078
|
+
this.statsResults[mediaType][sendrecvType].totalSamplesDecoded =
|
|
1079
|
+
result.totalSamplesDecoded || 0;
|
|
854
1080
|
this.statsResults[mediaType][sendrecvType].concealedSamples = result.concealedSamples || 0;
|
|
855
1081
|
}
|
|
856
1082
|
}
|
|
@@ -894,7 +1120,10 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
894
1120
|
RemoteNetworkType[result.id] = [];
|
|
895
1121
|
}
|
|
896
1122
|
|
|
897
|
-
if (
|
|
1123
|
+
if (
|
|
1124
|
+
result.candidateType &&
|
|
1125
|
+
RemoteCandidateType[result.id].indexOf(result.candidateType) === -1
|
|
1126
|
+
) {
|
|
898
1127
|
RemoteCandidateType[result.id].push(result.candidateType);
|
|
899
1128
|
}
|
|
900
1129
|
|
|
@@ -902,7 +1131,10 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
902
1131
|
RemoteTransport[result.id].push(result.protocol.toUpperCase());
|
|
903
1132
|
}
|
|
904
1133
|
|
|
905
|
-
if (
|
|
1134
|
+
if (
|
|
1135
|
+
result.ip &&
|
|
1136
|
+
RemoteIpAddress[result.id].indexOf(`${result.ip}:${result.portNumber}`) === -1
|
|
1137
|
+
) {
|
|
906
1138
|
RemoteIpAddress[result.id].push(`${result.ip}`); // TODO: Add ports
|
|
907
1139
|
}
|
|
908
1140
|
|
|
@@ -919,13 +1151,16 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
919
1151
|
transport: RemoteTransport[result.id],
|
|
920
1152
|
timestamp: result.time,
|
|
921
1153
|
id: result.id,
|
|
922
|
-
type: result.type
|
|
1154
|
+
type: result.type,
|
|
923
1155
|
};
|
|
924
1156
|
|
|
925
1157
|
this.statsResults.connectionType[ipType].candidateType = RemoteCandidateType[result.id];
|
|
926
1158
|
this.statsResults.connectionType[ipType].ipAddress = RemoteIpAddress[result.id];
|
|
927
1159
|
|
|
928
|
-
this.statsResults.connectionType[ipType].networkType =
|
|
1160
|
+
this.statsResults.connectionType[ipType].networkType =
|
|
1161
|
+
RemoteNetworkType[result.id][0] === NETWORK_TYPE.VPN
|
|
1162
|
+
? NETWORK_TYPE.UNKNOWN
|
|
1163
|
+
: RemoteNetworkType[result.id][0];
|
|
929
1164
|
this.statsResults.connectionType[ipType].transport = RemoteTransport[result.id];
|
|
930
1165
|
|
|
931
1166
|
this.statsResults[type][sendRecvType].totalRoundTripTime = result.totalRoundTripTime;
|
|
@@ -944,16 +1179,9 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
944
1179
|
if (!result || result.type !== 'track') {
|
|
945
1180
|
return;
|
|
946
1181
|
}
|
|
947
|
-
if (result.type !== 'track') return;
|
|
948
1182
|
|
|
949
|
-
const sendrecvType =
|
|
950
|
-
|
|
951
|
-
if (result.frameWidth && result.frameHeight) {
|
|
952
|
-
this.statsResults.resolutions[mediaType][sendrecvType].width = result.frameWidth;
|
|
953
|
-
this.statsResults.resolutions[mediaType][sendrecvType].height = result.frameHeight;
|
|
954
|
-
this.statsResults.resolutions[mediaType][sendrecvType].framesSent = result.framesSent;
|
|
955
|
-
this.statsResults.resolutions[mediaType][sendrecvType].hugeFramesSent = result.hugeFramesSent;
|
|
956
|
-
}
|
|
1183
|
+
const sendrecvType =
|
|
1184
|
+
result.remoteSource === true ? STATS.RECEIVE_DIRECTION : STATS.SEND_DIRECTION;
|
|
957
1185
|
|
|
958
1186
|
if (sendrecvType === STATS.RECEIVE_DIRECTION) {
|
|
959
1187
|
this.statsResults.resolutions[mediaType][sendrecvType].framesReceived = result.framesReceived;
|
|
@@ -961,18 +1189,21 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
961
1189
|
this.statsResults.resolutions[mediaType][sendrecvType].framesDropped = result.framesDropped;
|
|
962
1190
|
}
|
|
963
1191
|
|
|
964
|
-
|
|
965
|
-
|
|
966
|
-
|
|
1192
|
+
if (result.trackIdentifier && !mediaType.includes('audio')) {
|
|
1193
|
+
this.statsResults.resolutions[mediaType][sendrecvType].trackIdentifier =
|
|
1194
|
+
result.trackIdentifier;
|
|
967
1195
|
|
|
968
1196
|
const jitterBufferDelay = result && result.jitterBufferDelay;
|
|
969
1197
|
const jitterBufferEmittedCount = result && result.jitterBufferEmittedCount;
|
|
970
1198
|
|
|
971
|
-
this.statsResults.resolutions[mediaType][sendrecvType].avgJitterDelay =
|
|
1199
|
+
this.statsResults.resolutions[mediaType][sendrecvType].avgJitterDelay =
|
|
1200
|
+
jitterBufferEmittedCount && +jitterBufferDelay / +jitterBufferEmittedCount;
|
|
972
1201
|
|
|
973
1202
|
// Used to calculate the jitter
|
|
974
|
-
this.statsResults.resolutions[mediaType][sendrecvType].jitterBufferDelay =
|
|
975
|
-
|
|
1203
|
+
this.statsResults.resolutions[mediaType][sendrecvType].jitterBufferDelay =
|
|
1204
|
+
result.jitterBufferDelay;
|
|
1205
|
+
this.statsResults.resolutions[mediaType][sendrecvType].jitterBufferEmittedCount =
|
|
1206
|
+
result.jitterBufferEmittedCount;
|
|
976
1207
|
}
|
|
977
1208
|
}
|
|
978
1209
|
|
|
@@ -984,16 +1215,20 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
984
1215
|
* @returns {void}
|
|
985
1216
|
* @memberof StatsAnalyzer
|
|
986
1217
|
*/
|
|
987
|
-
|
|
988
|
-
|
|
1218
|
+
compareSentAndReceived(result, type) {
|
|
1219
|
+
// Don't compare on transceivers without a sender.
|
|
1220
|
+
if (!type || !this.statsResults.internal[type].send) {
|
|
989
1221
|
return;
|
|
990
1222
|
}
|
|
991
1223
|
|
|
992
1224
|
const mediaType = type;
|
|
993
1225
|
|
|
994
|
-
if (!this.statsResults.internal[mediaType].send.totalPacketsLostOnReceiver) {
|
|
1226
|
+
if (!this.statsResults.internal[mediaType].send.totalPacketsLostOnReceiver) {
|
|
1227
|
+
this.statsResults.internal[mediaType].send.totalPacketsLostOnReceiver = result.packetsLost;
|
|
1228
|
+
}
|
|
995
1229
|
|
|
996
|
-
const currentPacketLoss =
|
|
1230
|
+
const currentPacketLoss =
|
|
1231
|
+
result.packetsLost - this.statsResults.internal[mediaType].send.totalPacketsLostOnReceiver;
|
|
997
1232
|
|
|
998
1233
|
this.statsResults.internal[mediaType].send.totalPacketsLostOnReceiver = result.packetsLost;
|
|
999
1234
|
this.statsResults[mediaType].send.packetsLostOnReceiver = currentPacketLoss;
|
|
@@ -1007,18 +1242,31 @@ export class StatsAnalyzer extends EventsScope {
|
|
|
1007
1242
|
this.statsResults[mediaType].send.reportsReceived = result.reportsReceived;
|
|
1008
1243
|
|
|
1009
1244
|
// Total packloss ratio on this video section of the call
|
|
1010
|
-
this.statsResults[mediaType].send.overAllPacketLossRatio =
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1014
|
-
|
|
1245
|
+
this.statsResults[mediaType].send.overAllPacketLossRatio =
|
|
1246
|
+
this.statsResults[mediaType].send.totalPacketsLostOnReceiver > 0
|
|
1247
|
+
? this.statsResults[mediaType].send.totalPacketsLostOnReceiver /
|
|
1248
|
+
this.statsResults[mediaType].send.totalPacketsSent
|
|
1249
|
+
: 0;
|
|
1250
|
+
this.statsResults[mediaType].send.currentPacketLossRatio =
|
|
1251
|
+
this.statsResults[mediaType].send.packetsLostOnReceiver > 0
|
|
1252
|
+
? (this.statsResults[mediaType].send.packetsLostOnReceiver * 100) /
|
|
1253
|
+
(this.statsResults[mediaType].send.packetsSent +
|
|
1254
|
+
this.statsResults[mediaType].send.packetsLostOnReceiver)
|
|
1255
|
+
: 0;
|
|
1256
|
+
|
|
1257
|
+
if (
|
|
1258
|
+
this.statsResults[mediaType].send.maxPacketLossRatio <
|
|
1259
|
+
this.statsResults[mediaType].send.currentPacketLossRatio
|
|
1260
|
+
) {
|
|
1261
|
+
this.statsResults[mediaType].send.maxPacketLossRatio =
|
|
1262
|
+
this.statsResults[mediaType].send.currentPacketLossRatio;
|
|
1015
1263
|
}
|
|
1016
1264
|
|
|
1017
1265
|
if (result.type === 'remote-inbound-rtp') {
|
|
1018
1266
|
this.networkQualityMonitor.determineUplinkNetworkQuality({
|
|
1019
1267
|
mediaType,
|
|
1020
1268
|
remoteRtpResults: result,
|
|
1021
|
-
statsAnalyzerCurrentStats: this.statsResults
|
|
1269
|
+
statsAnalyzerCurrentStats: this.statsResults,
|
|
1022
1270
|
});
|
|
1023
1271
|
}
|
|
1024
1272
|
}
|