@opentok/client 2.35.0-alpha.49 → 2.35.0-alpha.50

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.
@@ -1,11 +1,11 @@
1
1
  /**
2
- * @license OpenTok.js 2.35.0 1130ccbf0
2
+ * @license OpenTok.js 2.35.0 af69a9c37
3
3
  *
4
4
  * Copyright (c) 2010-2026 TokBox, Inc.
5
5
  * Subject to the applicable Software Development Kit (SDK) License Agreement:
6
6
  * https://www.vonage.com/legal/communications-apis/terms-of-use/
7
7
  *
8
- * Date: Tue, 09 Jun 2026 09:26:44 GMT
8
+ * Date: Tue, 09 Jun 2026 11:10:58 GMT
9
9
  */
10
10
 
11
11
  (function webpackUniversalModuleDefinition(root, factory) {
@@ -2398,20 +2398,30 @@ const PENDING = Symbol('pendingCalls');
2398
2398
  /**
2399
2399
  * Add (or overwrite) a pending method call.
2400
2400
  * Keeps only the latest call per method.
2401
+ * Accepts a cancel function called when the method is overridden.
2401
2402
  *
2402
2403
  * @param {Object} instance
2403
2404
  * @param {Function} method
2404
2405
  * @param {Array} args
2406
+ * @param {Function} cancel
2405
2407
  */
2406
- function addToPending(instance, method, args) {
2408
+ function addToPending(instance, method, args, cancel) {
2409
+ if (cancel === void 0) {
2410
+ cancel = () => {};
2411
+ }
2407
2412
  if (!instance[PENDING]) {
2408
2413
  // eslint-disable-next-line no-param-reassign
2409
2414
  instance[PENDING] = new Map();
2410
2415
  }
2411
2416
  const queue = instance[PENDING];
2417
+ const previous = queue.get(method);
2418
+ if (previous && typeof previous.cancel === 'function') {
2419
+ previous.cancel();
2420
+ }
2412
2421
  queue.set(method, {
2413
2422
  fn: method.bind(instance),
2414
- args
2423
+ args,
2424
+ cancel
2415
2425
  });
2416
2426
  }
2417
2427
 
@@ -25597,7 +25607,7 @@ function SubscriberFactory(_ref2) {
25597
25607
  logAnalyticsEvent('SetStyle', 'Subscriber', payload, null, 0.1);
25598
25608
  });
25599
25609
  function setAudioOnly(audioOnly) {
25600
- getAllPeerConnections().forEach( /*#__PURE__*/function () {
25610
+ const peerConnectionUpdates = getAllPeerConnections().map( /*#__PURE__*/function () {
25601
25611
  var _ref21 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee10(peerConnection) {
25602
25612
  return _regenerator.default.wrap(function _callee10$(_context10) {
25603
25613
  while (1) switch (_context10.prev = _context10.next) {
@@ -25605,7 +25615,7 @@ function SubscriberFactory(_ref2) {
25605
25615
  _context10.next = 2;
25606
25616
  return peerConnection;
25607
25617
  case 2:
25608
- _context10.sent.subscribeToVideo(!audioOnly);
25618
+ return _context10.abrupt("return", _context10.sent.subscribeToVideo(!audioOnly));
25609
25619
  case 3:
25610
25620
  case "end":
25611
25621
  return _context10.stop();
@@ -25626,6 +25636,7 @@ function SubscriberFactory(_ref2) {
25626
25636
  if (_audioLevelMeter) {
25627
25637
  _audioLevelMeter.audioOnly(audioFallback);
25628
25638
  }
25639
+ return peerConnectionUpdates;
25629
25640
  }
25630
25641
 
25631
25642
  // logs an analytics event for getStats on the first call
@@ -26338,6 +26349,7 @@ function SubscriberFactory(_ref2) {
26338
26349
  };
26339
26350
  function applyAudioVolume(audioVolume) {
26340
26351
  const video = _widgetView && _widgetView.video();
26352
+ const promises = [];
26341
26353
  if (video) {
26342
26354
  try {
26343
26355
  video.setAudioVolume(audioVolume);
@@ -26346,28 +26358,34 @@ function SubscriberFactory(_ref2) {
26346
26358
  if (_audioVolume === 0) {
26347
26359
  logging.info('Using subscribeToAudio to mute Audio because setAudioVolume(0) failed');
26348
26360
  // If we can't set the audioVolume to 0 then at least mute by setting subscribeToAudio(false)
26349
- _subscriber.subscribeToAudio(false, 'internal');
26361
+ promises.push(_subscriber.subscribeToAudio.promise(false, 'internal'));
26350
26362
  }
26351
26363
  }
26352
26364
  }
26353
26365
  if (_chrome) {
26354
26366
  _chrome.muteButton.muted(audioVolume === 0);
26355
26367
  }
26368
+ return Promise.all(promises);
26356
26369
  }
26357
- function setAudioVolume(requestedVolume) {
26370
+ function setAudioVolume(requestedVolume, callback) {
26371
+ if (callback === void 0) {
26372
+ callback = () => {};
26373
+ }
26358
26374
  const volume = normalizeAudioVolume(requestedVolume);
26375
+ const rangeErrorMessage = 'value should be an integer between 0 and 100';
26359
26376
  if (isNaN(volume)) {
26360
- logging.error('OT.Subscriber.setAudioVolume: value should be an integer between 0 and 100');
26377
+ logging.error(`OT.Subscriber.setAudioVolume: ${rangeErrorMessage}`);
26378
+ callback(new Error(rangeErrorMessage));
26361
26379
  return {
26362
26380
  volume,
26363
- error: 'value should be an integer between 0 and 100'
26381
+ error: rangeErrorMessage
26364
26382
  };
26365
26383
  }
26366
26384
  if (volume !== requestedVolume) {
26367
- logging.warn('OT.Subscriber.setAudioVolume: value should be an integer between 0 and 100');
26385
+ logging.warn(`OT.Subscriber.setAudioVolume: ${rangeErrorMessage}`);
26368
26386
  }
26369
26387
  if (volume === _audioVolume) {
26370
- applyAudioVolume(_audioVolume);
26388
+ applyAudioVolume(_audioVolume).then(() => callback()).catch(err => callback(err));
26371
26389
  return {
26372
26390
  volume,
26373
26391
  message: 'Requested volume is same as already set audioVolume'
@@ -26377,15 +26395,16 @@ function SubscriberFactory(_ref2) {
26377
26395
  _latestPositiveVolume = _audioVolume;
26378
26396
  }
26379
26397
  _audioVolume = volume;
26380
- applyAudioVolume(_audioVolume);
26398
+ const promises = [applyAudioVolume(_audioVolume)];
26381
26399
  if (_audioVolume > 0 && !_isSubscribingToAudio) {
26382
26400
  // in Firefox (and others) we don't stop subscribing to audio when muted, however if we are 'unmuting' and in
26383
26401
  // the subscribeToAudio: false state we should subscribe to audio again
26384
26402
 
26385
26403
  // subscribeToAudio is going to call us with _latestPositiveVolume so we'll update it here
26386
26404
  _latestPositiveVolume = _audioVolume;
26387
- _subscriber.subscribeToAudio(true, 'internal');
26405
+ promises.push(_subscriber.subscribeToAudio.promise(true, 'internal'));
26388
26406
  }
26407
+ Promise.all(promises).then(() => callback()).catch(err => callback(err));
26389
26408
  return {
26390
26409
  volume
26391
26410
  };
@@ -26408,6 +26427,13 @@ function SubscriberFactory(_ref2) {
26408
26427
  });
26409
26428
  }
26410
26429
  });
26430
+ const setAudioVolumeWithCallback = function setAudioVolumeWithCallback(requestedVolume, callback) {
26431
+ if (callback === void 0) {
26432
+ callback = () => {};
26433
+ }
26434
+ const result = setAudioVolume(requestedVolume, callback);
26435
+ logSetAudioVolumeLimitedRunner.run(result);
26436
+ };
26411
26437
 
26412
26438
  /**
26413
26439
  * Sets the audio volume, between 0 and 100, of the Subscriber.
@@ -26428,13 +26454,41 @@ function SubscriberFactory(_ref2) {
26428
26454
  * @method #setAudioVolume
26429
26455
  * @memberOf Subscriber
26430
26456
  */
26431
-
26432
26457
  this.setAudioVolume = requestedVolume => {
26433
- const result = setAudioVolume(requestedVolume);
26434
- logSetAudioVolumeLimitedRunner.run(result);
26458
+ setAudioVolumeWithCallback(requestedVolume);
26435
26459
  return this;
26436
26460
  };
26437
26461
 
26462
+ /**
26463
+ * Promise-based variant of {@link Subscriber#setAudioVolume}.
26464
+ *
26465
+ * Sets the audio volume of the Subscriber and returns a Promise that settles once all
26466
+ * underlying audio operations have completed (including any audio-processor connector
26467
+ * update triggered by unmuting).
26468
+ *
26469
+ * @param {Number} value - The audio volume, between 0 and 100.
26470
+ * @returns {Promise<void>} Resolves when the volume has been successfully applied;
26471
+ * rejects with an <code>Error</code> if the value is out of range or if any
26472
+ * underlying audio operation fails.
26473
+ *
26474
+ * @example
26475
+ * subscriber.setAudioVolume.promise(50)
26476
+ * .then(() => console.log('volume set'))
26477
+ * .catch(err => console.error('failed to set volume', err));
26478
+ *
26479
+ * @method #setAudioVolume.promise
26480
+ * @memberOf Subscriber
26481
+ */
26482
+ this.setAudioVolume.promise = requestedVolume => new Promise((resolve, reject) => {
26483
+ setAudioVolumeWithCallback(requestedVolume, err => {
26484
+ if (err) {
26485
+ reject(err);
26486
+ } else {
26487
+ resolve();
26488
+ }
26489
+ });
26490
+ });
26491
+
26438
26492
  /**
26439
26493
  * Returns the audio volume, between 0 and 100, of the Subscriber.
26440
26494
  *
@@ -26457,40 +26511,17 @@ function SubscriberFactory(_ref2) {
26457
26511
  }
26458
26512
  return _audioVolume;
26459
26513
  };
26460
-
26461
- /**
26462
- * Toggles audio on and off. Starts subscribing to audio (if it is available and currently
26463
- * not being subscribed to) when the <code>value</code> is <code>true</code>; stops
26464
- * subscribing to audio (if it is currently being subscribed to) when the <code>value</code>
26465
- * is <code>false</code>.
26466
- * <p>
26467
- * <i>Note:</i> This method only affects the local playback of audio. It has no impact on the
26468
- * audio for other connections subscribing to the same stream. If the Publisher is not
26469
- * publishing audio, enabling the Subscriber audio will have no practical effect.
26470
- * </p>
26471
- *
26472
- * @param {Boolean} value Whether to start subscribing to audio (<code>true</code>) or not
26473
- * (<code>false</code>).
26474
- *
26475
- * @return {Subscriber} The Subscriber object. This lets you chain method calls, as in the
26476
- * following:
26477
- *
26478
- * <pre>mySubscriber.subscribeToAudio(true).subscribeToVideo(false);</pre>
26479
- *
26480
- * @see <a href="#subscribeToVideo">subscribeToVideo()</a>
26481
- * @see <a href="Session.html#subscribe">Session.subscribe()</a>
26482
- * @see <a href="StreamPropertyChangedEvent.html">StreamPropertyChangedEvent</a>
26483
- *
26484
- * @method #subscribeToAudio
26485
- * @memberOf Subscriber
26486
- */
26487
- this.subscribeToAudio = (pValue, reason) => {
26514
+ const subscribeToAudioWithCallback = function subscribeToAudioWithCallback(pValue, reason, callback) {
26515
+ if (callback === void 0) {
26516
+ callback = () => {};
26517
+ }
26488
26518
  const value = (0, _castToBoolean.default)(pValue, true);
26519
+ const promises = [];
26489
26520
  if (!reason && !_state.isSubscribing()) {
26490
- (0, _pendingCalls.addToPending)(this, this.subscribeToAudio, [value]);
26491
- return this;
26521
+ (0, _pendingCalls.addToPending)(_this, subscribeToAudioWithCallback, [value, reason, callback], () => callback(new Error('pending subscribeToAudio overridden')));
26522
+ return;
26492
26523
  }
26493
- getAllPeerConnections().forEach( /*#__PURE__*/function () {
26524
+ const subs = getAllPeerConnections().map( /*#__PURE__*/function () {
26494
26525
  var _ref33 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee18(peerConnection) {
26495
26526
  return _regenerator.default.wrap(function _callee18$(_context18) {
26496
26527
  while (1) switch (_context18.prev = _context18.next) {
@@ -26498,7 +26529,7 @@ function SubscriberFactory(_ref2) {
26498
26529
  _context18.next = 2;
26499
26530
  return peerConnection;
26500
26531
  case 2:
26501
- _context18.sent.subscribeToAudio(value);
26532
+ return _context18.abrupt("return", _context18.sent.subscribeToAudio(value));
26502
26533
  case 3:
26503
26534
  case "end":
26504
26535
  return _context18.stop();
@@ -26509,6 +26540,7 @@ function SubscriberFactory(_ref2) {
26509
26540
  return _ref33.apply(this, arguments);
26510
26541
  };
26511
26542
  }());
26543
+ promises.push(...subs);
26512
26544
  if (_stream && getAllPeerConnections().length !== 0) {
26513
26545
  setChannelActiveStateForSubscriber({
26514
26546
  channelType: 'audio',
@@ -26526,7 +26558,7 @@ function SubscriberFactory(_ref2) {
26526
26558
  }
26527
26559
  if (_audioConnector.audioMediaProcessorConnector) {
26528
26560
  if (_isSubscribingToAudio) {
26529
- _setAudioMediaProcessorConnector();
26561
+ promises.push(_setAudioMediaProcessorConnector());
26530
26562
  } else {
26531
26563
  try {
26532
26564
  _audioConnector.resetAudioStreamAndTrack();
@@ -26534,17 +26566,90 @@ function SubscriberFactory(_ref2) {
26534
26566
  logAnalyticsEvent('subscribeToAudio', 'Failure', {
26535
26567
  message: `Error resetting track: ${error.message}`
26536
26568
  });
26537
- return this;
26569
+ callback(error);
26570
+ return;
26538
26571
  }
26539
26572
  }
26540
26573
  }
26541
- logAnalyticsEvent('subscribeToAudio', 'Success', {
26542
- subscribeToAudio: value
26543
- }, {
26544
- attemptDuration: Date.now() - attemptStart
26574
+ Promise.all(promises).then(() => {
26575
+ logAnalyticsEvent('subscribeToAudio', 'Success', {
26576
+ subscribeToAudio: value
26577
+ }, {
26578
+ attemptDuration: Date.now() - attemptStart
26579
+ });
26580
+ callback();
26581
+ }).catch(err => {
26582
+ logAnalyticsEvent('subscribeToAudio', 'Failure', {
26583
+ message: (err == null ? void 0 : err.message) || String(err)
26584
+ }, {
26585
+ attemptDuration: Date.now() - attemptStart
26586
+ });
26587
+ callback(err);
26545
26588
  });
26589
+ };
26590
+
26591
+ /**
26592
+ * Toggles audio on and off. Starts subscribing to audio (if it is available and currently
26593
+ * not being subscribed to) when the <code>value</code> is <code>true</code>; stops
26594
+ * subscribing to audio (if it is currently being subscribed to) when the <code>value</code>
26595
+ * is <code>false</code>.
26596
+ * <p>
26597
+ * <i>Note:</i> This method only affects the local playback of audio. It has no impact on the
26598
+ * audio for other connections subscribing to the same stream. If the Publisher is not
26599
+ * publishing audio, enabling the Subscriber audio will have no practical effect.
26600
+ * </p>
26601
+ *
26602
+ * @param {Boolean} value Whether to start subscribing to audio (<code>true</code>) or not
26603
+ * (<code>false</code>).
26604
+ *
26605
+ * @return {Subscriber} The Subscriber object. This lets you chain method calls, as in the
26606
+ * following:
26607
+ *
26608
+ * <pre>mySubscriber.subscribeToAudio(true).subscribeToVideo(false);</pre>
26609
+ *
26610
+ * @see <a href="#subscribeToVideo">subscribeToVideo()</a>
26611
+ * @see <a href="Session.html#subscribe">Session.subscribe()</a>
26612
+ * @see <a href="StreamPropertyChangedEvent.html">StreamPropertyChangedEvent</a>
26613
+ *
26614
+ * @method #subscribeToAudio
26615
+ * @memberOf Subscriber
26616
+ */
26617
+ this.subscribeToAudio = (pValue, reason) => {
26618
+ subscribeToAudioWithCallback(pValue, reason);
26546
26619
  return this;
26547
26620
  };
26621
+
26622
+ /**
26623
+ * Promise-based variant of {@link Subscriber#subscribeToAudio}.
26624
+ *
26625
+ * Toggles audio on or off and returns a Promise that settles once all underlying
26626
+ * peer-connection and audio-processor operations have completed.
26627
+ *
26628
+ * @param {Boolean} value - <code>true</code> to start subscribing to audio,
26629
+ * <code>false</code> to stop.
26630
+ * @param {String} [reason] - Internal reason string (e.g. <code>'internal'</code>).
26631
+ * Pass <code>undefined</code> for a user-initiated call.
26632
+ * @returns {Promise<void>} Resolves when audio has been successfully toggled;
26633
+ * rejects with an <code>Error</code> if any operation fails.
26634
+ *
26635
+ * @example
26636
+ * // Mute audio and wait until the operation is fully complete
26637
+ * subscriber.subscribeToAudio.promise(false)
26638
+ * .then(() => console.log('audio muted'))
26639
+ * .catch(err => console.error('failed to mute audio', err));
26640
+ *
26641
+ * @method #subscribeToAudio.promise
26642
+ * @memberOf Subscriber
26643
+ */
26644
+ this.subscribeToAudio.promise = (pValue, reason) => new Promise((resolve, reject) => {
26645
+ subscribeToAudioWithCallback(pValue, reason, err => {
26646
+ if (err) {
26647
+ reject(err);
26648
+ } else {
26649
+ resolve();
26650
+ }
26651
+ });
26652
+ });
26548
26653
  const reasonMap = {
26549
26654
  auto: 'quality',
26550
26655
  publishVideo: 'publishVideo',
@@ -26563,6 +26668,106 @@ function SubscriberFactory(_ref2) {
26563
26668
  document.removeEventListener('visibilitychange', onVisibilityChange);
26564
26669
  });
26565
26670
  }
26671
+ const subscribeToVideoWithCallback = /*#__PURE__*/function () {
26672
+ var _ref34 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee19(pValue, reason, callback) {
26673
+ var enableVideo, attemptStart, promises, message;
26674
+ return _regenerator.default.wrap(function _callee19$(_context19) {
26675
+ while (1) switch (_context19.prev = _context19.next) {
26676
+ case 0:
26677
+ if (callback === void 0) {
26678
+ callback = () => {};
26679
+ }
26680
+ enableVideo = (0, _castToBoolean.default)(pValue, true);
26681
+ if (!(!reason && !_state.isSubscribing())) {
26682
+ _context19.next = 5;
26683
+ break;
26684
+ }
26685
+ (0, _pendingCalls.addToPending)(_this, subscribeToVideoWithCallback, [enableVideo, reason, callback], () => callback(new Error('pending subscribeToVideo overridden')));
26686
+ return _context19.abrupt("return");
26687
+ case 5:
26688
+ // We restore to undefined to keep backward compatibility
26689
+ // eslint-disable-next-line no-param-reassign
26690
+ if (reason === 'internal') {
26691
+ reason = undefined;
26692
+ }
26693
+ if (!reason) {
26694
+ _isVideoManuallyMuted = !enableVideo;
26695
+ } else if (reason === 'auto') {
26696
+ updateCongestionLevel(enableVideo ? null : 2);
26697
+ }
26698
+ logAnalyticsEvent('subscribeToVideo', 'Attempt', {
26699
+ subscribeToVideo: enableVideo,
26700
+ reason
26701
+ });
26702
+ attemptStart = Date.now();
26703
+ promises = setAudioOnly(!enableVideo || !_stream.hasVideo || !_webRTCStream);
26704
+ if (!(_stream.hasVideo && !_streamHasTracks('video'))) {
26705
+ _context19.next = 17;
26706
+ break;
26707
+ }
26708
+ if (enableVideo) {
26709
+ logging.info('Subscriber is audio-only due to incompatibility, can\'t subscribeToVideo.');
26710
+ }
26711
+ _properties.subscribeToVideo = false;
26712
+ message = 'No video tracks available';
26713
+ logAnalyticsEvent('subscribeToVideo', 'Failure', {
26714
+ message
26715
+ });
26716
+ callback(new Error(message));
26717
+ return _context19.abrupt("return");
26718
+ case 17:
26719
+ if (_chrome && _chrome.videoDisabledIndicator) {
26720
+ // If this is an auto disableVideo then we want to show the indicator, otherwise hide it again
26721
+ _chrome.videoDisabledIndicator.disableVideo(!enableVideo && reason === 'auto');
26722
+ }
26723
+ if (getAllPeerConnections().length > 0 && _session && _stream) {
26724
+ if ((enableVideo !== _properties.subscribeToVideo || reason !== _lastSubscribeToVideoReason) && !(_isVideoManuallyMuted && !!reason)) {
26725
+ setChannelActiveStateForSubscriber({
26726
+ channelType: 'video',
26727
+ activeState: enableVideo,
26728
+ activeReason: reason
26729
+ });
26730
+ }
26731
+ }
26732
+ _properties.subscribeToVideo = enableVideo;
26733
+ _lastSubscribeToVideoReason = reason;
26734
+ _videoEnabled = enableVideo;
26735
+ if (_videoMediaProcessorConnector) {
26736
+ if (_videoEnabled) {
26737
+ promises.push(_setVideoMediaProcessorConnector());
26738
+ } else {
26739
+ _resetVideoStream();
26740
+ }
26741
+ }
26742
+ if (reason !== 'loading') {
26743
+ _this.dispatchEvent(new Events.VideoEnabledChangedEvent(enableVideo ? 'videoEnabled' : 'videoDisabled', {
26744
+ reason: reasonMap[reason] || 'subscribeToVideo'
26745
+ }));
26746
+ }
26747
+ Promise.all(promises).then(() => {
26748
+ logAnalyticsEvent('subscribeToVideo', 'Success', {
26749
+ subscribeToVideo: enableVideo,
26750
+ reason
26751
+ }, {
26752
+ attemptDuration: Date.now() - attemptStart
26753
+ });
26754
+ callback();
26755
+ }).catch(err => {
26756
+ logAnalyticsEvent('subscribeToVideo', 'Failure', {
26757
+ message: (err == null ? void 0 : err.message) || String(err)
26758
+ });
26759
+ callback(err);
26760
+ });
26761
+ case 25:
26762
+ case "end":
26763
+ return _context19.stop();
26764
+ }
26765
+ }, _callee19);
26766
+ }));
26767
+ return function subscribeToVideoWithCallback(_x19, _x20, _x21) {
26768
+ return _ref34.apply(this, arguments);
26769
+ };
26770
+ }();
26566
26771
 
26567
26772
  /**
26568
26773
  * Toggles video on and off. Starts subscribing to video (if it is available and
@@ -26591,73 +26796,42 @@ function SubscriberFactory(_ref2) {
26591
26796
  * @memberOf Subscriber
26592
26797
  */
26593
26798
  this.subscribeToVideo = (pValue, reason) => {
26594
- const enableVideo = (0, _castToBoolean.default)(pValue, true);
26595
- if (!reason && !_state.isSubscribing()) {
26596
- (0, _pendingCalls.addToPending)(this, this.subscribeToVideo, [enableVideo]);
26597
- return this;
26598
- }
26599
- if (reason === 'internal') {
26600
- // We restore to undefined to keep backward compatibility
26601
- // eslint-disable-next-line no-param-reassign
26602
- reason = undefined;
26603
- }
26604
- if (!reason) {
26605
- _isVideoManuallyMuted = !enableVideo;
26606
- } else if (reason === 'auto') {
26607
- updateCongestionLevel(enableVideo ? null : 2);
26608
- }
26609
- logAnalyticsEvent('subscribeToVideo', 'Attempt', {
26610
- subscribeToVideo: enableVideo,
26611
- reason
26612
- });
26613
- const attemptStart = Date.now();
26614
- setAudioOnly(!enableVideo || !_stream.hasVideo || !_webRTCStream);
26615
- if (_stream.hasVideo && !_streamHasTracks('video')) {
26616
- if (enableVideo) {
26617
- logging.info('Subscriber is audio-only due to incompatibility, can\'t subscribeToVideo.');
26618
- }
26619
- _properties.subscribeToVideo = false;
26620
- logAnalyticsEvent('subscribeToVideo', 'Failure', {
26621
- message: 'No video tracks available'
26622
- });
26623
- return this;
26624
- }
26625
- if (_chrome && _chrome.videoDisabledIndicator) {
26626
- // If this is an auto disableVideo then we want to show the indicator, otherwise hide it again
26627
- _chrome.videoDisabledIndicator.disableVideo(!enableVideo && reason === 'auto');
26628
- }
26629
- if (getAllPeerConnections().length > 0 && _session && _stream) {
26630
- if ((enableVideo !== _properties.subscribeToVideo || reason !== _lastSubscribeToVideoReason) && !(_isVideoManuallyMuted && !!reason)) {
26631
- setChannelActiveStateForSubscriber({
26632
- channelType: 'video',
26633
- activeState: enableVideo,
26634
- activeReason: reason
26635
- });
26636
- }
26637
- }
26638
- _properties.subscribeToVideo = enableVideo;
26639
- _lastSubscribeToVideoReason = reason;
26640
- _videoEnabled = enableVideo;
26641
- if (_videoMediaProcessorConnector) {
26642
- if (_videoEnabled) {
26643
- _setVideoMediaProcessorConnector();
26799
+ subscribeToVideoWithCallback(pValue, reason);
26800
+ return this;
26801
+ };
26802
+
26803
+ /**
26804
+ * Promise-based variant of {@link Subscriber#subscribeToVideo}.
26805
+ *
26806
+ * Toggles video on or off and returns a Promise that settles once all underlying
26807
+ * operations have completed (including any video media-processor connector update).
26808
+ *
26809
+ * @param {Boolean} value - <code>true</code> to start subscribing to video,
26810
+ * <code>false</code> to stop.
26811
+ * @param {String} [reason] - Internal reason string (e.g. <code>'auto'</code>).
26812
+ * Pass <code>undefined</code> for a user-initiated call.
26813
+ * @returns {Promise<void>} Resolves when video has been successfully toggled;
26814
+ * rejects with an <code>Error</code> if any operation fails (e.g. no video tracks
26815
+ * available, or the media-processor connector throws).
26816
+ *
26817
+ * @example
26818
+ * // Disable video and wait until the operation is fully complete
26819
+ * subscriber.subscribeToVideo.promise(false)
26820
+ * .then(() => console.log('video disabled'))
26821
+ * .catch(err => console.error('failed to disable video', err));
26822
+ *
26823
+ * @method #subscribeToVideo.promise
26824
+ * @memberOf Subscriber
26825
+ */
26826
+ this.subscribeToVideo.promise = (pValue, reason) => new Promise((resolve, reject) => {
26827
+ subscribeToVideoWithCallback(pValue, reason, err => {
26828
+ if (err) {
26829
+ reject(err);
26644
26830
  } else {
26645
- _resetVideoStream();
26831
+ resolve();
26646
26832
  }
26647
- }
26648
- logAnalyticsEvent('subscribeToVideo', 'Success', {
26649
- subscribeToVideo: enableVideo,
26650
- reason
26651
- }, {
26652
- attemptDuration: Date.now() - attemptStart
26653
26833
  });
26654
- if (reason !== 'loading') {
26655
- this.dispatchEvent(new Events.VideoEnabledChangedEvent(enableVideo ? 'videoEnabled' : 'videoDisabled', {
26656
- reason: reasonMap[reason] || 'subscribeToVideo'
26657
- }));
26658
- }
26659
- return this;
26660
- };
26834
+ });
26661
26835
 
26662
26836
  /**
26663
26837
  * Sets the preferred resolution of the subscriber's video.
@@ -26951,12 +27125,12 @@ function SubscriberFactory(_ref2) {
26951
27125
  }
26952
27126
  };
26953
27127
  this._setupPeerConnection = /*#__PURE__*/function () {
26954
- var _ref35 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee19(_ref34) {
27128
+ var _ref36 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee20(_ref35) {
26955
27129
  var send, log, logQoS, sourceStreamId, peerId;
26956
- return _regenerator.default.wrap(function _callee19$(_context19) {
26957
- while (1) switch (_context19.prev = _context19.next) {
27130
+ return _regenerator.default.wrap(function _callee20$(_context20) {
27131
+ while (1) switch (_context20.prev = _context20.next) {
26958
27132
  case 0:
26959
- send = _ref34.send, log = _ref34.log, logQoS = _ref34.logQoS, sourceStreamId = _ref34.sourceStreamId, peerId = _ref34.peerId;
27133
+ send = _ref35.send, log = _ref35.log, logQoS = _ref35.logQoS, sourceStreamId = _ref35.sourceStreamId, peerId = _ref35.peerId;
26960
27134
  if (_properties.testNetwork) {
26961
27135
  setAudioVolume(0);
26962
27136
  }
@@ -27008,15 +27182,15 @@ function SubscriberFactory(_ref2) {
27008
27182
  });
27009
27183
  });
27010
27184
  });
27011
- return _context19.abrupt("return", peerConnectionsAsync[sourceStreamId]);
27185
+ return _context20.abrupt("return", peerConnectionsAsync[sourceStreamId]);
27012
27186
  case 7:
27013
27187
  case "end":
27014
- return _context19.stop();
27188
+ return _context20.stop();
27015
27189
  }
27016
- }, _callee19);
27190
+ }, _callee20);
27017
27191
  }));
27018
- return function (_x19) {
27019
- return _ref35.apply(this, arguments);
27192
+ return function (_x22) {
27193
+ return _ref36.apply(this, arguments);
27020
27194
  };
27021
27195
  }();
27022
27196
 
@@ -27073,103 +27247,103 @@ function SubscriberFactory(_ref2) {
27073
27247
  this.on('styleValueChanged', updateChromeForStyleChange, this);
27074
27248
  this._ = {
27075
27249
  getDataChannel(label, options, completion) {
27076
- return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee20() {
27077
- return _regenerator.default.wrap(function _callee20$(_context20) {
27078
- while (1) switch (_context20.prev = _context20.next) {
27250
+ return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee21() {
27251
+ return _regenerator.default.wrap(function _callee21$(_context21) {
27252
+ while (1) switch (_context21.prev = _context21.next) {
27079
27253
  case 0:
27080
27254
  if (getCurrentPeerConnection()) {
27081
- _context20.next = 3;
27255
+ _context21.next = 3;
27082
27256
  break;
27083
27257
  }
27084
27258
  completion(new OTHelpers.Error('Cannot create a DataChannel before there is a publisher connection.'));
27085
- return _context20.abrupt("return");
27259
+ return _context21.abrupt("return");
27086
27260
  case 3:
27087
- _context20.next = 5;
27261
+ _context21.next = 5;
27088
27262
  return getCurrentPeerConnection();
27089
27263
  case 5:
27090
- _context20.sent.getDataChannel(label, options, completion);
27264
+ _context21.sent.getDataChannel(label, options, completion);
27091
27265
  case 6:
27092
27266
  case "end":
27093
- return _context20.stop();
27267
+ return _context21.stop();
27094
27268
  }
27095
- }, _callee20);
27269
+ }, _callee21);
27096
27270
  }))();
27097
27271
  },
27098
27272
  iceRestart(reason, forcedRestart) {
27099
- return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee21() {
27273
+ return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee22() {
27100
27274
  var peerConnection;
27101
- return _regenerator.default.wrap(function _callee21$(_context21) {
27102
- while (1) switch (_context21.prev = _context21.next) {
27275
+ return _regenerator.default.wrap(function _callee22$(_context22) {
27276
+ while (1) switch (_context22.prev = _context22.next) {
27103
27277
  case 0:
27104
27278
  if (forcedRestart === void 0) {
27105
27279
  forcedRestart = false;
27106
27280
  }
27107
27281
  if (_session._.isSocketConnected()) {
27108
- _context21.next = 4;
27282
+ _context22.next = 4;
27109
27283
  break;
27110
27284
  }
27111
27285
  logging.debug('Subscriber: Skipping ice restart, websocket is not connected');
27112
- return _context21.abrupt("return");
27286
+ return _context22.abrupt("return");
27113
27287
  case 4:
27114
27288
  if (!_session.sessionInfo.p2pEnabled) {
27115
- _context21.next = 6;
27289
+ _context22.next = 6;
27116
27290
  break;
27117
27291
  }
27118
- return _context21.abrupt("return");
27292
+ return _context22.abrupt("return");
27119
27293
  case 6:
27120
- _context21.next = 8;
27294
+ _context22.next = 8;
27121
27295
  return getPeerConnectionBySourceStreamId('MANTIS');
27122
27296
  case 8:
27123
- peerConnection = _context21.sent;
27297
+ peerConnection = _context22.sent;
27124
27298
  if (peerConnection) {
27125
- _context21.next = 12;
27299
+ _context22.next = 12;
27126
27300
  break;
27127
27301
  }
27128
27302
  logging.debug('Subscriber: Skipping ice restart, we have no peer connection');
27129
- return _context21.abrupt("return");
27303
+ return _context22.abrupt("return");
27130
27304
  case 12:
27131
27305
  logging.debug('Subscriber: iceRestart attempt');
27132
27306
  peerConnection.iceRestart(reason, forcedRestart);
27133
27307
  case 14:
27134
27308
  case "end":
27135
- return _context21.stop();
27309
+ return _context22.stop();
27136
27310
  }
27137
- }, _callee21);
27311
+ }, _callee22);
27138
27312
  }))();
27139
27313
  },
27140
27314
  unblockAudio: () => _widgetView && _widgetView.unblockAudio(),
27141
27315
  webRtcStream: () => _webRTCStream,
27142
27316
  setIceConfig: function () {
27143
- var _setIceConfig = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee23(iceConfig) {
27144
- return _regenerator.default.wrap(function _callee23$(_context23) {
27145
- while (1) switch (_context23.prev = _context23.next) {
27317
+ var _setIceConfig = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee24(iceConfig) {
27318
+ return _regenerator.default.wrap(function _callee24$(_context24) {
27319
+ while (1) switch (_context24.prev = _context24.next) {
27146
27320
  case 0:
27147
27321
  getAllPeerConnections().forEach( /*#__PURE__*/function () {
27148
- var _ref36 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee22(pc) {
27149
- return _regenerator.default.wrap(function _callee22$(_context22) {
27150
- while (1) switch (_context22.prev = _context22.next) {
27322
+ var _ref37 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee23(pc) {
27323
+ return _regenerator.default.wrap(function _callee23$(_context23) {
27324
+ while (1) switch (_context23.prev = _context23.next) {
27151
27325
  case 0:
27152
- _context22.next = 2;
27326
+ _context23.next = 2;
27153
27327
  return pc;
27154
27328
  case 2:
27155
- return _context22.abrupt("return", _context22.sent.setIceConfig(iceConfig));
27329
+ return _context23.abrupt("return", _context23.sent.setIceConfig(iceConfig));
27156
27330
  case 3:
27157
27331
  case "end":
27158
- return _context22.stop();
27332
+ return _context23.stop();
27159
27333
  }
27160
- }, _callee22);
27334
+ }, _callee23);
27161
27335
  }));
27162
- return function (_x21) {
27163
- return _ref36.apply(this, arguments);
27336
+ return function (_x24) {
27337
+ return _ref37.apply(this, arguments);
27164
27338
  };
27165
27339
  }());
27166
27340
  case 1:
27167
27341
  case "end":
27168
- return _context23.stop();
27342
+ return _context24.stop();
27169
27343
  }
27170
- }, _callee23);
27344
+ }, _callee24);
27171
27345
  }));
27172
- function setIceConfig(_x20) {
27346
+ function setIceConfig(_x23) {
27173
27347
  return _setIceConfig.apply(this, arguments);
27174
27348
  }
27175
27349
  return setIceConfig;
@@ -27188,15 +27362,15 @@ function SubscriberFactory(_ref2) {
27188
27362
  amrState.startTransitionToRouted(_transitionRelayedToRouted);
27189
27363
  },
27190
27364
  startMigration() {
27191
- return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee24() {
27192
- return _regenerator.default.wrap(function _callee24$(_context24) {
27193
- while (1) switch (_context24.prev = _context24.next) {
27365
+ return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee25() {
27366
+ return _regenerator.default.wrap(function _callee25$(_context25) {
27367
+ while (1) switch (_context25.prev = _context25.next) {
27194
27368
  case 0:
27195
27369
  if (!_state.isMigrating()) {
27196
- _context24.next = 2;
27370
+ _context25.next = 2;
27197
27371
  break;
27198
27372
  }
27199
- return _context24.abrupt("return");
27373
+ return _context25.abrupt("return");
27200
27374
  case 2:
27201
27375
  _state.set('Migrating');
27202
27376
  logAnalyticsEvent('SessionMigration', 'Attempt');
@@ -27206,53 +27380,53 @@ function SubscriberFactory(_ref2) {
27206
27380
  socket = _session._.getSocket();
27207
27381
  socket.on('signalingNetworkQualityScoreChanged', networkConditionChecker.checkNetworkConditionChange);
27208
27382
  if (!_session.sessionInfo.p2pEnabled) {
27209
- _context24.next = 12;
27383
+ _context25.next = 12;
27210
27384
  break;
27211
27385
  }
27212
27386
  subscriberCreate('P2P');
27213
- _context24.next = 16;
27387
+ _context25.next = 16;
27214
27388
  break;
27215
27389
  case 12:
27216
- _context24.next = 14;
27390
+ _context25.next = 14;
27217
27391
  return getPeerConnectionBySourceStreamId('MANTIS');
27218
27392
  case 14:
27219
- _previousPeerConnection = _context24.sent;
27393
+ _previousPeerConnection = _context25.sent;
27220
27394
  subscriberCreate('MANTIS');
27221
27395
  case 16:
27222
27396
  case "end":
27223
- return _context24.stop();
27397
+ return _context25.stop();
27224
27398
  }
27225
- }, _callee24);
27399
+ }, _callee25);
27226
27400
  }))();
27227
27401
  },
27228
27402
  finishMigration() {
27229
- return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee26() {
27403
+ return (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee27() {
27230
27404
  var destroyPeerConnection, _getPeerConnectionByS;
27231
- return _regenerator.default.wrap(function _callee26$(_context26) {
27232
- while (1) switch (_context26.prev = _context26.next) {
27405
+ return _regenerator.default.wrap(function _callee27$(_context27) {
27406
+ while (1) switch (_context27.prev = _context27.next) {
27233
27407
  case 0:
27234
27408
  destroyPeerConnection = /*#__PURE__*/function () {
27235
- var _ref37 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee25(pc, sourceStreamId) {
27236
- return _regenerator.default.wrap(function _callee25$(_context25) {
27237
- while (1) switch (_context25.prev = _context25.next) {
27409
+ var _ref38 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee26(pc, sourceStreamId) {
27410
+ return _regenerator.default.wrap(function _callee26$(_context26) {
27411
+ while (1) switch (_context26.prev = _context26.next) {
27238
27412
  case 0:
27239
27413
  if (!pc) {
27240
- _context25.next = 5;
27414
+ _context26.next = 5;
27241
27415
  break;
27242
27416
  }
27243
- _context25.next = 3;
27417
+ _context26.next = 3;
27244
27418
  return _subscriberStatsHelper.removePeerConnection(pc);
27245
27419
  case 3:
27246
27420
  pc.close();
27247
27421
  delete peerConnectionsAsync[sourceStreamId];
27248
27422
  case 5:
27249
27423
  case "end":
27250
- return _context25.stop();
27424
+ return _context26.stop();
27251
27425
  }
27252
- }, _callee25);
27426
+ }, _callee26);
27253
27427
  }));
27254
- return function destroyPeerConnection(_x22, _x23) {
27255
- return _ref37.apply(this, arguments);
27428
+ return function destroyPeerConnection(_x25, _x26) {
27429
+ return _ref38.apply(this, arguments);
27256
27430
  };
27257
27431
  }(); // Clear previous PC
27258
27432
  // We don't pass 'MANTIS' because we don't want to delete the new MANTIS peer connection
@@ -27268,9 +27442,9 @@ function SubscriberFactory(_ref2) {
27268
27442
  logAnalyticsEvent('SessionMigration', 'Success');
27269
27443
  case 7:
27270
27444
  case "end":
27271
- return _context26.stop();
27445
+ return _context27.stop();
27272
27446
  }
27273
- }, _callee26);
27447
+ }, _callee27);
27274
27448
  }))();
27275
27449
  },
27276
27450
  setSinkId(deviceId) {
@@ -27408,6 +27582,9 @@ function SubscriberFactory(_ref2) {
27408
27582
  * @param {Boolean} value Whether to start subscribing to captions (<code>true</code>) or not
27409
27583
  * (<code>false</code>).
27410
27584
  *
27585
+ * @return {Promise<void>} A promise that resolves when the server has acknowledged the
27586
+ * caption channel update. The promise is rejected if an error occurs while sending the update.
27587
+ *
27411
27588
  * @see <a href="#isSubscribedToCaptions">isSubscribedToCaptions()</a>
27412
27589
  * @see <a href="#event:captionReceived">captionReceived</a> event
27413
27590
  * @see <a href="StreamPropertyChangedEvent.html">StreamPropertyChangedEvent</a>
@@ -27416,34 +27593,36 @@ function SubscriberFactory(_ref2) {
27416
27593
  * @method #subscribeToCaptions
27417
27594
  * @memberOf Subscriber
27418
27595
  */
27419
- this.subscribeToCaptions = /*#__PURE__*/function () {
27420
- var _ref38 = (0, _asyncToGenerator2.default)( /*#__PURE__*/_regenerator.default.mark(function _callee27(value) {
27421
- var active, attributes;
27422
- return _regenerator.default.wrap(function _callee27$(_context27) {
27423
- while (1) switch (_context27.prev = _context27.next) {
27424
- case 0:
27425
- active = (0, _castToBoolean.default)(value, true);
27426
- attributes = {
27427
- active
27428
- };
27429
- _properties.subscribeToCaptions = active;
27430
- logAnalyticsEvent('subscribeToCaptions', 'Attempt', {
27431
- subscribeToCaptions: active
27432
- });
27433
- socket.subscriberChannelUpdate(_stream.id, _this.widgetId, 'caption1', attributes);
27434
- logAnalyticsEvent('subscribeToCaptions', 'Success', {
27435
- subscribeToCaptions: active
27436
- });
27437
- case 6:
27438
- case "end":
27439
- return _context27.stop();
27596
+ this.subscribeToCaptions = value => new Promise((resolve, reject) => {
27597
+ try {
27598
+ const active = (0, _castToBoolean.default)(value, true);
27599
+ const attributes = {
27600
+ active
27601
+ };
27602
+ _properties.subscribeToCaptions = active;
27603
+ logAnalyticsEvent('subscribeToCaptions', 'Attempt', {
27604
+ subscribeToCaptions: active
27605
+ });
27606
+ socket.subscriberChannelUpdate(_stream.id, this.widgetId, 'caption1', attributes, err => {
27607
+ if (err) {
27608
+ logAnalyticsEvent('subscribeToCaptions', 'Failure', {
27609
+ message: (err == null ? void 0 : err.message) || String(err)
27610
+ });
27611
+ reject(err);
27612
+ } else {
27613
+ logAnalyticsEvent('subscribeToCaptions', 'Success', {
27614
+ subscribeToCaptions: active
27615
+ });
27616
+ resolve();
27440
27617
  }
27441
- }, _callee27);
27442
- }));
27443
- return function (_x24) {
27444
- return _ref38.apply(this, arguments);
27445
- };
27446
- }();
27618
+ });
27619
+ } catch (err) {
27620
+ logAnalyticsEvent('subscribeToCaptions', 'Failure', {
27621
+ message: (err == null ? void 0 : err.message) || String(err)
27622
+ });
27623
+ reject(err);
27624
+ }
27625
+ });
27447
27626
 
27448
27627
  /**
27449
27628
  * Sets the preferred language for captions translation for this subscriber.
@@ -27467,7 +27646,7 @@ function SubscriberFactory(_ref2) {
27467
27646
  _context28.next = 4;
27468
27647
  break;
27469
27648
  }
27470
- message = `Invalid captions language code ${langCode}`;
27649
+ message = `Invalid captions translation language ${langCode}`;
27471
27650
  logging.warn(`setCaptionsTranslationLanguage: ${message}`);
27472
27651
  throw otError(_Errors.default.INVALID_PARAMETER, new Error(`setCaptionsTranslationLanguage: ${message}`));
27473
27652
  case 4:
@@ -27486,7 +27665,7 @@ function SubscriberFactory(_ref2) {
27486
27665
  }
27487
27666
  }, _callee28);
27488
27667
  }));
27489
- return function (_x25) {
27668
+ return function (_x27) {
27490
27669
  return _ref39.apply(this, arguments);
27491
27670
  };
27492
27671
  }();
@@ -27720,7 +27899,7 @@ function SubscriberFactory(_ref2) {
27720
27899
  }
27721
27900
  }, _callee29, null, [[15, 20]]);
27722
27901
  }));
27723
- return function (_x26) {
27902
+ return function (_x28) {
27724
27903
  return _ref40.apply(this, arguments);
27725
27904
  };
27726
27905
  }();
@@ -27895,7 +28074,7 @@ function SubscriberFactory(_ref2) {
27895
28074
  }
27896
28075
  }, _callee31);
27897
28076
  }));
27898
- return function (_x27) {
28077
+ return function (_x29) {
27899
28078
  return _ref42.apply(this, arguments);
27900
28079
  };
27901
28080
  }();
@@ -29339,8 +29518,11 @@ function RaptorSocketFactory(deps) {
29339
29518
  this.subscriberUpdate = function (streamId, subscriberId, attributes) {
29340
29519
  this.publish(RaptorMessage.subscribers.update(_apiKey, _sessionId, streamId, subscriberId, attributes), {}, true);
29341
29520
  };
29342
- this.subscriberChannelUpdate = function (streamId, subscriberId, channelId, attributes) {
29343
- this.publish(RaptorMessage.subscriberChannels.update(_apiKey, _sessionId, streamId, subscriberId, channelId, attributes), {}, true);
29521
+ this.subscriberChannelUpdate = function (streamId, subscriberId, channelId, attributes, completion) {
29522
+ if (completion === void 0) {
29523
+ completion = () => {};
29524
+ }
29525
+ this.publish(RaptorMessage.subscriberChannels.update(_apiKey, _sessionId, streamId, subscriberId, channelId, attributes), {}, true, completion);
29344
29526
  };
29345
29527
  this.forceDisconnect = function (connectionIdToDisconnect, completion) {
29346
29528
  this.publish(RaptorMessage.connections.destroy({
@@ -41954,7 +42136,7 @@ function staticConfigFactory(_temp) {
41954
42136
  _ref$axios = _ref.axios,
41955
42137
  axios = _ref$axios === void 0 ? _axios.default : _ref$axios,
41956
42138
  _ref$properties = _ref.properties,
41957
- properties = _ref$properties === void 0 ? {"version":"v2.35.0","buildHash":"1130ccbf0","minimumVersion":{"firefox":52,"chrome":49},"debug":false,"websiteURL":"http://www.tokbox.com","configURL":"https://config.opentok.com","ipWhitelistConfigURL":"","cdnURL":"","loggingURL":"https://hlg.tokbox.com/prod","apiURL":"https://anvil.opentok.com","vonageApiURL":""} : _ref$properties;
42139
+ properties = _ref$properties === void 0 ? {"version":"v2.35.0","buildHash":"af69a9c37","minimumVersion":{"firefox":52,"chrome":49},"debug":false,"websiteURL":"http://www.tokbox.com","configURL":"https://config.opentok.com","ipWhitelistConfigURL":"","cdnURL":"","loggingURL":"https://hlg.tokbox.com/prod","apiURL":"https://anvil.opentok.com","vonageApiURL":""} : _ref$properties;
41958
42140
  /** @type builtInConfig */
41959
42141
  const builtInConfig = (0, _cloneDeep.default)(properties);
41960
42142
  /**