UNPKG

sinch-rtc

Version:

RTC JavaScript/Web SDK

253 lines 12.1 kB
"use strict"; var __awaiter = (this && this.__awaiter) || function (thisArg, _arguments, P, generator) { function adopt(value) { return value instanceof P ? value : new P(function (resolve) { resolve(value); }); } return new (P || (P = Promise))(function (resolve, reject) { function fulfilled(value) { try { step(generator.next(value)); } catch (e) { reject(e); } } function rejected(value) { try { step(generator["throw"](value)); } catch (e) { reject(e); } } function step(result) { result.done ? resolve(result.value) : adopt(result.value).then(fulfilled, rejected); } step((generator = generator.apply(thisArg, _arguments || [])).next()); }); }; Object.defineProperty(exports, "__esModule", { value: true }); exports.DefaultSinchClient = void 0; const calling_1 = require("./calling"); const models_1 = require("./models"); const api_1 = require("./ocra/api"); const InstanceController_1 = require("./instance/InstanceController"); const fsm_1 = require("./session/fsm"); const push_1 = require("./push"); const ClientEventFanout_1 = require("./calling/listeners/ClientEventFanout"); const CallReporter_1 = require("./calling/reporting/CallReporter"); const ApiClient_1 = require("./ocra/ApiClient"); const utils_1 = require("./utils"); const Features_1 = require("./features/Features"); const StorageFactory_1 = require("./storage/StorageFactory"); const IceServer_1 = require("./rtc/IceServer"); class DefaultSinchClient { /** * @param config - * config.applicationKey - application unique key from Sinch portal * config.userId - userId for whom instance is created * [config.ttl] TODO: TTL param for setting lifetime of Ocra instance */ constructor(config) { this.ServiceWorkerName = "sw.js"; this.isClientStarted = false; this.useRelayIceCandidatesOnly = false; this.isUsingManagedPush = false; this.processExternalPushNotification = (json) => { const payload = { sinch: json, name: "ForSmokeTests", }; this.relayRemotePushNotification(payload); }; this.onPush = (message) => { this.relayRemotePushNotification(message.data); }; this.clientEvent = new ClientEventFanout_1.ClientEventFanout(this); this.features = Features_1.FeaturesFactory.create(StorageFactory_1.StorageFactory.createFeatureStorage()); if (!config || !config.applicationKey) { throw new Error("Parameter appKey is required"); } this.applicationKey = config.applicationKey; this.userId = config.userId; this.callerIdentifier = config.callerIdentifier; this.apiClient = ApiClient_1.ApiClientFactory.create(new api_1.Configuration({ basePath: this.getBaseUrl(config.baseUrl), fetchApi: config.fetchApi, })); this.instanceController = new InstanceController_1.InstanceController(this.applicationKey, this.userId, this.clientEvent, this.apiClient); this.pushService = push_1.PushFactory.createPushService(this.userId, this.apiClient); this.defaultCallClient = calling_1.CallClientFactory.create(this.userId, this.applicationKey, config.mediaManager); this.onStartedAction = new Array(); this.addTurnListener = (0, utils_1.pipe)(IceServer_1.onTurnFeatureFlagChanged, this.features.addListener.bind(this.features)); } set pushNotificationDisplayName(displayName) { if (displayName && displayName.length > 255) throw new fsm_1.ArgumentError("displayName must not exceed 255 bytes", (0, utils_1.nameof)(displayName)); this.pushService.pushNotificationDisplayName = displayName; } get pushNotificationDisplayName() { return this.pushService.pushNotificationDisplayName; } setUseRelayIceCandidatesOnly(useRelayIceCandidatesOnly) { this.useRelayIceCandidatesOnly = useRelayIceCandidatesOnly; } getBaseUrl(url) { return ((!this.isUrl(url) ? "https://" : "") + url + DefaultSinchClient.OCRA_PATH); } isUrl(urlOrHost) { return urlOrHost.startsWith("http://") || urlOrHost.startsWith("https://"); } start(instanceConfig) { return __awaiter(this, void 0, void 0, function* () { try { this.started(yield this.instanceController.start(), instanceConfig); } catch (ex) { this.isClientStarted = false; console.error(ex); this.failed("Unable to create instance!"); } }); } setSupportManagedPush(serviceWorker) { return __awaiter(this, void 0, void 0, function* () { this.instanceController.toggleCapability(models_1.Capability.PushV4, true); this.isUsingManagedPush = true; this.pushWorker = push_1.PushFactory.createPushWorker(serviceWorker !== null && serviceWorker !== void 0 ? serviceWorker : this.ServiceWorkerName, this.pushService); yield this.pushWorker.register(); this.pushWorker.addEventListener(this.onPush); }); } disableManagedPushSupport() { return __awaiter(this, void 0, void 0, function* () { var _a; this.instanceController.toggleCapability(models_1.Capability.PushV4, false); this.isUsingManagedPush = false; yield ((_a = this.pushWorker) === null || _a === void 0 ? void 0 : _a.unregister()); this.pushWorker = undefined; }); } failed(reason) { return __awaiter(this, void 0, void 0, function* () { this.clientEvent.onEvent({ eventType: "failed", context: reason }); }); } setupPush(instance, applicationServerKey) { return __awaiter(this, void 0, void 0, function* () { if (!applicationServerKey) throw new fsm_1.InvalidOperationError("Missing public VAPID key"); if (this.pushWorker) { // todo: this key should be populated from the instanceConfig once the push backend is ready, for now fallback on hardcoded. yield this.pushWorker.start(applicationServerKey, instance); } }); } createAndSetUpCallReporter(instance) { return new CallReporter_1.CallReporter(this.userId, instance, this.apiClient); } started(instance, config) { return __awaiter(this, void 0, void 0, function* () { var _a; try { if (this.instanceController.authentication) { const instanceConfig = config !== null && config !== void 0 ? config : (yield this.apiClient.getConfig({ instanceId: instance.id, userId: this.userId, })); this.instanceConfigJson = JSON.stringify(instanceConfig); this.setupConfigCheck(instance, instanceConfig); this.instanceController.setUpdateInstanceTtlWindow(instanceConfig.updateInstanceTtlWindowDays); this.apiClient.setUpdateInstanceTtlWindow(instanceConfig.updateInstanceTtlWindowDays); yield this.instanceController.prolongInstanceIfNeeded(); this.addTurnListener(this.instanceController); const fetchIceServers = (0, IceServer_1.createIceServerFetcher)(this.apiClient, this.userId, instance.id); this.features.setUserInstance(this.userId, instance.id, this.applicationKey); const callReporter = this.createAndSetUpCallReporter(instance); if (this.features.shouldRefresh()) { yield this.features.refresh(this.apiClient); } if (this.isUsingManagedPush) { yield this.setupPush(instance, (_a = instanceConfig.pushConfig) === null || _a === void 0 ? void 0 : _a.w3cApplicationServerKey); } this.defaultCallClient.init(this, instanceConfig.rtcProfile, instanceConfig.rtcConfig, fetchIceServers, callReporter, this.pushService, this.useRelayIceCandidatesOnly, this.features, instance.id, this.callerIdentifier); this.isClientStarted = true; this.onStartedAction.splice(0).forEach((a) => a()); this.clientEvent.onEvent({ eventType: "started" }); } } catch (error) { this.failed(error).catch(() => { console.error(error); }); } }); } setupConfigCheck(instance, instanceConfig) { var _a, _b; const configUpdater = () => __awaiter(this, void 0, void 0, function* () { var _a; const newInstanceConfig = yield this.apiClient.getConfig({ instanceId: instance.id, userId: this.userId, }); const newInstanceConfigJson = JSON.stringify(newInstanceConfig); if (this.instanceConfigJson !== newInstanceConfigJson) { this.clearInstanceConfigUpdateInterval(); // eslint-disable-next-line no-constant-condition while (true) { if (!((_a = this.defaultCallClient.getInstance()) === null || _a === void 0 ? void 0 : _a.hasActiveCall())) { console.log("New instance config - restarting client"); this.terminate(); this.start(newInstanceConfig); break; } yield utils_1.PromiseHelper.sleep(1000); } } }); const interval = setInterval(configUpdater, instanceConfig.configRefreshIntervalMs); this.instanceConfigUpdateInterval = (_b = (_a = interval.unref) === null || _a === void 0 ? void 0 : _a.call(interval)) !== null && _b !== void 0 ? _b : interval; } clearInstanceConfigUpdateInterval() { if (this.instanceConfigUpdateInterval != null) { clearInterval(this.instanceConfigUpdateInterval); this.instanceConfigUpdateInterval = undefined; } } addListener(listener) { this.clientEvent.addListener(listener); } removeListener(listener) { this.clientEvent.removeListener(listener); } initiateCall(request) { if (this.isClientStarted) { return this.apiClient.initiateCall(request); } else { throw new fsm_1.InvalidOperationError("Can not initiate a call before authentication"); } } get callClient() { return this.defaultCallClient; } terminate() { this.isClientStarted = false; this.instanceController.terminate(); this.clearInstanceConfigUpdateInterval(); this.features.resetListeners(); this.clientEvent.onEvent({ eventType: "terminated" }); } get localUserId() { return this.userId; } isStarted() { return this.isClientStarted; } relayRemotePushNotification(payload) { const result = new push_1.DefaultNotificationResult(payload.sinch, payload.name); if (result.isValid()) { if (this.isStarted()) { this.defaultCallClient.handleCallPushPayload(result); } else { this.onStartedAction.push(() => this.defaultCallClient.handleCallPushPayload(result)); this.start(); } } return result; } showPushNotification(title, options) { var _a; (_a = this.pushWorker) === null || _a === void 0 ? void 0 : _a.showNotification(title, options); } } exports.DefaultSinchClient = DefaultSinchClient; DefaultSinchClient.OCRA_PATH = "/ocra"; // Export as standalone to global scope if (typeof window !== "undefined") window.SinchClient = DefaultSinchClient; //# sourceMappingURL=DefaultSinchClient.js.map