@webex/plugin-meetings 3.0.0-stream-classes.5 → 3.0.0
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/.eslintrc.js +6 -0
- package/README.md +12 -0
- package/babel.config.js +3 -0
- package/dist/annotation/constants.js +12 -20
- package/dist/annotation/constants.js.map +1 -1
- package/dist/annotation/index.js +25 -10
- package/dist/annotation/index.js.map +1 -1
- package/dist/breakouts/breakout.js +2 -3
- package/dist/breakouts/breakout.js.map +1 -1
- package/dist/breakouts/collection.js +1 -2
- package/dist/breakouts/collection.js.map +1 -1
- package/dist/breakouts/edit-lock-error.js +1 -2
- package/dist/breakouts/edit-lock-error.js.map +1 -1
- package/dist/breakouts/events.js +1 -2
- package/dist/breakouts/events.js.map +1 -1
- package/dist/breakouts/index.js +13 -14
- package/dist/breakouts/index.js.map +1 -1
- package/dist/breakouts/request.js +1 -2
- package/dist/breakouts/request.js.map +1 -1
- package/dist/breakouts/utils.js +3 -6
- package/dist/breakouts/utils.js.map +1 -1
- package/dist/common/browser-detection.js +2 -3
- package/dist/common/browser-detection.js.map +1 -1
- package/dist/common/collection.js +3 -4
- package/dist/common/collection.js.map +1 -1
- package/dist/common/config.js +1 -2
- package/dist/common/config.js.map +1 -1
- package/dist/common/errors/captcha-error.js +1 -2
- package/dist/common/errors/captcha-error.js.map +1 -1
- package/dist/common/errors/intent-to-join.js +1 -2
- package/dist/common/errors/intent-to-join.js.map +1 -1
- package/dist/common/errors/join-meeting.js +1 -2
- package/dist/common/errors/join-meeting.js.map +1 -1
- package/dist/common/errors/media.js +1 -2
- package/dist/common/errors/media.js.map +1 -1
- package/dist/common/errors/no-meeting-info.d.ts +14 -0
- package/dist/common/errors/no-meeting-info.js +50 -0
- package/dist/common/errors/no-meeting-info.js.map +1 -0
- package/dist/common/errors/parameter.js +3 -4
- package/dist/common/errors/parameter.js.map +1 -1
- package/dist/common/errors/password-error.js +1 -2
- package/dist/common/errors/password-error.js.map +1 -1
- package/dist/common/errors/permission.js +1 -2
- package/dist/common/errors/permission.js.map +1 -1
- package/dist/common/errors/reclaim-host-role-errors.d.ts +60 -0
- package/dist/common/errors/reclaim-host-role-errors.js +154 -0
- package/dist/common/errors/reclaim-host-role-errors.js.map +1 -0
- package/dist/common/errors/reconnection-in-progress.js +1 -2
- package/dist/common/errors/reconnection-in-progress.js.map +1 -1
- package/dist/common/errors/reconnection.js +1 -2
- package/dist/common/errors/reconnection.js.map +1 -1
- package/dist/common/errors/stats.js +1 -2
- package/dist/common/errors/stats.js.map +1 -1
- package/dist/{types/common → common}/errors/webex-errors.d.ts +13 -1
- package/dist/common/errors/webex-errors.js +35 -16
- package/dist/common/errors/webex-errors.js.map +1 -1
- package/dist/common/errors/webex-meetings-error.js +1 -2
- package/dist/common/errors/webex-meetings-error.js.map +1 -1
- package/dist/common/events/events-scope.js +1 -2
- package/dist/common/events/events-scope.js.map +1 -1
- package/dist/common/events/events.js +1 -2
- package/dist/common/events/events.js.map +1 -1
- package/dist/common/events/trigger-proxy.js +1 -2
- package/dist/common/events/trigger-proxy.js.map +1 -1
- package/dist/common/events/util.js +1 -2
- package/dist/common/events/util.js.map +1 -1
- package/dist/common/logs/logger-config.js +1 -2
- package/dist/common/logs/logger-config.js.map +1 -1
- package/dist/common/logs/logger-proxy.js +1 -2
- package/dist/common/logs/logger-proxy.js.map +1 -1
- package/dist/{types/common → common}/logs/request.d.ts +3 -1
- package/dist/common/logs/request.js +8 -5
- package/dist/common/logs/request.js.map +1 -1
- package/dist/common/queue.js +2 -4
- package/dist/common/queue.js.map +1 -1
- package/dist/{types/config.d.ts → config.d.ts} +1 -1
- package/dist/config.js +3 -3
- package/dist/config.js.map +1 -1
- package/dist/{types/constants.d.ts → constants.d.ts} +71 -15
- package/dist/constants.js +252 -371
- package/dist/constants.js.map +1 -1
- package/dist/controls-options-manager/constants.js +3 -6
- package/dist/controls-options-manager/constants.js.map +1 -1
- package/dist/controls-options-manager/enums.js +7 -10
- package/dist/controls-options-manager/enums.js.map +1 -1
- package/dist/controls-options-manager/index.js +27 -32
- package/dist/controls-options-manager/index.js.map +1 -1
- package/dist/controls-options-manager/util.js +1 -2
- package/dist/controls-options-manager/util.js.map +1 -1
- package/dist/index.js +8 -5
- package/dist/index.js.map +1 -1
- package/dist/interceptors/index.d.ts +2 -0
- package/dist/interceptors/index.js +15 -0
- package/dist/interceptors/index.js.map +1 -0
- package/dist/interceptors/locusRetry.d.ts +27 -0
- package/dist/interceptors/locusRetry.js +94 -0
- package/dist/interceptors/locusRetry.js.map +1 -0
- package/dist/interpretation/collection.js +1 -2
- package/dist/interpretation/collection.js.map +1 -1
- package/dist/interpretation/index.js +2 -3
- package/dist/interpretation/index.js.map +1 -1
- package/dist/interpretation/siLanguage.js +2 -3
- package/dist/interpretation/siLanguage.js.map +1 -1
- package/dist/locus-info/controlsUtils.js +12 -13
- package/dist/locus-info/controlsUtils.js.map +1 -1
- package/dist/locus-info/embeddedAppsUtils.js +3 -4
- package/dist/locus-info/embeddedAppsUtils.js.map +1 -1
- package/dist/locus-info/fullState.js +1 -2
- package/dist/locus-info/fullState.js.map +1 -1
- package/dist/locus-info/hostUtils.js +1 -2
- package/dist/locus-info/hostUtils.js.map +1 -1
- package/dist/{types/locus-info → locus-info}/index.d.ts +1 -1
- package/dist/locus-info/index.js +38 -37
- package/dist/locus-info/index.js.map +1 -1
- package/dist/locus-info/infoUtils.js +3 -4
- package/dist/locus-info/infoUtils.js.map +1 -1
- package/dist/locus-info/mediaSharesUtils.js +16 -3
- package/dist/locus-info/mediaSharesUtils.js.map +1 -1
- package/dist/{types/locus-info → locus-info}/parser.d.ts +3 -2
- package/dist/locus-info/parser.js +43 -31
- package/dist/locus-info/parser.js.map +1 -1
- package/dist/locus-info/selfUtils.js +7 -6
- package/dist/locus-info/selfUtils.js.map +1 -1
- package/dist/media/index.js +15 -10
- package/dist/media/index.js.map +1 -1
- package/dist/media/properties.js +16 -7
- package/dist/media/properties.js.map +1 -1
- package/dist/media/util.js +1 -2
- package/dist/media/util.js.map +1 -1
- package/dist/mediaQualityMetrics/config.d.ts +241 -0
- package/dist/mediaQualityMetrics/config.js +135 -339
- package/dist/mediaQualityMetrics/config.js.map +1 -1
- package/dist/{types/meeting → meeting}/in-meeting-actions.d.ts +4 -0
- package/dist/meeting/in-meeting-actions.js +18 -2
- package/dist/meeting/in-meeting-actions.js.map +1 -1
- package/dist/{types/meeting → meeting}/index.d.ts +318 -45
- package/dist/meeting/index.js +2620 -1405
- package/dist/meeting/index.js.map +1 -1
- package/dist/meeting/locusMediaRequest.js +4 -5
- package/dist/meeting/locusMediaRequest.js.map +1 -1
- package/dist/meeting/muteState.js +2 -4
- package/dist/meeting/muteState.js.map +1 -1
- package/dist/{types/meeting → meeting}/request.d.ts +2 -0
- package/dist/meeting/request.js +46 -31
- package/dist/meeting/request.js.map +1 -1
- package/dist/meeting/state.js +1 -2
- package/dist/meeting/state.js.map +1 -1
- package/dist/{types/meeting → meeting}/util.d.ts +17 -0
- package/dist/meeting/util.js +83 -10
- package/dist/meeting/util.js.map +1 -1
- package/dist/meeting/voicea-meeting.d.ts +16 -0
- package/dist/meeting/voicea-meeting.js +169 -0
- package/dist/meeting/voicea-meeting.js.map +1 -0
- package/dist/meeting-info/collection.js +3 -4
- package/dist/meeting-info/collection.js.map +1 -1
- package/dist/{types/meeting-info → meeting-info}/index.d.ts +7 -0
- package/dist/meeting-info/index.js +53 -27
- package/dist/meeting-info/index.js.map +1 -1
- package/dist/{types/meeting-info → meeting-info}/meeting-info-v2.d.ts +1 -0
- package/dist/meeting-info/meeting-info-v2.js +52 -33
- package/dist/meeting-info/meeting-info-v2.js.map +1 -1
- package/dist/meeting-info/request.js +1 -2
- package/dist/meeting-info/request.js.map +1 -1
- package/dist/meeting-info/util.js +8 -8
- package/dist/meeting-info/util.js.map +1 -1
- package/dist/meeting-info/utilv2.js +12 -9
- package/dist/meeting-info/utilv2.js.map +1 -1
- package/dist/{types/meetings → meetings}/collection.d.ts +9 -0
- package/dist/meetings/collection.js +21 -5
- package/dist/meetings/collection.js.map +1 -1
- package/dist/{types/meetings → meetings}/index.d.ts +45 -16
- package/dist/meetings/index.js +166 -74
- package/dist/meetings/index.js.map +1 -1
- package/dist/meetings/request.js +2 -3
- package/dist/meetings/request.js.map +1 -1
- package/dist/meetings/util.js +3 -10
- package/dist/meetings/util.js.map +1 -1
- package/dist/{types/member → member}/index.d.ts +1 -0
- package/dist/member/index.js +10 -3
- package/dist/member/index.js.map +1 -1
- package/dist/member/member.types.d.ts +11 -0
- package/dist/member/member.types.js +17 -0
- package/dist/member/member.types.js.map +1 -0
- package/dist/member/types.js +6 -8
- package/dist/member/types.js.map +1 -1
- package/dist/member/util.js +12 -2
- package/dist/member/util.js.map +1 -1
- package/dist/members/collection.js +1 -2
- package/dist/members/collection.js.map +1 -1
- package/dist/members/index.js +25 -8
- package/dist/members/index.js.map +1 -1
- package/dist/members/request.js +2 -3
- package/dist/members/request.js.map +1 -1
- package/dist/{types/members → members}/types.d.ts +1 -0
- package/dist/members/types.js +3 -4
- package/dist/members/types.js.map +1 -1
- package/dist/{types/members → members}/util.d.ts +6 -1
- package/dist/members/util.js +18 -8
- package/dist/members/util.js.map +1 -1
- package/dist/{types/metrics → metrics}/constants.d.ts +12 -0
- package/dist/metrics/constants.js +14 -3
- package/dist/metrics/constants.js.map +1 -1
- package/dist/metrics/index.js +3 -2
- package/dist/metrics/index.js.map +1 -1
- package/dist/multistream/mediaRequestManager.js +9 -11
- package/dist/multistream/mediaRequestManager.js.map +1 -1
- package/dist/multistream/receiveSlot.js +3 -5
- package/dist/multistream/receiveSlot.js.map +1 -1
- package/dist/multistream/receiveSlotManager.js +7 -9
- package/dist/multistream/receiveSlotManager.js.map +1 -1
- package/dist/multistream/remoteMedia.js +3 -5
- package/dist/multistream/remoteMedia.js.map +1 -1
- package/dist/multistream/remoteMediaGroup.js +7 -6
- package/dist/multistream/remoteMediaGroup.js.map +1 -1
- package/dist/multistream/remoteMediaManager.js +28 -27
- package/dist/multistream/remoteMediaManager.js.map +1 -1
- package/dist/multistream/sendSlotManager.js +9 -6
- package/dist/multistream/sendSlotManager.js.map +1 -1
- package/dist/networkQualityMonitor/index.js +1 -2
- package/dist/networkQualityMonitor/index.js.map +1 -1
- package/dist/personal-meeting-room/index.js +2 -3
- package/dist/personal-meeting-room/index.js.map +1 -1
- package/dist/personal-meeting-room/request.js +2 -3
- package/dist/personal-meeting-room/request.js.map +1 -1
- package/dist/personal-meeting-room/util.js +1 -2
- package/dist/personal-meeting-room/util.js.map +1 -1
- package/dist/reachability/clusterReachability.d.ts +109 -0
- package/dist/reachability/clusterReachability.js +357 -0
- package/dist/reachability/clusterReachability.js.map +1 -0
- package/dist/reachability/index.d.ts +105 -0
- package/dist/reachability/index.js +279 -436
- package/dist/reachability/index.js.map +1 -1
- package/dist/reachability/request.js +14 -11
- package/dist/reachability/request.js.map +1 -1
- package/dist/reachability/util.d.ts +8 -0
- package/dist/reachability/util.js +29 -0
- package/dist/reachability/util.js.map +1 -0
- package/dist/reactions/constants.js +1 -2
- package/dist/reactions/constants.js.map +1 -1
- package/dist/reactions/reactions.js +2 -4
- package/dist/reactions/reactions.js.map +1 -1
- package/dist/reactions/reactions.type.js +6 -8
- package/dist/reactions/reactions.type.js.map +1 -1
- package/dist/{types/reconnection-manager → reconnection-manager}/index.d.ts +10 -0
- package/dist/reconnection-manager/index.js +129 -106
- package/dist/reconnection-manager/index.js.map +1 -1
- package/dist/recording-controller/enums.js +4 -5
- package/dist/recording-controller/enums.js.map +1 -1
- package/dist/recording-controller/index.js +43 -51
- package/dist/recording-controller/index.js.map +1 -1
- package/dist/recording-controller/util.js +1 -2
- package/dist/recording-controller/util.js.map +1 -1
- package/dist/{types/roap → roap}/index.d.ts +2 -1
- package/dist/roap/index.js +59 -28
- package/dist/roap/index.js.map +1 -1
- package/dist/roap/request.js +14 -22
- package/dist/roap/request.js.map +1 -1
- package/dist/{types/roap → roap}/turnDiscovery.d.ts +21 -4
- package/dist/roap/turnDiscovery.js +182 -89
- package/dist/roap/turnDiscovery.js.map +1 -1
- package/dist/rtcMetrics/constants.js +1 -2
- package/dist/rtcMetrics/constants.js.map +1 -1
- package/dist/{types/rtcMetrics → rtcMetrics}/index.d.ts +15 -1
- package/dist/rtcMetrics/index.js +72 -12
- package/dist/rtcMetrics/index.js.map +1 -1
- package/dist/statsAnalyzer/global.js +1 -2
- package/dist/statsAnalyzer/global.js.map +1 -1
- package/dist/{types/statsAnalyzer → statsAnalyzer}/index.d.ts +28 -11
- package/dist/statsAnalyzer/index.js +371 -318
- package/dist/statsAnalyzer/index.js.map +1 -1
- package/dist/statsAnalyzer/mqaUtil.d.ts +48 -0
- package/dist/statsAnalyzer/mqaUtil.js +295 -162
- package/dist/statsAnalyzer/mqaUtil.js.map +1 -1
- package/dist/transcription/index.js +1 -2
- package/dist/transcription/index.js.map +1 -1
- package/dist/webinar/collection.d.ts +16 -0
- package/dist/webinar/collection.js +43 -0
- package/dist/webinar/collection.js.map +1 -0
- package/dist/webinar/index.d.ts +5 -0
- package/dist/webinar/index.js +68 -0
- package/dist/webinar/index.js.map +1 -0
- package/jest.config.js +3 -0
- package/package.json +44 -24
- package/process +1 -0
- package/src/common/errors/no-meeting-info.ts +24 -0
- package/src/common/errors/reclaim-host-role-errors.ts +134 -0
- package/src/common/errors/webex-errors.ts +19 -2
- package/src/common/logs/request.ts +5 -1
- package/src/config.ts +3 -5
- package/src/constants.ts +77 -8
- package/src/index.ts +4 -0
- package/src/interceptors/index.ts +3 -0
- package/src/interceptors/locusRetry.ts +67 -0
- package/src/locus-info/index.ts +19 -14
- package/src/locus-info/mediaSharesUtils.ts +16 -0
- package/src/locus-info/parser.ts +40 -21
- package/src/media/index.ts +8 -6
- package/src/media/properties.ts +17 -2
- package/src/mediaQualityMetrics/config.ts +103 -238
- package/src/meeting/in-meeting-actions.ts +8 -0
- package/src/meeting/index.ts +1664 -642
- package/src/meeting/request.ts +18 -0
- package/src/meeting/util.ts +102 -1
- package/src/meeting/voicea-meeting.ts +122 -0
- package/src/meeting-info/index.ts +47 -20
- package/src/meeting-info/meeting-info-v2.ts +32 -16
- package/src/meeting-info/util.ts +12 -9
- package/src/meeting-info/utilv2.ts +25 -15
- package/src/meetings/collection.ts +13 -0
- package/src/meetings/index.ts +112 -31
- package/src/meetings/util.ts +2 -8
- package/src/member/index.ts +9 -1
- package/src/member/member.types.ts +13 -0
- package/src/member/util.ts +14 -0
- package/src/members/index.ts +29 -2
- package/src/members/types.ts +1 -0
- package/src/members/util.ts +15 -1
- package/src/metrics/constants.ts +12 -0
- package/src/reachability/clusterReachability.ts +320 -0
- package/src/reachability/index.ts +221 -382
- package/src/reachability/request.ts +1 -1
- package/src/reachability/util.ts +24 -0
- package/src/reconnection-manager/index.ts +87 -83
- package/src/roap/index.ts +60 -24
- package/src/roap/request.ts +4 -17
- package/src/roap/turnDiscovery.ts +112 -39
- package/src/rtcMetrics/index.ts +71 -5
- package/src/statsAnalyzer/index.ts +430 -427
- package/src/statsAnalyzer/mqaUtil.ts +317 -168
- package/src/webinar/collection.ts +31 -0
- package/src/webinar/index.ts +62 -0
- package/test/integration/spec/journey.js +12 -12
- package/test/integration/spec/space-meeting.js +1 -1
- package/test/unit/spec/breakouts/breakout.ts +2 -1
- package/test/unit/spec/breakouts/index.ts +7 -4
- package/test/unit/spec/interceptors/locusRetry.ts +131 -0
- package/test/unit/spec/locus-info/index.js +88 -12
- package/test/unit/spec/locus-info/lib/SeqCmp.json +16 -0
- package/test/unit/spec/locus-info/mediaSharesUtils.ts +10 -0
- package/test/unit/spec/locus-info/parser.js +54 -13
- package/test/unit/spec/locus-info/selfUtils.js +1 -1
- package/test/unit/spec/media/index.ts +25 -4
- package/test/unit/spec/media/properties.ts +2 -2
- package/test/unit/spec/meeting/in-meeting-actions.ts +4 -0
- package/test/unit/spec/meeting/index.js +4388 -1382
- package/test/unit/spec/meeting/request.js +63 -12
- package/test/unit/spec/meeting/utils.js +145 -10
- package/test/unit/spec/meeting/voicea-meeting.ts +266 -0
- package/test/unit/spec/meeting-info/index.js +180 -61
- package/test/unit/spec/meeting-info/meetinginfov2.js +216 -68
- package/test/unit/spec/meetings/collection.js +12 -0
- package/test/unit/spec/meetings/index.js +674 -193
- package/test/unit/spec/meetings/utils.js +35 -12
- package/test/unit/spec/member/index.js +8 -7
- package/test/unit/spec/member/util.js +32 -0
- package/test/unit/spec/members/index.js +130 -17
- package/test/unit/spec/members/utils.js +26 -0
- package/test/unit/spec/metrics/index.js +1 -2
- package/test/unit/spec/multistream/mediaRequestManager.ts +1 -0
- package/test/unit/spec/reachability/clusterReachability.ts +279 -0
- package/test/unit/spec/reachability/index.ts +505 -135
- package/test/unit/spec/reachability/util.ts +40 -0
- package/test/unit/spec/reconnection-manager/index.js +74 -17
- package/test/unit/spec/recording-controller/index.js +0 -1
- package/test/unit/spec/roap/index.ts +181 -61
- package/test/unit/spec/roap/request.ts +27 -3
- package/test/unit/spec/roap/turnDiscovery.ts +363 -102
- package/test/unit/spec/rtcMetrics/index.ts +57 -3
- package/test/unit/spec/stats-analyzer/index.js +1225 -12
- package/test/unit/spec/webinar/collection.ts +13 -0
- package/test/unit/spec/webinar/index.ts +60 -0
- package/test/utils/webex-test-users.js +12 -4
- package/dist/types/mediaQualityMetrics/config.d.ts +0 -365
- package/dist/types/reachability/index.d.ts +0 -152
- package/dist/types/statsAnalyzer/mqaUtil.d.ts +0 -24
- /package/dist/{types/annotation → annotation}/annotation.types.d.ts +0 -0
- /package/dist/{types/annotation → annotation}/constants.d.ts +0 -0
- /package/dist/{types/annotation → annotation}/index.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/breakout.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/collection.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/edit-lock-error.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/events.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/index.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/request.d.ts +0 -0
- /package/dist/{types/breakouts → breakouts}/utils.d.ts +0 -0
- /package/dist/{types/common → common}/browser-detection.d.ts +0 -0
- /package/dist/{types/common → common}/collection.d.ts +0 -0
- /package/dist/{types/common → common}/config.d.ts +0 -0
- /package/dist/{types/common → common}/errors/captcha-error.d.ts +0 -0
- /package/dist/{types/common → common}/errors/intent-to-join.d.ts +0 -0
- /package/dist/{types/common → common}/errors/join-meeting.d.ts +0 -0
- /package/dist/{types/common → common}/errors/media.d.ts +0 -0
- /package/dist/{types/common → common}/errors/parameter.d.ts +0 -0
- /package/dist/{types/common → common}/errors/password-error.d.ts +0 -0
- /package/dist/{types/common → common}/errors/permission.d.ts +0 -0
- /package/dist/{types/common → common}/errors/reconnection-in-progress.d.ts +0 -0
- /package/dist/{types/common → common}/errors/reconnection.d.ts +0 -0
- /package/dist/{types/common → common}/errors/stats.d.ts +0 -0
- /package/dist/{types/common → common}/errors/webex-meetings-error.d.ts +0 -0
- /package/dist/{types/common → common}/events/events-scope.d.ts +0 -0
- /package/dist/{types/common → common}/events/events.d.ts +0 -0
- /package/dist/{types/common → common}/events/trigger-proxy.d.ts +0 -0
- /package/dist/{types/common → common}/events/util.d.ts +0 -0
- /package/dist/{types/common → common}/logs/logger-config.d.ts +0 -0
- /package/dist/{types/common → common}/logs/logger-proxy.d.ts +0 -0
- /package/dist/{types/common → common}/queue.d.ts +0 -0
- /package/dist/{types/controls-options-manager → controls-options-manager}/constants.d.ts +0 -0
- /package/dist/{types/controls-options-manager → controls-options-manager}/enums.d.ts +0 -0
- /package/dist/{types/controls-options-manager → controls-options-manager}/index.d.ts +0 -0
- /package/dist/{types/controls-options-manager → controls-options-manager}/types.d.ts +0 -0
- /package/dist/{types/controls-options-manager → controls-options-manager}/util.d.ts +0 -0
- /package/dist/{types/index.d.ts → index.d.ts} +0 -0
- /package/dist/{types/interpretation → interpretation}/collection.d.ts +0 -0
- /package/dist/{types/interpretation → interpretation}/index.d.ts +0 -0
- /package/dist/{types/interpretation → interpretation}/siLanguage.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/controlsUtils.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/embeddedAppsUtils.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/fullState.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/hostUtils.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/infoUtils.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/mediaSharesUtils.d.ts +0 -0
- /package/dist/{types/locus-info → locus-info}/selfUtils.d.ts +0 -0
- /package/dist/{types/media → media}/index.d.ts +0 -0
- /package/dist/{types/media → media}/properties.d.ts +0 -0
- /package/dist/{types/media → media}/util.d.ts +0 -0
- /package/dist/{types/meeting → meeting}/locusMediaRequest.d.ts +0 -0
- /package/dist/{types/meeting → meeting}/muteState.d.ts +0 -0
- /package/dist/{types/meeting → meeting}/request.type.d.ts +0 -0
- /package/dist/{types/meeting → meeting}/state.d.ts +0 -0
- /package/dist/{types/meeting-info → meeting-info}/collection.d.ts +0 -0
- /package/dist/{types/meeting-info → meeting-info}/request.d.ts +0 -0
- /package/dist/{types/meeting-info → meeting-info}/util.d.ts +0 -0
- /package/dist/{types/meeting-info → meeting-info}/utilv2.d.ts +0 -0
- /package/dist/{types/meetings → meetings}/meetings.types.d.ts +0 -0
- /package/dist/{types/meetings → meetings}/request.d.ts +0 -0
- /package/dist/{types/meetings → meetings}/util.d.ts +0 -0
- /package/dist/{types/member → member}/types.d.ts +0 -0
- /package/dist/{types/member → member}/util.d.ts +0 -0
- /package/dist/{types/members → members}/collection.d.ts +0 -0
- /package/dist/{types/members → members}/index.d.ts +0 -0
- /package/dist/{types/members → members}/request.d.ts +0 -0
- /package/dist/{types/metrics → metrics}/index.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/mediaRequestManager.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/receiveSlot.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/receiveSlotManager.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/remoteMedia.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/remoteMediaGroup.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/remoteMediaManager.d.ts +0 -0
- /package/dist/{types/multistream → multistream}/sendSlotManager.d.ts +0 -0
- /package/dist/{types/networkQualityMonitor → networkQualityMonitor}/index.d.ts +0 -0
- /package/dist/{types/personal-meeting-room → personal-meeting-room}/index.d.ts +0 -0
- /package/dist/{types/personal-meeting-room → personal-meeting-room}/request.d.ts +0 -0
- /package/dist/{types/personal-meeting-room → personal-meeting-room}/util.d.ts +0 -0
- /package/dist/{types/reachability → reachability}/request.d.ts +0 -0
- /package/dist/{types/reactions → reactions}/constants.d.ts +0 -0
- /package/dist/{types/reactions → reactions}/reactions.d.ts +0 -0
- /package/dist/{types/reactions → reactions}/reactions.type.d.ts +0 -0
- /package/dist/{types/recording-controller → recording-controller}/enums.d.ts +0 -0
- /package/dist/{types/recording-controller → recording-controller}/index.d.ts +0 -0
- /package/dist/{types/recording-controller → recording-controller}/util.d.ts +0 -0
- /package/dist/{types/roap → roap}/request.d.ts +0 -0
- /package/dist/{types/rtcMetrics → rtcMetrics}/constants.d.ts +0 -0
- /package/dist/{types/statsAnalyzer → statsAnalyzer}/global.d.ts +0 -0
- /package/dist/{types/transcription → transcription}/index.d.ts +0 -0
- /package/test/unit/spec/locus-info/{selfConstant.js → lib/selfConstant.js} +0 -0
|
@@ -162,9 +162,24 @@ describe('plugin-meetings', () => {
|
|
|
162
162
|
});
|
|
163
163
|
|
|
164
164
|
describe("#handleRoapMercury", () => {
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
165
|
+
let envelope;
|
|
166
|
+
let meetingCollection;
|
|
167
|
+
let roapMessageReceived;
|
|
168
|
+
let handleTurnDiscoveryResponse;
|
|
169
|
+
let meeting;
|
|
170
|
+
|
|
171
|
+
beforeEach(() => {
|
|
172
|
+
roapMessageReceived = sinon.stub();
|
|
173
|
+
handleTurnDiscoveryResponse = sinon.stub();
|
|
174
|
+
|
|
175
|
+
meeting = {
|
|
176
|
+
id: 'meeting-id',
|
|
177
|
+
roapMessageReceived,
|
|
178
|
+
roap: {
|
|
179
|
+
turnDiscovery: {handleTurnDiscoveryResponse}
|
|
180
|
+
}
|
|
181
|
+
};
|
|
182
|
+
envelope = {
|
|
168
183
|
data: {
|
|
169
184
|
message:{
|
|
170
185
|
seq: "seq",
|
|
@@ -178,17 +193,12 @@ describe('plugin-meetings', () => {
|
|
|
178
193
|
eventType: 'locus.message.roap',
|
|
179
194
|
}
|
|
180
195
|
};
|
|
181
|
-
|
|
182
|
-
getByKey: () =>
|
|
183
|
-
id: 'meeting-id',
|
|
184
|
-
mediaProperties: {
|
|
185
|
-
webrtcMediaConnection: {
|
|
186
|
-
roapMessageReceived
|
|
187
|
-
}
|
|
188
|
-
}
|
|
189
|
-
})
|
|
196
|
+
meetingCollection = {
|
|
197
|
+
getByKey: () => meeting
|
|
190
198
|
};
|
|
199
|
+
});
|
|
191
200
|
|
|
201
|
+
it('it sends the correct behaviour metric', () => {
|
|
192
202
|
MeetingsUtil.handleRoapMercury(envelope, meetingCollection);
|
|
193
203
|
assert.calledWith(Metrics.sendBehavioralMetric, BEHAVIORAL_METRICS.ROAP_MERCURY_EVENT_RECEIVED, {
|
|
194
204
|
correlation_id: 'correlationId',
|
|
@@ -207,6 +217,19 @@ describe('plugin-meetings', () => {
|
|
|
207
217
|
})
|
|
208
218
|
|
|
209
219
|
});
|
|
220
|
+
|
|
221
|
+
it('calls handleTurnDiscoveryResponse for TURN_DISCOVERY_RESPONSE', () => {
|
|
222
|
+
envelope.data.message.messageType = 'TURN_DISCOVERY_RESPONSE';
|
|
223
|
+
delete envelope.data.message.sdps;
|
|
224
|
+
MeetingsUtil.handleRoapMercury(envelope, meetingCollection);
|
|
225
|
+
assert.calledWith(meeting.roap.turnDiscovery.handleTurnDiscoveryResponse, {
|
|
226
|
+
seq: "seq",
|
|
227
|
+
messageType: 'TURN_DISCOVERY_RESPONSE',
|
|
228
|
+
errorType: 'errorType',
|
|
229
|
+
tieBreaker: 'tieBreaker',
|
|
230
|
+
errorCause: 'errorCause',
|
|
231
|
+
}, 'from mercury')
|
|
232
|
+
});
|
|
210
233
|
})
|
|
211
234
|
});
|
|
212
235
|
|
|
@@ -17,13 +17,7 @@ describe('member', () => {
|
|
|
17
17
|
assert.exists(member.supportsInterpretation);
|
|
18
18
|
assert.exists(member.supportsBreakouts);
|
|
19
19
|
assert.exists(member.supportLiveAnnotation);
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
it('checks that processParticipant calls isHandRaised', () => {
|
|
23
|
-
sinon.spy(MemberUtil, 'isHandRaised');
|
|
24
|
-
member.processParticipant(participant);
|
|
25
|
-
|
|
26
|
-
assert.calledOnceWithExactly(MemberUtil.isHandRaised, participant);
|
|
20
|
+
assert.exists(member.canReclaimHost);
|
|
27
21
|
});
|
|
28
22
|
|
|
29
23
|
describe('roles', () => {
|
|
@@ -49,6 +43,13 @@ describe('member', () => {
|
|
|
49
43
|
|
|
50
44
|
assert.calledOnceWithExactly(MemberUtil.isHandRaised, participant);
|
|
51
45
|
});
|
|
46
|
+
|
|
47
|
+
it('checks that processParticipant calls canReclaimHost', () => {
|
|
48
|
+
sinon.spy(MemberUtil, 'canReclaimHost');
|
|
49
|
+
member.processParticipant(participant);
|
|
50
|
+
|
|
51
|
+
assert.calledOnceWithExactly(MemberUtil.canReclaimHost, participant);
|
|
52
|
+
});
|
|
52
53
|
})
|
|
53
54
|
|
|
54
55
|
describe('#processMember', () => {
|
|
@@ -50,6 +50,38 @@ describe('plugin-meetings', () => {
|
|
|
50
50
|
});
|
|
51
51
|
});
|
|
52
52
|
|
|
53
|
+
describe('MemberUtil.canReclaimHost', () => {
|
|
54
|
+
it('throws error when there is no participant', () => {
|
|
55
|
+
assert.throws(() => {
|
|
56
|
+
MemberUtil.canReclaimHost();
|
|
57
|
+
}, 'canReclaimHostRole could not be processed, participant is undefined.');
|
|
58
|
+
});
|
|
59
|
+
|
|
60
|
+
it('returns true when canReclaimHostRole is true', () => {
|
|
61
|
+
const participant = {
|
|
62
|
+
canReclaimHostRole: true,
|
|
63
|
+
};
|
|
64
|
+
|
|
65
|
+
assert.isTrue(MemberUtil.canReclaimHost(participant));
|
|
66
|
+
});
|
|
67
|
+
|
|
68
|
+
it('returns false when canReclaimHostRole is false', () => {
|
|
69
|
+
const participant = {
|
|
70
|
+
canReclaimHostRole: false,
|
|
71
|
+
};
|
|
72
|
+
|
|
73
|
+
assert.isFalse(MemberUtil.canReclaimHost(participant));
|
|
74
|
+
});
|
|
75
|
+
|
|
76
|
+
it('returns false when canReclaimHostRole is falsy', () => {
|
|
77
|
+
const participant = {
|
|
78
|
+
canReclaimHostRole: undefined,
|
|
79
|
+
};
|
|
80
|
+
|
|
81
|
+
assert.isFalse(MemberUtil.canReclaimHost(participant));
|
|
82
|
+
});
|
|
83
|
+
});
|
|
84
|
+
|
|
53
85
|
describe('MemberUtil.extractControlRoles', () => {
|
|
54
86
|
it('happy path extract control roles', () => {
|
|
55
87
|
const participant = {
|
|
@@ -17,6 +17,12 @@ import MembersUtil from '@webex/plugin-meetings/src/members/util';
|
|
|
17
17
|
import * as MembersRequestImport from '@webex/plugin-meetings/src/members/request';
|
|
18
18
|
import Trigger from '@webex/plugin-meetings/src/common/events/trigger-proxy';
|
|
19
19
|
import {EVENT_TRIGGERS} from '@webex/plugin-meetings/src/constants';
|
|
20
|
+
import {
|
|
21
|
+
ReclaimHostEmptyWrongKeyError,
|
|
22
|
+
ReclaimHostIsHostAlreadyError,
|
|
23
|
+
ReclaimHostNotAllowedError,
|
|
24
|
+
ReclaimHostNotSupportedError,
|
|
25
|
+
} from '../../../../src/common/errors/reclaim-host-role-errors';
|
|
20
26
|
|
|
21
27
|
const {assert} = chai;
|
|
22
28
|
|
|
@@ -337,7 +343,17 @@ describe('plugin-meetings', () => {
|
|
|
337
343
|
});
|
|
338
344
|
|
|
339
345
|
describe('#assignRoles', () => {
|
|
340
|
-
const
|
|
346
|
+
const fakeRoles = [
|
|
347
|
+
{type: 'PRESENTER', hasRole: true},
|
|
348
|
+
{type: 'MODERATOR', hasRole: false},
|
|
349
|
+
{type: 'COHOST', hasRole: true},
|
|
350
|
+
];
|
|
351
|
+
|
|
352
|
+
const resolvedValue = "it worked";
|
|
353
|
+
|
|
354
|
+
const genericMessage = 'Generic error from the API';
|
|
355
|
+
|
|
356
|
+
const setup = (locusUrl, errorCode) => {
|
|
341
357
|
const members = createMembers({url: locusUrl});
|
|
342
358
|
|
|
343
359
|
const spies = {
|
|
@@ -345,9 +361,14 @@ describe('plugin-meetings', () => {
|
|
|
345
361
|
MembersUtil,
|
|
346
362
|
'generateRoleAssignmentMemberOptions'
|
|
347
363
|
),
|
|
348
|
-
assignRolesMember: sandbox.spy(members.membersRequest, 'assignRolesMember'),
|
|
349
364
|
};
|
|
350
365
|
|
|
366
|
+
if (errorCode) {
|
|
367
|
+
spies.assignRolesMember = sandbox.stub(members.membersRequest, 'assignRolesMember').rejects({body: {errorCode}, message: genericMessage});
|
|
368
|
+
} else {
|
|
369
|
+
spies.assignRolesMember = sandbox.stub(members.membersRequest, 'assignRolesMember').resolves(resolvedValue);
|
|
370
|
+
}
|
|
371
|
+
|
|
351
372
|
return {members, spies};
|
|
352
373
|
};
|
|
353
374
|
|
|
@@ -357,6 +378,21 @@ describe('plugin-meetings', () => {
|
|
|
357
378
|
assert.notCalled(spies.assignRolesMember);
|
|
358
379
|
};
|
|
359
380
|
|
|
381
|
+
const checkError = async (error, expectedMemberId, expectedRoles, expectedLocusUrl, resultPromise, expectedMessage, spies) => {
|
|
382
|
+
await assert.isRejected(resultPromise, error, expectedMessage);
|
|
383
|
+
assert.calledOnceWithExactly(
|
|
384
|
+
spies.generateRoleAssignmentMemberOptions,
|
|
385
|
+
expectedMemberId,
|
|
386
|
+
expectedRoles,
|
|
387
|
+
expectedLocusUrl
|
|
388
|
+
);
|
|
389
|
+
assert.calledOnceWithExactly(spies.assignRolesMember, {
|
|
390
|
+
memberId: expectedMemberId,
|
|
391
|
+
roles: expectedRoles,
|
|
392
|
+
locusUrl: expectedLocusUrl,
|
|
393
|
+
});
|
|
394
|
+
};
|
|
395
|
+
|
|
360
396
|
const checkValid = async (
|
|
361
397
|
resultPromise,
|
|
362
398
|
spies,
|
|
@@ -364,7 +400,7 @@ describe('plugin-meetings', () => {
|
|
|
364
400
|
expectedRoles,
|
|
365
401
|
expectedLocusUrl
|
|
366
402
|
) => {
|
|
367
|
-
await assert.isFulfilled(resultPromise);
|
|
403
|
+
const resolvedValue = await assert.isFulfilled(resultPromise);
|
|
368
404
|
assert.calledOnceWithExactly(
|
|
369
405
|
spies.generateRoleAssignmentMemberOptions,
|
|
370
406
|
expectedMemberId,
|
|
@@ -376,7 +412,7 @@ describe('plugin-meetings', () => {
|
|
|
376
412
|
roles: expectedRoles,
|
|
377
413
|
locusUrl: expectedLocusUrl,
|
|
378
414
|
});
|
|
379
|
-
assert.strictEqual(
|
|
415
|
+
assert.strictEqual(resolvedValue, resolvedValue);
|
|
380
416
|
};
|
|
381
417
|
|
|
382
418
|
it('should not make a request if there is no member id', async () => {
|
|
@@ -387,7 +423,7 @@ describe('plugin-meetings', () => {
|
|
|
387
423
|
await checkInvalid(
|
|
388
424
|
resultPromise,
|
|
389
425
|
'The member id must be defined to assign the roles to a member.',
|
|
390
|
-
spies
|
|
426
|
+
spies,
|
|
391
427
|
);
|
|
392
428
|
});
|
|
393
429
|
|
|
@@ -399,7 +435,92 @@ describe('plugin-meetings', () => {
|
|
|
399
435
|
await checkInvalid(
|
|
400
436
|
resultPromise,
|
|
401
437
|
'The associated locus url for this meetings members object must be defined.',
|
|
402
|
-
spies
|
|
438
|
+
spies,
|
|
439
|
+
);
|
|
440
|
+
});
|
|
441
|
+
|
|
442
|
+
it('should not make a request if locus throws ReclaimHostNotSupportedError', async () => {
|
|
443
|
+
const memberId = uuid.v4();
|
|
444
|
+
const {members, spies} = setup(url1, 2400127);
|
|
445
|
+
|
|
446
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
447
|
+
|
|
448
|
+
await checkError(
|
|
449
|
+
ReclaimHostNotSupportedError,
|
|
450
|
+
memberId,
|
|
451
|
+
fakeRoles,
|
|
452
|
+
url1,
|
|
453
|
+
resultPromise,
|
|
454
|
+
'Non converged meetings, PSTN or SIP users in converged meetings are not supported currently.',
|
|
455
|
+
spies,
|
|
456
|
+
);
|
|
457
|
+
});
|
|
458
|
+
|
|
459
|
+
it('should not make a request if locus throws ReclaimHostNotAllowedError', async () => {
|
|
460
|
+
const memberId = uuid.v4();
|
|
461
|
+
const {members, spies} = setup(url1, 2403135);
|
|
462
|
+
|
|
463
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
464
|
+
|
|
465
|
+
await checkError(
|
|
466
|
+
ReclaimHostNotAllowedError,
|
|
467
|
+
memberId,
|
|
468
|
+
fakeRoles,
|
|
469
|
+
url1,
|
|
470
|
+
resultPromise,
|
|
471
|
+
'Reclaim Host Role Not Allowed For Other Participants. Participants cannot claim host role in PMR meeting, space instant meeting or escalated instant meeting. However, the original host still can reclaim host role when it manually makes another participant to be the host.',
|
|
472
|
+
spies,
|
|
473
|
+
);
|
|
474
|
+
});
|
|
475
|
+
|
|
476
|
+
it('should not make a request if locus throws ReclaimHostEmptyWrongKeyError', async () => {
|
|
477
|
+
const memberId = uuid.v4();
|
|
478
|
+
const {members, spies} = setup(url1, 2403136);
|
|
479
|
+
|
|
480
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
481
|
+
|
|
482
|
+
await checkError(
|
|
483
|
+
ReclaimHostEmptyWrongKeyError,
|
|
484
|
+
memberId,
|
|
485
|
+
fakeRoles,
|
|
486
|
+
url1,
|
|
487
|
+
resultPromise,
|
|
488
|
+
'Host Key Not Specified Or Matched. The original host can reclaim the host role without entering the host key. However, any other person who claims the host role must enter the host key to get it.',
|
|
489
|
+
spies,
|
|
490
|
+
);
|
|
491
|
+
});
|
|
492
|
+
|
|
493
|
+
it('should not make a request if locus throws ReclaimHostIsHostAlreadyError', async () => {
|
|
494
|
+
const memberId = uuid.v4();
|
|
495
|
+
const {members, spies} = setup(url1, 2409150);
|
|
496
|
+
|
|
497
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
498
|
+
|
|
499
|
+
await checkError(
|
|
500
|
+
ReclaimHostIsHostAlreadyError,
|
|
501
|
+
memberId,
|
|
502
|
+
fakeRoles,
|
|
503
|
+
url1,
|
|
504
|
+
resultPromise,
|
|
505
|
+
'Participant Having Host Role Already. Participant who sends request to reclaim host role has already a host role.',
|
|
506
|
+
spies,
|
|
507
|
+
);
|
|
508
|
+
});
|
|
509
|
+
|
|
510
|
+
it('should not make a request if locus throws a different error', async () => {
|
|
511
|
+
const memberId = uuid.v4();
|
|
512
|
+
const {members, spies} = setup(url1, 1234);
|
|
513
|
+
|
|
514
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
515
|
+
|
|
516
|
+
await checkError(
|
|
517
|
+
{body: {errorCode: 1234}, message: genericMessage},
|
|
518
|
+
memberId,
|
|
519
|
+
fakeRoles,
|
|
520
|
+
url1,
|
|
521
|
+
resultPromise,
|
|
522
|
+
genericMessage,
|
|
523
|
+
spies,
|
|
403
524
|
);
|
|
404
525
|
});
|
|
405
526
|
|
|
@@ -407,22 +528,14 @@ describe('plugin-meetings', () => {
|
|
|
407
528
|
const memberId = uuid.v4();
|
|
408
529
|
const {members, spies} = setup(url1);
|
|
409
530
|
|
|
410
|
-
const resultPromise = members.assignRoles(memberId,
|
|
411
|
-
{type: 'PRESENTER', hasRole: true},
|
|
412
|
-
{type: 'MODERATOR', hasRole: false},
|
|
413
|
-
{type: 'COHOST', hasRole: true},
|
|
414
|
-
]);
|
|
531
|
+
const resultPromise = members.assignRoles(memberId, fakeRoles);
|
|
415
532
|
|
|
416
533
|
await checkValid(
|
|
417
534
|
resultPromise,
|
|
418
535
|
spies,
|
|
419
536
|
memberId,
|
|
420
|
-
|
|
421
|
-
|
|
422
|
-
{type: 'MODERATOR', hasRole: false},
|
|
423
|
-
{type: 'COHOST', hasRole: true},
|
|
424
|
-
],
|
|
425
|
-
url1
|
|
537
|
+
fakeRoles,
|
|
538
|
+
url1,
|
|
426
539
|
);
|
|
427
540
|
});
|
|
428
541
|
});
|
|
@@ -59,6 +59,32 @@ describe('plugin-meetings', () => {
|
|
|
59
59
|
},
|
|
60
60
|
});
|
|
61
61
|
});
|
|
62
|
+
|
|
63
|
+
it('returns the correct request params with a hostKey', () => {
|
|
64
|
+
const format = {
|
|
65
|
+
locusUrl: 'locusUrl',
|
|
66
|
+
memberId: 'test',
|
|
67
|
+
roles: [
|
|
68
|
+
{type: 'PRESENTER', hasRole: true, hostKey: '123456'},
|
|
69
|
+
{type: 'MODERATOR', hasRole: false, hostKey: '123456'},
|
|
70
|
+
{type: 'COHOST', hasRole: true, hostKey: '123456'},
|
|
71
|
+
],
|
|
72
|
+
};
|
|
73
|
+
|
|
74
|
+
assert.deepEqual(MembersUtil.getRoleAssignmentMemberRequestParams(format), {
|
|
75
|
+
method: 'PATCH',
|
|
76
|
+
uri: `locusUrl/${PARTICIPANT}/test/${CONTROLS}`,
|
|
77
|
+
body: {
|
|
78
|
+
role: {
|
|
79
|
+
roles: [
|
|
80
|
+
{type: 'PRESENTER', hasRole: true, hostKey: '123456'},
|
|
81
|
+
{type: 'MODERATOR', hasRole: false, hostKey: '123456'},
|
|
82
|
+
{type: 'COHOST', hasRole: true, hostKey: '123456'},
|
|
83
|
+
],
|
|
84
|
+
},
|
|
85
|
+
},
|
|
86
|
+
});
|
|
87
|
+
});
|
|
62
88
|
});
|
|
63
89
|
|
|
64
90
|
describe('#generateRaiseHandMemberOptions', () => {
|
|
@@ -5,7 +5,6 @@ import 'jsdom-global/register';
|
|
|
5
5
|
import sinon from 'sinon';
|
|
6
6
|
import Metrics from '@webex/internal-plugin-metrics';
|
|
7
7
|
import MockWebex from '@webex/test-helper-mock-webex';
|
|
8
|
-
import {browserOnly} from '@webex/test-helper-mocha';
|
|
9
8
|
import {assert} from '@webex/test-helper-chai';
|
|
10
9
|
|
|
11
10
|
import metrics from '@webex/plugin-meetings/src/metrics';
|
|
@@ -14,7 +13,7 @@ import metrics from '@webex/plugin-meetings/src/metrics';
|
|
|
14
13
|
* Meeting can only run in a browser, so we can only send metrics for
|
|
15
14
|
* browser usage.
|
|
16
15
|
*/
|
|
17
|
-
|
|
16
|
+
describe('Meeting metrics', () => {
|
|
18
17
|
let webex, mockSubmitMetric, sandbox;
|
|
19
18
|
|
|
20
19
|
beforeEach(() => {
|
|
@@ -0,0 +1,279 @@
|
|
|
1
|
+
import {assert} from '@webex/test-helper-chai';
|
|
2
|
+
import MockWebex from '@webex/test-helper-mock-webex';
|
|
3
|
+
import sinon from 'sinon';
|
|
4
|
+
import testUtils from '../../../utils/testUtils';
|
|
5
|
+
|
|
6
|
+
// packages/@webex/plugin-meetings/test/unit/spec/reachability/clusterReachability.ts
|
|
7
|
+
import { ClusterReachability } from '@webex/plugin-meetings/src/reachability/clusterReachability'; // replace with actual path
|
|
8
|
+
|
|
9
|
+
describe('ClusterReachability', () => {
|
|
10
|
+
let previousRTCPeerConnection;
|
|
11
|
+
let clusterReachability;
|
|
12
|
+
let fakePeerConnection;
|
|
13
|
+
|
|
14
|
+
const FAKE_OFFER = {type: 'offer', sdp: 'fake sdp'};
|
|
15
|
+
|
|
16
|
+
beforeEach(() => {
|
|
17
|
+
fakePeerConnection = {
|
|
18
|
+
createOffer: sinon.stub().resolves(FAKE_OFFER),
|
|
19
|
+
setLocalDescription: sinon.stub().resolves(),
|
|
20
|
+
close: sinon.stub(),
|
|
21
|
+
iceGatheringState: 'new',
|
|
22
|
+
};
|
|
23
|
+
|
|
24
|
+
previousRTCPeerConnection = global.RTCPeerConnection;
|
|
25
|
+
global.RTCPeerConnection = sinon.stub().returns(fakePeerConnection);
|
|
26
|
+
|
|
27
|
+
clusterReachability = new ClusterReachability('testName', {
|
|
28
|
+
isVideoMesh: false,
|
|
29
|
+
udp: ['stun:udp1', 'stun:udp2'],
|
|
30
|
+
tcp: ['stun:tcp1.webex.com', 'stun:tcp2.webex.com:5004'],
|
|
31
|
+
xtls: ['xtls1', 'xtls2'],
|
|
32
|
+
});
|
|
33
|
+
|
|
34
|
+
});
|
|
35
|
+
|
|
36
|
+
afterEach(() => {
|
|
37
|
+
global.RTCPeerConnection = previousRTCPeerConnection;
|
|
38
|
+
});
|
|
39
|
+
|
|
40
|
+
it('should create an instance correctly', () => {
|
|
41
|
+
assert.instanceOf(clusterReachability, ClusterReachability);
|
|
42
|
+
assert.equal(clusterReachability.name, 'testName');
|
|
43
|
+
assert.equal(clusterReachability.isVideoMesh, false);
|
|
44
|
+
assert.equal(clusterReachability.numUdpUrls, 2);
|
|
45
|
+
assert.equal(clusterReachability.numTcpUrls, 2);
|
|
46
|
+
});
|
|
47
|
+
|
|
48
|
+
it('should create a peer connection with the right config', () => {
|
|
49
|
+
assert.calledOnceWithExactly(global.RTCPeerConnection, {
|
|
50
|
+
iceServers: [
|
|
51
|
+
{username: '', credential: '', urls: ['stun:udp1']},
|
|
52
|
+
{username: '', credential: '', urls: ['stun:udp2']},
|
|
53
|
+
{username: 'webexturnreachuser', credential: 'webexturnreachpwd', urls: ['turn:tcp1.webex.com?transport=tcp']},
|
|
54
|
+
{username: 'webexturnreachuser', credential: 'webexturnreachpwd', urls: ['turn:tcp2.webex.com:5004?transport=tcp']}
|
|
55
|
+
],
|
|
56
|
+
iceCandidatePoolSize: 0,
|
|
57
|
+
iceTransportPolicy: 'all',
|
|
58
|
+
});
|
|
59
|
+
});
|
|
60
|
+
|
|
61
|
+
it('should create a peer connection with the right config even if lists of urls are empty', () => {
|
|
62
|
+
(global.RTCPeerConnection as any).resetHistory();
|
|
63
|
+
|
|
64
|
+
clusterReachability = new ClusterReachability('testName', {
|
|
65
|
+
isVideoMesh: false,
|
|
66
|
+
udp: [],
|
|
67
|
+
tcp: [],
|
|
68
|
+
xtls: [],
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
assert.calledOnceWithExactly(global.RTCPeerConnection, {
|
|
72
|
+
iceServers: [],
|
|
73
|
+
iceCandidatePoolSize: 0,
|
|
74
|
+
iceTransportPolicy: 'all',
|
|
75
|
+
});
|
|
76
|
+
});
|
|
77
|
+
|
|
78
|
+
it('returns correct results before start() is called', () => {
|
|
79
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
80
|
+
udp: {result: 'untested'},
|
|
81
|
+
tcp: {result: 'untested'},
|
|
82
|
+
xtls: {result: 'untested'}
|
|
83
|
+
});
|
|
84
|
+
});
|
|
85
|
+
|
|
86
|
+
describe('#start', () => {
|
|
87
|
+
let clock;
|
|
88
|
+
|
|
89
|
+
beforeEach(() => {
|
|
90
|
+
clock = sinon.useFakeTimers();
|
|
91
|
+
});
|
|
92
|
+
|
|
93
|
+
afterEach(() => {
|
|
94
|
+
clock.restore();
|
|
95
|
+
})
|
|
96
|
+
|
|
97
|
+
it('should initiate the ICE gathering process', async () => {
|
|
98
|
+
const promise = clusterReachability.start();
|
|
99
|
+
|
|
100
|
+
await testUtils.flushPromises();
|
|
101
|
+
|
|
102
|
+
// check that the right listeners are setup
|
|
103
|
+
assert.isFunction(fakePeerConnection.onicecandidate);
|
|
104
|
+
assert.isFunction(fakePeerConnection.onicegatheringstatechange);
|
|
105
|
+
|
|
106
|
+
// check that the right webrtc APIs are called
|
|
107
|
+
assert.calledOnceWithExactly(fakePeerConnection.createOffer, {offerToReceiveAudio: true});
|
|
108
|
+
assert.calledOnce(fakePeerConnection.setLocalDescription);
|
|
109
|
+
|
|
110
|
+
await clock.tickAsync(3000);// move the clock so that reachability times out
|
|
111
|
+
await promise;
|
|
112
|
+
});
|
|
113
|
+
|
|
114
|
+
it('resolves and has correct result as soon as it finds that both udp and tcp is reachable', async () => {
|
|
115
|
+
const promise = clusterReachability.start();
|
|
116
|
+
|
|
117
|
+
await clock.tickAsync(100);
|
|
118
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp'}});
|
|
119
|
+
|
|
120
|
+
await clock.tickAsync(100);
|
|
121
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'relay', address: 'someTurnRelayIp'}});
|
|
122
|
+
|
|
123
|
+
await promise;
|
|
124
|
+
|
|
125
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
126
|
+
udp: {result: 'reachable', latencyInMilliseconds: 100, clientMediaIPs: ['somePublicIp']},
|
|
127
|
+
tcp: {result: 'reachable', latencyInMilliseconds: 200},
|
|
128
|
+
xtls: {result: 'untested'}
|
|
129
|
+
});
|
|
130
|
+
});
|
|
131
|
+
|
|
132
|
+
it('times out correctly', async () => {
|
|
133
|
+
const promise = clusterReachability.start();
|
|
134
|
+
|
|
135
|
+
// progress time without any candidates
|
|
136
|
+
await clock.tickAsync(3000);
|
|
137
|
+
await promise;
|
|
138
|
+
|
|
139
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
140
|
+
udp: {result: 'unreachable'},
|
|
141
|
+
tcp: {result: 'unreachable'},
|
|
142
|
+
xtls: {result: 'untested'}
|
|
143
|
+
});
|
|
144
|
+
});
|
|
145
|
+
|
|
146
|
+
it('times out correctly for video mesh nodes', async () => {
|
|
147
|
+
clusterReachability = new ClusterReachability('testName', {
|
|
148
|
+
isVideoMesh: true,
|
|
149
|
+
udp: ['stun:udp1', 'stun:udp2'],
|
|
150
|
+
tcp: ['stun:tcp1.webex.com', 'stun:tcp2.webex.com:5004'],
|
|
151
|
+
xtls: ['xtls1', 'xtls2'],
|
|
152
|
+
});
|
|
153
|
+
|
|
154
|
+
const promise = clusterReachability.start();
|
|
155
|
+
|
|
156
|
+
// video mesh nodes have shorter timeout of just 1s
|
|
157
|
+
await clock.tickAsync(1000);
|
|
158
|
+
await promise;
|
|
159
|
+
|
|
160
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
161
|
+
udp: {result: 'unreachable'},
|
|
162
|
+
tcp: {result: 'unreachable'},
|
|
163
|
+
xtls: {result: 'untested'}
|
|
164
|
+
});
|
|
165
|
+
});
|
|
166
|
+
|
|
167
|
+
it('resolves when ICE gathering is completed', async () => {
|
|
168
|
+
const promise = clusterReachability.start();
|
|
169
|
+
|
|
170
|
+
await testUtils.flushPromises();
|
|
171
|
+
|
|
172
|
+
fakePeerConnection.iceConnectionState = 'complete';
|
|
173
|
+
fakePeerConnection.onicegatheringstatechange();
|
|
174
|
+
await promise;
|
|
175
|
+
|
|
176
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
177
|
+
udp: {result: 'unreachable'},
|
|
178
|
+
tcp: {result: 'unreachable'},
|
|
179
|
+
xtls: {result: 'untested'}
|
|
180
|
+
});
|
|
181
|
+
});
|
|
182
|
+
|
|
183
|
+
it('resolves with the right result when ICE gathering is completed', async () => {
|
|
184
|
+
const promise = clusterReachability.start();
|
|
185
|
+
|
|
186
|
+
// send 1 candidate
|
|
187
|
+
await clock.tickAsync(30);
|
|
188
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp1'}});
|
|
189
|
+
|
|
190
|
+
fakePeerConnection.iceConnectionState = 'complete';
|
|
191
|
+
fakePeerConnection.onicegatheringstatechange();
|
|
192
|
+
await promise;
|
|
193
|
+
|
|
194
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
195
|
+
udp: {result: 'reachable', latencyInMilliseconds: 30, clientMediaIPs: ['somePublicIp1']},
|
|
196
|
+
tcp: {result: 'unreachable'},
|
|
197
|
+
xtls: {result: 'untested'}
|
|
198
|
+
});
|
|
199
|
+
});
|
|
200
|
+
|
|
201
|
+
it('should store latency only for the first srflx candidate, but IPs from all of them', async () => {
|
|
202
|
+
const promise = clusterReachability.start();
|
|
203
|
+
|
|
204
|
+
await clock.tickAsync(10);
|
|
205
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp1'}});
|
|
206
|
+
|
|
207
|
+
// generate more candidates
|
|
208
|
+
await clock.tickAsync(10);
|
|
209
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp2'}});
|
|
210
|
+
|
|
211
|
+
await clock.tickAsync(10);
|
|
212
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp3'}});
|
|
213
|
+
|
|
214
|
+
await clock.tickAsync(3000);// move the clock so that reachability times out
|
|
215
|
+
|
|
216
|
+
await promise;
|
|
217
|
+
|
|
218
|
+
// latency should be from only the first candidates, but the clientMediaIps should be from all UDP candidates (not TCP)
|
|
219
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
220
|
+
udp: {result: 'reachable', latencyInMilliseconds: 10, clientMediaIPs: ['somePublicIp1', 'somePublicIp2', 'somePublicIp3']},
|
|
221
|
+
tcp: {result: 'unreachable'},
|
|
222
|
+
xtls: {result: 'untested'}
|
|
223
|
+
});
|
|
224
|
+
});
|
|
225
|
+
|
|
226
|
+
it('should store latency only for the first relay candidate', async () => {
|
|
227
|
+
const promise = clusterReachability.start();
|
|
228
|
+
|
|
229
|
+
await clock.tickAsync(10);
|
|
230
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'relay', address: 'someTurnRelayIp1'}});
|
|
231
|
+
|
|
232
|
+
// generate more candidates
|
|
233
|
+
await clock.tickAsync(10);
|
|
234
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'relay', address: 'someTurnRelayIp2'}});
|
|
235
|
+
|
|
236
|
+
await clock.tickAsync(10);
|
|
237
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'relay', address: 'someTurnRelayIp3'}});
|
|
238
|
+
|
|
239
|
+
await clock.tickAsync(3000);// move the clock so that reachability times out
|
|
240
|
+
|
|
241
|
+
await promise;
|
|
242
|
+
|
|
243
|
+
// latency should be from only the first candidates, but the clientMediaIps should be from only from UDP candidates
|
|
244
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
245
|
+
udp: {result: 'unreachable'},
|
|
246
|
+
tcp: {result: 'reachable', latencyInMilliseconds: 10},
|
|
247
|
+
xtls: {result: 'untested'}
|
|
248
|
+
});
|
|
249
|
+
});
|
|
250
|
+
|
|
251
|
+
it('ignores duplicate clientMediaIps', async () => {
|
|
252
|
+
const promise = clusterReachability.start();
|
|
253
|
+
|
|
254
|
+
// generate candidates with duplicate addresses
|
|
255
|
+
await clock.tickAsync(10);
|
|
256
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp1'}});
|
|
257
|
+
|
|
258
|
+
await clock.tickAsync(10);
|
|
259
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp1'}});
|
|
260
|
+
|
|
261
|
+
await clock.tickAsync(10);
|
|
262
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp2'}});
|
|
263
|
+
|
|
264
|
+
await clock.tickAsync(10);
|
|
265
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'srflx', address: 'somePublicIp2'}});
|
|
266
|
+
|
|
267
|
+
// send also a relay candidate so that the reachability check finishes
|
|
268
|
+
fakePeerConnection.onicecandidate({candidate: {type: 'relay', address: 'someTurnRelayIp'}});
|
|
269
|
+
|
|
270
|
+
await promise;
|
|
271
|
+
|
|
272
|
+
assert.deepEqual(clusterReachability.getResult(), {
|
|
273
|
+
udp: {result: 'reachable', latencyInMilliseconds: 10, clientMediaIPs: ['somePublicIp1', 'somePublicIp2']},
|
|
274
|
+
tcp: {result: 'reachable', latencyInMilliseconds: 40},
|
|
275
|
+
xtls: {result: 'untested'}
|
|
276
|
+
});
|
|
277
|
+
});
|
|
278
|
+
});
|
|
279
|
+
});
|