UNPKG

sinch-rtc

Version:

RTC JavaScript/Web SDK

195 lines 7.47 kB
"use strict"; Object.defineProperty(exports, "__esModule", { value: true }); exports.CallReportUtils = void 0; const api_1 = require("../../ocra/api"); const api_2 = require("../../ocra/api"); const Direction_1 = require("../../session/Direction"); const SinchError_1 = require("../../SinchError"); const CallEndCause_1 = require("../CallEndCause"); const OutboundCall_1 = require("../OutboundCall"); const CallDestination_1 = require("./CallDestination"); const CallOrigin_1 = require("./CallOrigin"); /** * Class acting as a helper for converting properties of different components into format used in * call reporting functionality. */ class CallReportUtils { static getCallResult(call) { switch (call.details.endCause) { case CallEndCause_1.CallEndCause.Canceled: return api_1.CallResult.Canceled; case CallEndCause_1.CallEndCause.Denied: return api_1.CallResult.Denied; case CallEndCause_1.CallEndCause.Failure: return api_1.CallResult.Failure; case CallEndCause_1.CallEndCause.HungUp: case CallEndCause_1.CallEndCause.Inactive: return CallReportUtils.inferHungUpResult(call.details); case CallEndCause_1.CallEndCause.Timeout: return api_1.CallResult.NoAnswer; case CallEndCause_1.CallEndCause.OtherDeviceAnswered: return api_1.CallResult.OtherPeerAnswered; default: return api_1.CallResult.Failure; } } static getCallReportDirection(call) { return call.direction == Direction_1.Direction.Inbound ? api_2.Direction.Inbound : api_2.Direction.Outbound; } static getDurationInSeconds(durationMs) { return durationMs / 1000; } static getClientErrors(error) { if (error == undefined) { return undefined; } const clientError = { message: error.message, code: error.code, domain: CallReportUtils.getClientErrorDomain(error.domain), }; return [clientError]; } static getClientErrorDomain(domain) { switch (domain) { case SinchError_1.ErrorType.Http: return api_1.ClientErrorDomain.Http; case SinchError_1.ErrorType.Network: return api_1.ClientErrorDomain.Network; default: return undefined; } } static getRemoteDomain(call) { return call instanceof OutboundCall_1.OutboundCall ? call.destination.domain : call.remoteDomain; } static getCallDestination(call, userId) { return new CallDestination_1.CallDestination(call, userId).getDestination(); } static getCallOrigin(call, userId) { return new CallOrigin_1.CallOrigin(call, userId).getOrigin(); } static getCallReportInstance(instance) { return { version: instance.version, id: instance.id, }; } static getIceCandidate(candidate) { return { address: candidate.address, port: candidate.port, type: this.getIceCandidateType(candidate.candidateType), ipProtocolVersion: this.getIpVersion(candidate.address), transportProtocol: this.getIceTransportProtocol(candidate.protocol), relayProtocol: this.getRelayProtocol(candidate.relayProtocol), url: candidate.url, }; } static getPrimaryIceCandidate({ connectionInfos, isLocal, }) { const mapFunc = (connectionInfo) => isLocal ? connectionInfo.localIceCandidate : connectionInfo.remoteIceCandidate; const candidates = connectionInfos.map(mapFunc); const frequencyMap = new Map(); candidates.forEach((candidate) => { var _a; const key = this.getIceCandidateHash(candidate); frequencyMap.set(key, [(((_a = frequencyMap.get(key)) === null || _a === void 0 ? void 0 : _a[0]) || 0) + 1, candidate]); }); let mostUsedCanididate = undefined; let maxCount = 0; for (const [, pair] of frequencyMap) { if (pair[0] > maxCount) { maxCount = pair[0]; mostUsedCanididate = pair[1]; } } return mostUsedCanididate; } static filterSubsequentSameConnectionInfos(connectionInfos) { const filteredInfo = []; let current; for (const info of connectionInfos) { if (current && this.isConnectionInfoEqual(current, info)) { continue; } current = info; filteredInfo.push(info); } return filteredInfo; } static isConnectionInfoEqual(a, b) { return (this.getIceCandidateHash(a.localIceCandidate) == this.getIceCandidateHash(b.localIceCandidate) && this.getIceCandidateHash(a.remoteIceCandidate) === this.getIceCandidateHash(b.remoteIceCandidate)); } static getIceCandidateHash(candidate) { return `${candidate.address}:${candidate.port}:${candidate.ipProtocolVersion}:${candidate.type}:${candidate.transportProtocol}`; } static getIceCandidateType(type) { switch (type) { case "host": return api_1.IceCandidateType.Host; case "prflx": return api_1.IceCandidateType.Prflx; case "relay": return api_1.IceCandidateType.Relay; case "srflx": return api_1.IceCandidateType.Srflx; } } static getIceTransportProtocol(transport) { switch (transport) { case "udp": return api_1.TransportProtocol.Udp; case "tcp": return api_1.TransportProtocol.Tcp; } } static getRelayProtocol(protocol) { if (protocol === undefined || protocol === null) { return undefined; } switch (protocol.toLowerCase()) { case "udp": return api_1.RelayProtocol.Udp; case "tcp": return api_1.RelayProtocol.Tcp; case "tls": return api_1.RelayProtocol.Tls; default: return undefined; } } static getIpVersion(host) { // The "address" field in WebRTC stats could contain: // - ipv4 address // - ipv6 address // - fully qualified domain name // https://www.w3.org/TR/webrtc-stats/#dom-rtcicecandidatestats-address if (host === undefined) { return api_1.IpProtocolVersion.Unknown; } const dotCount = host.split(".").length - 1; if (dotCount == 3) { return api_1.IpProtocolVersion.Ipv4; } // ipv6 supports "compressed" representation, that omits leading zeroes. const colonsCount = host.split(":").length - 1; if (colonsCount >= 1) return api_1.IpProtocolVersion.Ipv6; return api_1.IpProtocolVersion.Unknown; } static inferHungUpResult(details) { const wasEstablished = details.establishedTime != undefined; return wasEstablished ? api_1.CallResult.Established : api_1.CallResult.Answered; } } exports.CallReportUtils = CallReportUtils; //# sourceMappingURL=CallReportUtils.js.map