You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.

PrecallTest.js 3.7KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133
  1. import EventEmitter from 'events';
  2. import browser from '../browser';
  3. import Settings from '../settings/Settings';
  4. import ScriptUtil from '../util/ScriptUtil';
  5. import { CALLSTATS_SCRIPT_URL } from './constants';
  6. const PRECALL_TEST_RESULTS = 'preCallTestResults';
  7. const emitter = new EventEmitter();
  8. let _initialized = false;
  9. let api = null;
  10. /**
  11. * Loads the callstats io script.
  12. *
  13. * @returns {Promise<void>}
  14. */
  15. function _loadScript(options) {
  16. if (browser.isReactNative()) {
  17. return;
  18. }
  19. return new Promise(resolve => {
  20. ScriptUtil.loadScript(
  21. options.callStatsCustomScriptUrl || CALLSTATS_SCRIPT_URL,
  22. /* async */ true,
  23. /* prepend */ true,
  24. /* relativeURL */ undefined,
  25. /* loadCallback */ resolve);
  26. });
  27. }
  28. /**
  29. * Initializes the callstats lib and registers a callback to be invoked
  30. * when there are 'preCallTestResults'.
  31. *
  32. * @typedef PrecallTestOptions
  33. * @type {Object}
  34. * @property {string} callStatsID - Callstats credentials - the id.
  35. * @property {string} callStatsSecret - Callstats credentials - the secret.
  36. * @property {string} statisticsId - The user name to use when initializing callstats.
  37. * @property {string} statisticsDisplayName - The user display name.
  38. *
  39. * @param { PrecallTestOptions} options - The init options.
  40. * @returns {Promise<void>}
  41. */
  42. function _initialize(options) {
  43. return new Promise((resolve, reject) => {
  44. const appId = options.callStatsID;
  45. const appSecret = options.callStatsSecret;
  46. const userId = options.statisticsId || options.statisticsDisplayName || Settings.callStatsUserName;
  47. api.initialize(appId, appSecret, userId, (status, message) => {
  48. if (status === 'success') {
  49. api.on(PRECALL_TEST_RESULTS, (...args) => {
  50. emitter.emit(PRECALL_TEST_RESULTS, ...args);
  51. });
  52. _initialized = true;
  53. resolve();
  54. } else {
  55. reject({
  56. status,
  57. message
  58. });
  59. }
  60. }, null, { disablePrecalltest: true });
  61. });
  62. }
  63. /**
  64. * Loads the callstats script and initializes the library.
  65. *
  66. * @param {Function} onResult - The callback to be invoked when results are received.
  67. * @returns {Promise<void>}
  68. */
  69. export async function init(options) {
  70. if (_initialized) {
  71. throw new Error('Precall Test already initialized');
  72. }
  73. const { callStatsID, callStatsSecret, disableThirdPartyRequests } = options;
  74. if (!callStatsID || !callStatsSecret || disableThirdPartyRequests) {
  75. throw new Error('Callstats is disabled');
  76. }
  77. await _loadScript(options);
  78. // eslint-disable-next-line new-cap
  79. api = new window.callstats();
  80. return _initialize(options);
  81. }
  82. /**
  83. * Executes a pre call test.
  84. *
  85. * @typedef PrecallTestResults
  86. * @type {Object}
  87. * @property {boolean} mediaConnectivity - If there is media connectivity or not.
  88. * @property {number} throughput - The average throughput.
  89. * @property {number} fractionalLoss - The packet loss.
  90. * @property {number} rtt - The round trip time.
  91. * @property {string} provider - It is usually 'callstats'.
  92. *
  93. * @returns {Promise<{PrecallTestResults}>}
  94. */
  95. export function execute() {
  96. if (!_initialized) {
  97. return Promise.reject('uninitialized');
  98. }
  99. return new Promise((resolve, reject) => {
  100. emitter.on(PRECALL_TEST_RESULTS, (status, payload) => {
  101. if (status === 'success') {
  102. resolve(payload);
  103. } else {
  104. reject({
  105. status,
  106. payload
  107. });
  108. }
  109. });
  110. api.makePrecallTest();
  111. });
  112. }
  113. export default {
  114. init,
  115. execute
  116. };