sip-connector 6.13.3 → 6.14.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/dist/index.d.ts +3 -1
- package/dist/index.d.ts.map +1 -1
- package/dist/index.es5.js +1 -1
- package/dist/index.es5.js.map +1 -1
- package/dist/index.js +7 -1
- package/dist/index.js.map +1 -1
- package/dist/index.umd.js +1 -1
- package/dist/index.umd.js.map +1 -1
- package/dist/logger.d.ts +7 -0
- package/dist/logger.d.ts.map +1 -0
- package/dist/logger.js +21 -0
- package/dist/logger.js.map +1 -0
- package/dist/tools/__fixtures__/call.d.ts +11 -0
- package/dist/tools/__fixtures__/call.d.ts.map +1 -0
- package/dist/tools/__fixtures__/call.js +38 -0
- package/dist/tools/__fixtures__/call.js.map +1 -0
- package/dist/tools/__fixtures__/connectToServer.d.ts +151 -0
- package/dist/tools/__fixtures__/connectToServer.d.ts.map +1 -0
- package/dist/tools/__fixtures__/connectToServer.js +35 -0
- package/dist/tools/__fixtures__/connectToServer.js.map +1 -0
- package/dist/tools/__fixtures__/hasValidUri.d.ts +10 -0
- package/dist/tools/__fixtures__/hasValidUri.d.ts.map +1 -0
- package/dist/tools/__fixtures__/hasValidUri.js +14 -0
- package/dist/tools/__fixtures__/hasValidUri.js.map +1 -0
- package/dist/tools/__fixtures__/permissions.d.ts +9 -0
- package/dist/tools/__fixtures__/permissions.d.ts.map +1 -0
- package/dist/tools/__fixtures__/permissions.js +15 -0
- package/dist/tools/__fixtures__/permissions.js.map +1 -0
- package/dist/tools/__fixtures__/processRequest.d.ts +4 -0
- package/dist/tools/__fixtures__/processRequest.d.ts.map +1 -0
- package/dist/tools/__fixtures__/processRequest.js +71 -0
- package/dist/tools/__fixtures__/processRequest.js.map +1 -0
- package/dist/tools/__tests-utils__/parseObject.d.ts +4 -0
- package/dist/tools/__tests-utils__/parseObject.d.ts.map +1 -0
- package/dist/tools/__tests-utils__/parseObject.js +27 -0
- package/dist/tools/__tests-utils__/parseObject.js.map +1 -0
- package/dist/tools/__tests-utils__/resolveParseArray.d.ts +3 -0
- package/dist/tools/__tests-utils__/resolveParseArray.d.ts.map +1 -0
- package/dist/tools/__tests-utils__/resolveParseArray.js +17 -0
- package/dist/tools/__tests-utils__/resolveParseArray.js.map +1 -0
- package/dist/tools/answerIncomingCall.d.ts +22 -0
- package/dist/tools/answerIncomingCall.d.ts.map +1 -0
- package/dist/tools/answerIncomingCall.js +94 -0
- package/dist/tools/answerIncomingCall.js.map +1 -0
- package/dist/tools/callToServer.d.ts +23 -0
- package/dist/tools/callToServer.d.ts.map +1 -0
- package/dist/tools/callToServer.js +90 -0
- package/dist/tools/callToServer.js.map +1 -0
- package/dist/tools/connectToServer.d.ts +15 -0
- package/dist/tools/connectToServer.d.ts.map +1 -0
- package/dist/tools/connectToServer.js +52 -0
- package/dist/tools/connectToServer.js.map +1 -0
- package/dist/tools/disconnectFromServer.d.ts +4 -0
- package/dist/tools/disconnectFromServer.d.ts.map +1 -0
- package/dist/tools/disconnectFromServer.js +23 -0
- package/dist/tools/disconnectFromServer.js.map +1 -0
- package/dist/tools/error/getLinkError.d.ts +4 -0
- package/dist/tools/error/getLinkError.d.ts.map +1 -0
- package/dist/tools/error/getLinkError.js +36 -0
- package/dist/tools/error/getLinkError.js.map +1 -0
- package/dist/tools/error/getTypeFromError.d.ts +12 -0
- package/dist/tools/error/getTypeFromError.d.ts.map +1 -0
- package/dist/tools/error/getTypeFromError.js +63 -0
- package/dist/tools/error/getTypeFromError.js.map +1 -0
- package/dist/tools/error/getValuesFromError.d.ts +10 -0
- package/dist/tools/error/getValuesFromError.d.ts.map +1 -0
- package/dist/tools/error/getValuesFromError.js +26 -0
- package/dist/tools/error/getValuesFromError.js.map +1 -0
- package/dist/tools/error/index.d.ts +5 -0
- package/dist/tools/error/index.d.ts.map +1 -0
- package/dist/tools/error/index.js +13 -0
- package/dist/tools/error/index.js.map +1 -0
- package/dist/tools/hasPurgatory.d.ts +4 -0
- package/dist/tools/hasPurgatory.d.ts.map +1 -0
- package/dist/tools/hasPurgatory.js +9 -0
- package/dist/tools/hasPurgatory.js.map +1 -0
- package/dist/tools/index.d.ts +20 -0
- package/dist/tools/index.d.ts.map +1 -0
- package/dist/tools/index.js +66 -0
- package/dist/tools/index.js.map +1 -0
- package/dist/tools/resolveAskPermissionToEnableCam.d.ts +4 -0
- package/dist/tools/resolveAskPermissionToEnableCam.d.ts.map +1 -0
- package/dist/tools/resolveAskPermissionToEnableCam.js +18 -0
- package/dist/tools/resolveAskPermissionToEnableCam.js.map +1 -0
- package/dist/tools/resolveGetRemoteStreams.d.ts +4 -0
- package/dist/tools/resolveGetRemoteStreams.d.ts.map +1 -0
- package/dist/tools/resolveGetRemoteStreams.js +15 -0
- package/dist/tools/resolveGetRemoteStreams.js.map +1 -0
- package/dist/tools/resolveHandleChangeTracks.d.ts +5 -0
- package/dist/tools/resolveHandleChangeTracks.d.ts.map +1 -0
- package/dist/tools/resolveHandleChangeTracks.js +14 -0
- package/dist/tools/resolveHandleChangeTracks.js.map +1 -0
- package/dist/tools/resolveOnMustStopPresentation.d.ts +4 -0
- package/dist/tools/resolveOnMustStopPresentation.d.ts.map +1 -0
- package/dist/tools/resolveOnMustStopPresentation.js +15 -0
- package/dist/tools/resolveOnMustStopPresentation.js.map +1 -0
- package/dist/tools/resolveOnUseLicense.d.ts +5 -0
- package/dist/tools/resolveOnUseLicense.d.ts.map +1 -0
- package/dist/tools/resolveOnUseLicense.js +15 -0
- package/dist/tools/resolveOnUseLicense.js.map +1 -0
- package/dist/tools/resolveSendMediaState.d.ts +7 -0
- package/dist/tools/resolveSendMediaState.d.ts.map +1 -0
- package/dist/tools/resolveSendMediaState.js +18 -0
- package/dist/tools/resolveSendMediaState.js.map +1 -0
- package/dist/tools/resolveSendRefusalToTurnOnCam.d.ts +4 -0
- package/dist/tools/resolveSendRefusalToTurnOnCam.d.ts.map +1 -0
- package/dist/tools/resolveSendRefusalToTurnOnCam.js +20 -0
- package/dist/tools/resolveSendRefusalToTurnOnCam.js.map +1 -0
- package/dist/tools/resolveSendRefusalToTurnOnMic.d.ts +4 -0
- package/dist/tools/resolveSendRefusalToTurnOnMic.d.ts.map +1 -0
- package/dist/tools/resolveSendRefusalToTurnOnMic.js +20 -0
- package/dist/tools/resolveSendRefusalToTurnOnMic.js.map +1 -0
- package/dist/tools/resolveStartPresentation.d.ts +10 -0
- package/dist/tools/resolveStartPresentation.d.ts.map +1 -0
- package/dist/tools/resolveStartPresentation.js +19 -0
- package/dist/tools/resolveStartPresentation.js.map +1 -0
- package/dist/tools/resolveStopShareSipConnector.d.ts +8 -0
- package/dist/tools/resolveStopShareSipConnector.d.ts.map +1 -0
- package/dist/tools/resolveStopShareSipConnector.js +19 -0
- package/dist/tools/resolveStopShareSipConnector.js.map +1 -0
- package/dist/tools/resolveUpdatePresentation.d.ts +10 -0
- package/dist/tools/resolveUpdatePresentation.d.ts.map +1 -0
- package/dist/tools/resolveUpdatePresentation.js +19 -0
- package/dist/tools/resolveUpdatePresentation.js.map +1 -0
- package/dist/tools/resolveUpdateRemoteStreams.d.ts +6 -0
- package/dist/tools/resolveUpdateRemoteStreams.d.ts.map +1 -0
- package/dist/tools/resolveUpdateRemoteStreams.js +18 -0
- package/dist/tools/resolveUpdateRemoteStreams.js.map +1 -0
- package/dist/tools/sendDTMFAccumulated.d.ts +10 -0
- package/dist/tools/sendDTMFAccumulated.d.ts.map +1 -0
- package/dist/tools/sendDTMFAccumulated.js +26 -0
- package/dist/tools/sendDTMFAccumulated.js.map +1 -0
- package/dist/tools/syncMediaState/index.d.ts +19 -0
- package/dist/tools/syncMediaState/index.d.ts.map +1 -0
- package/dist/tools/syncMediaState/index.js +55 -0
- package/dist/tools/syncMediaState/index.js.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStartMainCam.d.ts +6 -0
- package/dist/tools/syncMediaState/resolveOnStartMainCam.d.ts.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStartMainCam.js +15 -0
- package/dist/tools/syncMediaState/resolveOnStartMainCam.js.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStartMic.d.ts +6 -0
- package/dist/tools/syncMediaState/resolveOnStartMic.d.ts.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStartMic.js +15 -0
- package/dist/tools/syncMediaState/resolveOnStartMic.js.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStopMainCam.d.ts +6 -0
- package/dist/tools/syncMediaState/resolveOnStopMainCam.d.ts.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStopMainCam.js +15 -0
- package/dist/tools/syncMediaState/resolveOnStopMainCam.js.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStopMic.d.ts +6 -0
- package/dist/tools/syncMediaState/resolveOnStopMic.d.ts.map +1 -0
- package/dist/tools/syncMediaState/resolveOnStopMic.js +15 -0
- package/dist/tools/syncMediaState/resolveOnStopMic.js.map +1 -0
- package/package.json +8 -9
package/dist/index.es5.js.map
CHANGED
|
@@ -1 +1 @@
|
|
|
1
|
-
{"version":3,"file":"index.es5.js","sources":["../src/utils/getCodecFromSender.ts","../src/causes.ts","../src/constants.ts","../src/eventNames.ts","../src/utils.ts","../src/videoSendingBalancer/setEncodingsToSender.ts","../src/SipConnector.ts","../src/getExtraHeadersRemoteAddress.ts","../src/headers.ts","../src/utils/errors.ts","../src/videoSendingBalancer/scaleBitrate.ts","../src/utils/findSenderByStream.ts","../src/utils/findVideoSender.ts","../src/videoSendingBalancer/hasIncludesString.ts","../src/videoSendingBalancer/getMaxBitrateByWidth.ts","../src/videoSendingBalancer/scaleBitrateByCodec.ts","../src/videoSendingBalancer/hasAv1Codec.ts","../src/videoSendingBalancer/getMaxBitrateByWidthAndCodec.ts","../src/videoSendingBalancer/processSender.ts","../src/videoSendingBalancer/balance.ts","../src/videoSendingBalancer/index.ts"],"sourcesContent":["const statsReportToArray = (results: RTCStatsReport) => {\n return [...results.keys()].map((key) => {\n return results.get(key);\n });\n};\n\nconst findInResultByType = (results: RTCStatsReport, type: string) => {\n return statsReportToArray(results).find((value) => {\n return value.type === type;\n });\n};\n\nconst getCodecFromSender = (sender: RTCRtpSender): Promise<string | undefined> => {\n return sender.getStats().then((stats: RTCStatsReport) => {\n const codec = findInResultByType(stats, 'codec');\n\n return codec?.mimeType;\n });\n};\n\nexport default getCodecFromSender;\n","// Generic error causes.\nexport const CONNECTION_ERROR = 'Connection Error';\nexport const REQUEST_TIMEOUT = 'Request Timeout';\nexport const SIP_FAILURE_CODE = 'SIP Failure Code';\nexport const INTERNAL_ERROR = 'Internal Error';\n// SIP error causes.\nexport const BUSY = 'Busy';\nexport const REJECTED = 'Rejected';\nexport const REDIRECTED = 'Redirected';\nexport const UNAVAILABLE = 'Unavailable';\nexport const NOT_FOUND = 'Not Found';\nexport const ADDRESS_INCOMPLETE = 'Address Incomplete';\nexport const INCOMPATIBLE_SDP = 'Incompatible SDP';\nexport const MISSING_SDP = 'Missing SDP';\nexport const AUTHENTICATION_ERROR = 'Authentication Error';\n// Session error causes.\nexport const BYE = 'Terminated';\nexport const WEBRTC_ERROR = 'WebRTC Error';\nexport const CANCELED = 'Canceled';\nexport const NO_ANSWER = 'No Answer';\nexport const EXPIRES = 'Expires';\nexport const NO_ACK = 'No ACK';\nexport const DIALOG_ERROR = 'Dialog Error';\nexport const USER_DENIED_MEDIA_ACCESS = 'User Denied Media Access';\nexport const BAD_MEDIA_DESCRIPTION = 'Bad Media Description';\nexport const RTP_TIMEOUT = 'RTP Timeout';\n","export const INCOMING_CALL = 'incomingCall';\nexport const DECLINED_INCOMING_CALL = 'declinedIncomingCall';\nexport const FAILED_INCOMING_CALL = 'failedIncomingCall';\nexport const TERMINATED_INCOMING_CALL = 'terminatedIncomingCall';\nexport const CONNECTING = 'connecting';\nexport const CONNECTED = 'connected';\nexport const DISCONNECTED = 'disconnected';\nexport const NEW_RTC_SESSION = 'newRTCSession';\nexport const REGISTERED = 'registered';\nexport const UNREGISTERED = 'unregistered';\nexport const REGISTRATION_FAILED = 'registrationFailed';\nexport const NEW_MESSAGE = 'newMessage';\nexport const SIP_EVENT = 'sipEvent';\nexport const AVAILABLE_SECOND_REMOTE_STREAM_EVENT = 'availableSecondRemoteStream';\nexport const NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT = 'notAvailableSecondRemoteStream';\nexport const MUST_STOP_PRESENTATION_EVENT = 'mustStopPresentation';\nexport const SHARE_STATE = 'shareState';\nexport const ENTER_ROOM = 'enterRoom';\nexport const USE_LICENSE = 'useLicense';\nexport const PEER_CONNECTION_CONFIRMED = 'peerconnection:confirmed';\nexport const PEER_CONNECTION_ONTRACK = 'peerconnection:ontrack';\nexport const CHANNELS = 'channels';\nexport const CHANNELS_NOTIFY = 'channels:notify';\nexport const ENDED_FROM_SERVER = 'ended:fromserver';\nexport const MAIN_CAM_CONTROL = 'main-cam-control';\nexport const ADMIN_STOP_MAIN_CAM = 'admin-stop-main-cam';\nexport const ADMIN_START_MAIN_CAM = 'admin-start-main-cam';\nexport const ADMIN_STOP_MIC = 'admin-stop-mic';\nexport const ADMIN_START_MIC = 'admin-start-mic';\nexport const ADMIN_FORCE_SYNC_MEDIA_STATE = 'admin-force-sync-media-state';\nexport const PARTICIPANT_ADDED_TO_LIST_MODERATORS = 'participant:added-to-list-moderators';\nexport const PARTICIPANT_REMOVED_FROM_LIST_MODERATORS = 'participant:removed-from-list-moderators';\nexport const PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE = 'participant:move-request-to-conference';\nexport const PARTICIPANT_MOVE_REQUEST_TO_STREAM = 'participant:move-request-to-stream';\nexport const PARTICIPANT_CANCELLING_WORD_REQUEST = 'participant:canceling-word-request';\nexport const WEBCAST_STARTED = 'webcast:started';\nexport const WEBCAST_STOPPED = 'webcast:stopped';\nexport const ACCOUNT_CHANGED = 'account:changed';\nexport const ACCOUNT_DELETED = 'account:deleted';\nexport const CONFERENCE_PARTICIPANT_TOKEN_ISSUED = 'conference:participant-token-issued';\nexport const ENDED = 'ended';\nexport const SENDING = 'sending';\nexport const REINVITE = 'reinvite';\nexport const REPLACES = 'replaces';\nexport const REFER = 'refer';\nexport const PROGRESS = 'progress';\nexport const ACCEPTED = 'accepted';\nexport const CONFIRMED = 'confirmed';\nexport const PEER_CONNECTION = 'peerconnection';\nexport const FAILED = 'failed';\nexport const MUTED = 'muted';\nexport const UNMUTED = 'unmuted';\nexport const NEW_DTMF = 'newDTMF';\nexport const NEW_INFO = 'newInfo';\nexport const HOLD = 'hold';\nexport const UNHOLD = 'unhold';\nexport const UPDATE = 'update';\nexport const SDP = 'sdp';\nexport const ICE_CANDIDATE = 'icecandidate';\nexport const GET_USER_MEDIA_FAILED = 'getusermediafailed';\nexport const PEER_CONNECTION_CREATE_OFFER_FAILED = 'peerconnection:createofferfailed';\nexport const PEER_CONNECTION_CREATE_ANSWER_FAILED = 'peerconnection:createanswerfailed';\nexport const PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED =\n 'peerconnection:setlocaldescriptionfailed';\nexport const PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED =\n 'peerconnection:setremotedescriptionfailed';\nexport const PRESENTATION_START = 'presentation:start';\nexport const PRESENTATION_STARTED = 'presentation:started';\nexport const PRESENTATION_END = 'presentation:end';\nexport const PRESENTATION_ENDED = 'presentation:ended';\nexport const PRESENTATION_FAILED = 'presentation:failed';\n","import {\n INCOMING_CALL,\n DECLINED_INCOMING_CALL,\n TERMINATED_INCOMING_CALL,\n FAILED_INCOMING_CALL,\n CONNECTING,\n CONNECTED,\n DISCONNECTED,\n NEW_RTC_SESSION,\n REGISTERED,\n UNREGISTERED,\n REGISTRATION_FAILED,\n NEW_MESSAGE,\n SIP_EVENT,\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n MUST_STOP_PRESENTATION_EVENT,\n SHARE_STATE,\n ENTER_ROOM,\n USE_LICENSE,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n CHANNELS,\n CHANNELS_NOTIFY,\n ENDED_FROM_SERVER,\n MAIN_CAM_CONTROL,\n ADMIN_START_MAIN_CAM,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n ADMIN_START_MIC,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n ENDED,\n SENDING,\n REINVITE,\n REPLACES,\n REFER,\n PROGRESS,\n ACCEPTED,\n CONFIRMED,\n PEER_CONNECTION,\n FAILED,\n MUTED,\n UNMUTED,\n NEW_DTMF,\n NEW_INFO,\n HOLD,\n UNHOLD,\n UPDATE,\n SDP,\n ICE_CANDIDATE,\n GET_USER_MEDIA_FAILED,\n PEER_CONNECTION_CREATE_OFFER_FAILED,\n PEER_CONNECTION_CREATE_ANSWER_FAILED,\n PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED,\n PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED,\n PRESENTATION_START,\n PRESENTATION_STARTED,\n PRESENTATION_END,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n} from './constants';\n\nexport const UA_SYNTHETICS_EVENT_NAMES = [\n INCOMING_CALL,\n DECLINED_INCOMING_CALL,\n TERMINATED_INCOMING_CALL,\n FAILED_INCOMING_CALL,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n CHANNELS_NOTIFY,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n] as const;\n\nexport const UA_JSSIP_EVENT_NAMES = [\n CONNECTING,\n CONNECTED,\n DISCONNECTED,\n NEW_RTC_SESSION,\n REGISTERED,\n UNREGISTERED,\n REGISTRATION_FAILED,\n NEW_MESSAGE,\n SIP_EVENT,\n] as const;\n\nexport const SESSION_SYNTHETICS_EVENT_NAMES = [\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n MUST_STOP_PRESENTATION_EVENT,\n SHARE_STATE,\n ENTER_ROOM,\n USE_LICENSE,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n CHANNELS,\n ENDED_FROM_SERVER,\n MAIN_CAM_CONTROL,\n ADMIN_START_MAIN_CAM,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n ADMIN_START_MIC,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n] as const;\n\nexport const SESSION_JSSIP_EVENT_NAMES = [\n ENDED,\n CONNECTING,\n SENDING,\n REINVITE,\n REPLACES,\n REFER,\n PROGRESS,\n ACCEPTED,\n CONFIRMED,\n PEER_CONNECTION,\n FAILED,\n MUTED,\n UNMUTED,\n NEW_DTMF,\n NEW_INFO,\n HOLD,\n UNHOLD,\n UPDATE,\n SDP,\n ICE_CANDIDATE,\n GET_USER_MEDIA_FAILED,\n PEER_CONNECTION_CREATE_OFFER_FAILED,\n PEER_CONNECTION_CREATE_ANSWER_FAILED,\n PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED,\n PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED,\n PRESENTATION_START,\n PRESENTATION_STARTED,\n PRESENTATION_END,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n] as const;\n\nexport const UA_EVENT_NAMES = [...UA_JSSIP_EVENT_NAMES, ...UA_SYNTHETICS_EVENT_NAMES];\n\nexport const SESSION_EVENT_NAMES = [\n ...SESSION_JSSIP_EVENT_NAMES,\n ...SESSION_SYNTHETICS_EVENT_NAMES,\n] as const;\n\nexport type TEventUA = (typeof UA_EVENT_NAMES)[number];\n\nexport type TEventSession = (typeof SESSION_EVENT_NAMES)[number];\n","export function resolveSipUrl(serverUrl: string): (string) => string {\n return (id: string): string => {\n return `sip:${id}@${serverUrl}`;\n };\n}\n\nconst resolveRandomInt = (min: number, max: number) => {\n return () => {\n return Math.floor(Math.random() * (max - min)) + min;\n };\n};\nexport const parseDisplayName = (displayName: string) => {\n return displayName.trim().replace(/ /g, '_');\n};\nexport const generateUserId = resolveRandomInt(100000, 99999999);\n\nexport const prepareMediaStream = (\n mediaStream?: MediaStream,\n {\n videoMode,\n audioMode,\n }: {\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n } = {},\n): MediaStream | undefined => {\n if (!mediaStream || (videoMode === 'recvonly' && audioMode === 'recvonly')) {\n return undefined;\n }\n\n const audioTracks = audioMode === 'recvonly' ? [] : mediaStream.getAudioTracks();\n const videoTracks = videoMode === 'recvonly' ? [] : mediaStream.getVideoTracks();\n const tracks = [...audioTracks, ...videoTracks];\n const newStream = new MediaStream(tracks);\n\n newStream.getTracks = () => {\n return [...newStream.getAudioTracks(), ...newStream.getVideoTracks()]; // for garante audio first order\n };\n\n return newStream;\n};\n\nexport const hasVideoTracks = (remoteTracks: MediaStreamTrack[]): boolean => {\n const isVideoTracksExists = remoteTracks.some((remoteTrack: MediaStreamTrack): boolean => {\n const { kind } = remoteTrack;\n\n return kind === 'video';\n });\n\n return isVideoTracksExists;\n};\n","export type TOnSetParameters = (parameters: RTCRtpSendParameters) => void;\nexport type TResult = { parameters: RTCRtpSendParameters; isChanged: boolean };\n\nconst MIN_SCALE_RESOLUTION_DOWN_BY = 1;\nconst resolveHasNeedToUpdateItemEncoding = (defaultValue: number | undefined) => {\n return (itemEncodingTarget: typeof defaultValue, itemEncodingCurrent?: number): boolean => {\n const isChangedDefaultScale =\n itemEncodingCurrent === undefined && itemEncodingTarget !== defaultValue;\n const isChangedPrevScale =\n itemEncodingCurrent !== undefined && itemEncodingTarget !== itemEncodingCurrent;\n\n const isNeedToChange = isChangedPrevScale || isChangedDefaultScale;\n\n return isNeedToChange;\n };\n};\n\nconst hasNeedToUpdateScaleResolutionDownBy = resolveHasNeedToUpdateItemEncoding(\n MIN_SCALE_RESOLUTION_DOWN_BY,\n);\nconst performUpdateScaleResolutionDownBy = (\n scaleResolutionDownByTarget?: number,\n scaleResolutionDownByCurrent?: number,\n): number | undefined => {\n const scaleResolutionDownByTargetParsed: number | null =\n scaleResolutionDownByTarget !== undefined\n ? Math.max(scaleResolutionDownByTarget, MIN_SCALE_RESOLUTION_DOWN_BY)\n : null;\n\n if (\n scaleResolutionDownByTargetParsed !== null &&\n hasNeedToUpdateScaleResolutionDownBy(\n scaleResolutionDownByTargetParsed,\n scaleResolutionDownByCurrent,\n )\n ) {\n return scaleResolutionDownByTargetParsed;\n }\n\n return undefined;\n};\n\nconst hasNeedToUpdateMaxBitrate = resolveHasNeedToUpdateItemEncoding(undefined);\nconst performUpdateMaxBitrate = (\n maxBitrateTarget?: number,\n maxBitrateCurrent?: number,\n): number | undefined => {\n if (hasNeedToUpdateMaxBitrate(maxBitrateTarget, maxBitrateCurrent)) {\n return maxBitrateTarget;\n }\n\n return undefined;\n};\n\nconst setEncodingsToSender = (\n sender: RTCRtpSender,\n encodingsTarget: { scaleResolutionDownBy?: number; maxBitrate?: number },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const parameters: RTCRtpSendParameters = sender.getParameters();\n\n if (!parameters.encodings || parameters.encodings.length === 0) {\n parameters.encodings = [{}];\n }\n\n const [encoding] = parameters.encodings;\n const scaleResolutionDownByCurrent = encoding.scaleResolutionDownBy;\n const scaleResolutionDownByTarget = performUpdateScaleResolutionDownBy(\n encodingsTarget.scaleResolutionDownBy,\n scaleResolutionDownByCurrent,\n );\n\n let isChanged = false;\n\n if (scaleResolutionDownByTarget !== undefined) {\n parameters.encodings[0].scaleResolutionDownBy = scaleResolutionDownByTarget;\n isChanged = true;\n }\n\n const maxBitrateCurrent = encoding.maxBitrate;\n const maxBitrateTarget = performUpdateMaxBitrate(encodingsTarget.maxBitrate, maxBitrateCurrent);\n\n if (maxBitrateTarget !== undefined) {\n parameters.encodings[0].maxBitrate = maxBitrateTarget;\n isChanged = true;\n }\n\n if (isChanged) {\n if (onSetParameters) {\n onSetParameters(parameters);\n }\n\n return sender.setParameters(parameters).then(() => {\n return { parameters, isChanged };\n });\n }\n\n return Promise.resolve({ parameters, isChanged });\n};\n\nexport default setEncodingsToSender;\n","import { CancelableRequest, isCanceledError } from '@krivega/cancelable-promise';\nimport type { UA, URI, WebSocketInterface } from '@krivega/jssip';\nimport type RTCSession from '@krivega/jssip/lib/RTCSession';\nimport type { IncomingInfoEvent, OutgoingInfoEvent } from '@krivega/jssip/lib/RTCSession';\nimport type { IncomingRequest } from '@krivega/jssip/lib/SIPMessage';\nimport type {\n IncomingRTCSessionEvent,\n RegisteredEvent,\n UnRegisteredEvent,\n} from '@krivega/jssip/lib/UA';\nimport Events from 'events-constructor';\nimport { BYE, CANCELED, REJECTED, REQUEST_TIMEOUT } from './causes';\nimport {\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n ADMIN_START_MAIN_CAM,\n ADMIN_START_MIC,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n CHANNELS,\n CHANNELS_NOTIFY,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n CONFIRMED,\n CONNECTED,\n CONNECTING,\n DECLINED_INCOMING_CALL,\n DISCONNECTED,\n ENDED,\n ENDED_FROM_SERVER,\n ENTER_ROOM,\n FAILED,\n FAILED_INCOMING_CALL,\n INCOMING_CALL,\n MAIN_CAM_CONTROL,\n MUST_STOP_PRESENTATION_EVENT,\n NEW_DTMF,\n NEW_INFO,\n NEW_RTC_SESSION,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n PEER_CONNECTION,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n REGISTERED,\n REGISTRATION_FAILED,\n SHARE_STATE,\n SIP_EVENT,\n TERMINATED_INCOMING_CALL,\n UNREGISTERED,\n USE_LICENSE,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n} from './constants';\nimport type { TEventSession, TEventUA } from './eventNames';\nimport {\n SESSION_EVENT_NAMES,\n SESSION_JSSIP_EVENT_NAMES,\n UA_EVENT_NAMES,\n UA_JSSIP_EVENT_NAMES,\n} from './eventNames';\nimport getExtraHeadersRemoteAddress from './getExtraHeadersRemoteAddress';\nimport {\n AVAILABLE_SECOND_REMOTE_STREAM,\n CONTENT_TYPE_CHANNELS,\n CONTENT_TYPE_ENTER_ROOM,\n CONTENT_TYPE_MAIN_CAM,\n CONTENT_TYPE_MEDIA_STATE,\n CONTENT_TYPE_MIC,\n CONTENT_TYPE_NOTIFY,\n CONTENT_TYPE_REFUSAL,\n CONTENT_TYPE_SHARE_STATE,\n CONTENT_TYPE_USE_LICENSE,\n HEADER_CONTENT_ENTER_ROOM,\n HEADER_CONTENT_SHARE_STATE,\n HEADER_CONTENT_TYPE_NAME,\n HEADER_CONTENT_USE_LICENSE,\n HEADER_ENABLE_MAIN_CAM,\n HEADER_INPUT_CHANNELS,\n HEADER_MAIN_CAM,\n HEADER_MAIN_CAM_RESOLUTION,\n HEADER_MAIN_CAM_STATE,\n HEADER_MEDIA_STATE,\n HEADER_MEDIA_SYNC,\n HEADER_MEDIA_TYPE,\n HEADER_MIC,\n HEADER_MIC_STATE,\n HEADER_NOTIFY,\n HEADER_OUTPUT_CHANNELS,\n HEADER_START_PRESENTATION,\n HEADER_START_PRESENTATION_P2P,\n HEADER_STOP_PRESENTATION,\n HEADER_STOP_PRESENTATION_P2P,\n MUST_STOP_PRESENTATION,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM,\n} from './headers';\nimport {\n generateUserId,\n hasVideoTracks,\n parseDisplayName,\n prepareMediaStream,\n resolveSipUrl,\n} from './utils';\nimport { hasDeclineResponseFromServer } from './utils/errors';\nimport scaleBitrate from './videoSendingBalancer/scaleBitrate';\n\nconst BUSY_HERE_STATUS_CODE = 486;\nconst REQUEST_TERMINATED_STATUS_CODE = 487;\nconst ORIGINATOR_LOCAL = 'local';\nconst ORIGINATOR_REMOTE = 'remote';\n\nexport enum EEventsMainCAM {\n PAUSE_MAIN_CAM = 'PAUSEMAINCAM',\n RESUME_MAIN_CAM = 'RESUMEMAINCAM',\n MAX_MAIN_CAM_RESOLUTION = 'MAXMAINCAMRESOLUTION',\n ADMIN_STOP_MAIN_CAM = 'ADMINSTOPMAINCAM',\n ADMIN_START_MAIN_CAM = 'ADMINSTARTMAINCAM',\n}\n\nexport enum EEventsMic {\n ADMIN_STOP_MIC = 'ADMINSTOPMIC',\n ADMIN_START_MIC = 'ADMINSTARTMIC',\n}\n\nexport enum EEventsSyncMediaState {\n ADMIN_SYNC_FORCED = '1',\n ADMIN_SYNC_NOT_FORCED = '0',\n}\n\nexport enum EUseLicense {\n AUDIO = 'AUDIO',\n VIDEO = 'VIDEO',\n AUDIOPLUSPRESENTATION = 'AUDIOPLUSPRESENTATION',\n}\n\nexport interface ICustomError extends Error {\n originator?: string;\n cause?: unknown;\n message: any;\n socket?: any;\n url?: string;\n code?: string;\n}\n\nexport const hasCanceledCallError = (error: ICustomError = new Error()): boolean => {\n const { originator, cause } = error;\n\n if (isCanceledError(error)) {\n return true;\n }\n\n if (typeof cause === 'string') {\n return (\n cause === REQUEST_TIMEOUT ||\n cause === REJECTED ||\n (originator === ORIGINATOR_LOCAL && (cause === CANCELED || cause === BYE))\n );\n }\n\n return false;\n};\n\nconst moduleName = 'SipConnector';\n\nexport type TJsSIP = {\n UA: typeof UA;\n WebSocketInterface: typeof WebSocketInterface;\n};\n\ntype TChannels = {\n inputChannels: string;\n outputChannels: string;\n};\n\ntype TMediaState = {\n cam: boolean;\n mic: boolean;\n};\n\ntype TParametersModeratorsList = {\n conference: string;\n};\n\ntype TParametersWebcast = {\n conference: string;\n type: string;\n};\n\ntype TParametersConferenceParticipantTokenIssued = {\n conference: string;\n participant: string;\n jwt: string;\n};\n\ntype TOptionsInfoMediaState = {\n noTerminateWhenError: boolean;\n};\n\nconst CMD_CHANNELS = 'channels' as const;\nconst CMD_WEBCAST_STARTED = 'WebcastStarted' as const;\nconst CMD_WEBCAST_STOPPED = 'WebcastStopped' as const;\nconst CMD_ACCOUNT_CHANGED = 'accountChanged' as const;\nconst CMD_ACCOUNT_DELETED = 'accountDeleted' as const;\nconst CMD_ADDED_TO_LIST_MODERATORS = 'addedToListModerators' as const;\nconst CMD_REMOVED_FROM_LIST_MODERATORS = 'removedFromListModerators' as const;\nconst CMD_MOVE_REQUEST_TO_CONFERENCE = 'WebcastParticipationAccepted' as const;\nconst CMD_CANCELLING_WORD_REQUEST = 'WebcastParticipationRejected' as const;\nconst CMD_MOVE_REQUEST_TO_STREAM = 'ParticipantMovedToWebcast' as const;\nconst CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED = 'ConferenceParticipantTokenIssued' as const;\n\ntype TAddedToListModeratorsInfoNotify = {\n cmd: typeof CMD_ADDED_TO_LIST_MODERATORS;\n conference: string;\n};\ntype TRemovedFromListModeratorsInfoNotify = {\n cmd: typeof CMD_REMOVED_FROM_LIST_MODERATORS;\n conference: string;\n};\ntype TMoveRequestToConferenceInfoNotify = {\n cmd: typeof CMD_MOVE_REQUEST_TO_CONFERENCE;\n body: { conference: string };\n};\ntype TCancelingWordRequestInfoNotify = {\n cmd: typeof CMD_CANCELLING_WORD_REQUEST;\n body: { conference: string };\n};\ntype TMoveRequestToStreamInfoNotify = {\n cmd: typeof CMD_MOVE_REQUEST_TO_STREAM;\n body: { conference: string };\n};\n\ntype TConferenceParticipantTokenIssued = {\n cmd: typeof CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED;\n body: { conference: string; participant: string; jwt: string };\n};\n\ntype TWebcastInfoNotify = {\n cmd: typeof CMD_WEBCAST_STARTED;\n body: { conference: string; type: string };\n};\ntype TChannelsInfoNotify = { cmd: typeof CMD_CHANNELS; input: string; output: string };\ntype TInfoNotify = Omit<\n TChannelsInfoNotify | TAddedToListModeratorsInfoNotify | TRemovedFromListModeratorsInfoNotify,\n 'cmd'\n> & { cmd: string };\n\ntype TOptionsExtraHeaders = {\n extraHeaders?: string[];\n};\n\ntype TOntrack = (track: RTCTrackEvent) => void;\n\ntype TParametersConnection = {\n displayName?: string;\n user?: string;\n password?: string;\n register?: boolean;\n sipServerUrl: string;\n sipWebSocketServerURL: string;\n remoteAddress?: string;\n sdpSemantics?: 'plan-b' | 'unified-plan';\n sessionTimers?: boolean;\n registerExpires?: number;\n connectionRecoveryMinInterval?: number;\n connectionRecoveryMaxInterval?: number;\n userAgent?: string;\n} & TOptionsExtraHeaders;\n\ntype TConnect = (parameters: TParametersConnection) => Promise<UA>;\ntype TCreateUa = (parameters: TParametersConnection) => Promise<UA>;\ntype TStart = () => Promise<UA>;\ntype TSet = ({\n displayName,\n password,\n}: {\n displayName?: string;\n password?: string;\n}) => Promise<boolean>;\n\ntype TDegradationPreference = 'maintain-framerate' | 'maintain-resolution' | 'balanced';\ntype TCall = ({\n number,\n mediaStream,\n extraHeaders,\n ontrack,\n iceServers,\n videoMode,\n audioMode,\n offerToReceiveAudio,\n offerToReceiveVideo,\n degradationPreference,\n}: {\n number: string;\n mediaStream?: MediaStream;\n extraHeaders?: TOptionsExtraHeaders['extraHeaders'];\n ontrack?: TOntrack;\n iceServers?: RTCIceServer[];\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n offerToReceiveAudio?: boolean;\n offerToReceiveVideo?: boolean;\n degradationPreference?: TDegradationPreference;\n}) => Promise<RTCPeerConnection>;\n\ntype TDisconnect = () => Promise<void>;\n\ntype TParametersAnswerToIncomingCall = {\n mediaStream: MediaStream;\n extraHeaders?: TOptionsExtraHeaders['extraHeaders'];\n ontrack?: TOntrack;\n iceServers?: RTCIceServer[];\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n degradationPreference?: TDegradationPreference;\n};\n\ntype TAnswerToIncomingCall = (\n parameters: TParametersAnswerToIncomingCall,\n) => Promise<RTCPeerConnection>;\n\ntype TSendDTMF = (tone: number | string) => Promise<void>;\n\ntype THangUp = () => Promise<void>;\n\nexport default class SipConnector {\n private _isRegisterConfig = false;\n\n private _connectionConfiguration: {\n sipServerUrl?: string;\n displayName?: string;\n register?: boolean;\n user?: string;\n password?: string;\n number?: string;\n answer?: boolean;\n } = {};\n\n private _remoteStreams: { [key: string]: MediaStream } = {};\n\n private JsSIP: TJsSIP;\n\n private _sessionEvents: Events<typeof SESSION_EVENT_NAMES>;\n\n private _uaEvents: Events<typeof UA_EVENT_NAMES>;\n\n private _cancelableConnect: CancelableRequest<Parameters<TConnect>[0], ReturnType<TConnect>>;\n\n private _cancelableCreateUa: CancelableRequest<Parameters<TCreateUa>[0], ReturnType<TCreateUa>>;\n\n private _cancelableDisconnect: CancelableRequest<void, ReturnType<TDisconnect>>;\n\n private _cancelableSet: CancelableRequest<Parameters<TSet>[0], ReturnType<TSet>>;\n\n private _cancelableCall: CancelableRequest<Parameters<TCall>[0], ReturnType<TCall>>;\n\n private _cancelableAnswer: CancelableRequest<\n Parameters<TAnswerToIncomingCall>[0],\n ReturnType<TAnswerToIncomingCall>\n >;\n\n private _cancelableSendDTMF: CancelableRequest<Parameters<TSendDTMF>[0], ReturnType<TSendDTMF>>;\n\n private getSipServerUrl: (id: string) => string = (id: string) => {\n return id;\n };\n\n promisePendingStartPresentation?: Promise<MediaStream>;\n promisePendingStopPresentation?: Promise<void | MediaStream>;\n\n ua?: UA;\n\n session?: RTCSession;\n\n incomingSession?: RTCSession;\n\n _streamPresentationCurrent?: MediaStream;\n\n socket?: WebSocketInterface;\n\n constructor({ JsSIP }: { JsSIP: TJsSIP }) {\n this.JsSIP = JsSIP;\n\n this._sessionEvents = new Events<typeof SESSION_EVENT_NAMES>(SESSION_EVENT_NAMES);\n this._uaEvents = new Events<typeof UA_EVENT_NAMES>(UA_EVENT_NAMES);\n\n this._cancelableConnect = new CancelableRequest<Parameters<TConnect>[0], ReturnType<TConnect>>(\n this._connect,\n {\n moduleName,\n afterCancelRequest: () => {\n this._cancelableCreateUa.cancelRequest();\n this._cancelableDisconnect.cancelRequest();\n },\n },\n );\n\n this._cancelableCreateUa = new CancelableRequest<\n Parameters<TCreateUa>[0],\n ReturnType<TCreateUa>\n >(this._createUa, { moduleName });\n\n this._cancelableDisconnect = new CancelableRequest<void, ReturnType<TDisconnect>>(\n this._disconnect,\n { moduleName },\n );\n\n this._cancelableSet = new CancelableRequest<Parameters<TSet>[0], ReturnType<TSet>>(this._set, {\n moduleName,\n });\n\n this._cancelableCall = new CancelableRequest<Parameters<TCall>[0], ReturnType<TCall>>(\n this._call,\n { moduleName },\n );\n\n this._cancelableAnswer = new CancelableRequest<\n Parameters<TAnswerToIncomingCall>[0],\n ReturnType<TAnswerToIncomingCall>\n >(this._answer, { moduleName });\n\n this._cancelableSendDTMF = new CancelableRequest<\n Parameters<TSendDTMF>[0],\n ReturnType<TSendDTMF>\n >(this._sendDTMF, { moduleName });\n\n this.onSession(SHARE_STATE, this._handleShareState);\n this.onSession(NEW_INFO, this._handleNewInfo);\n this.on(SIP_EVENT, this._handleSipEvent);\n\n this.onSession(FAILED, this._handleEnded);\n this.onSession(ENDED, this._handleEnded);\n }\n\n connect: TConnect = (data) => {\n this._cancelRequests();\n\n return this._cancelableConnect.request(data);\n };\n\n createUa: TCreateUa = (data) => {\n return this._cancelableCreateUa.request(data);\n };\n\n set: TSet = (data) => {\n return this._cancelableSet.request(data);\n };\n\n call: TCall = (data) => {\n return this._cancelableCall.request(data);\n };\n\n disconnect: TDisconnect = () => {\n this._cancelRequests();\n\n return this._disconnectWithoutCancelRequests();\n };\n\n answerToIncomingCall: TAnswerToIncomingCall = (data) => {\n return this._cancelableAnswer.request(data);\n };\n\n sendDTMF: TSendDTMF = (tone) => {\n return this._cancelableSendDTMF.request(tone);\n };\n\n hangUp: THangUp = () => {\n this._cancelRequests();\n\n return this._hangUpWithoutCancelRequests();\n };\n\n register(): Promise<RegisteredEvent> {\n return new Promise((resolve, reject) => {\n if (this.isRegisterConfig) {\n this.ua!.on(REGISTERED, resolve);\n this.ua!.on(REGISTRATION_FAILED, reject);\n this.ua!.register();\n } else {\n reject(new Error('Config is not registered'));\n }\n });\n }\n\n unregister(): Promise<UnRegisteredEvent> {\n return new Promise((resolve, reject) => {\n if (this.isRegistered) {\n this.ua!.on(UNREGISTERED, resolve);\n this.ua!.unregister();\n } else {\n reject(new Error('ua is not registered'));\n }\n });\n }\n\n tryRegister = () => {\n if (!this.isRegisterConfig) {\n return Promise.reject(new Error('Config is not registered'));\n }\n\n this._uaEvents.trigger(CONNECTING, undefined);\n\n return this.unregister()\n .finally(() => {\n return this.register();\n })\n .finally(() => {\n return undefined;\n });\n };\n\n sendOptions(target: string | URI, body?: string, extraHeaders?: string[]): Promise<void> {\n if (!this.ua) {\n return Promise.reject(new Error('is not connected'));\n }\n\n return new Promise((resolve, reject) => {\n try {\n this.ua.sendOptions(target, body, {\n extraHeaders,\n eventHandlers: {\n succeeded: () => {\n resolve();\n },\n failed: (error) => {\n reject(error);\n },\n },\n });\n } catch (error) {\n reject(error);\n }\n });\n }\n\n ping(body?: string, extraHeaders?: string[]): Promise<void> {\n if (!this.ua || !this.ua.configuration || !this.ua.configuration.uri) {\n return Promise.reject(new Error('is not connected'));\n }\n\n const target = this.ua.configuration.uri;\n\n return this.sendOptions(target, body, extraHeaders);\n }\n\n replaceMediaStream(\n mediaStream: MediaStream,\n options?: {\n deleteExisting: boolean;\n addMissing: boolean;\n forceRenegotiation: boolean;\n degradationPreference?: TDegradationPreference;\n },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this.session.replaceMediaStream(mediaStream, options);\n }\n\n declineToIncomingCall = ({ statusCode = REQUEST_TERMINATED_STATUS_CODE } = {}) => {\n return new Promise((resolve, reject) => {\n if (!this.isAvailableIncomingCall) {\n reject(new Error('no incomingSession'));\n\n return undefined;\n }\n\n const incomingSession = this!.incomingSession as RTCSession;\n const callerData = this.remoteCallerData;\n\n this._cancelableCall.cancelRequest();\n this._cancelableAnswer.cancelRequest();\n\n this.removeIncomingSession();\n this._uaEvents.trigger(DECLINED_INCOMING_CALL, callerData);\n resolve(incomingSession.terminate({ status_code: statusCode }));\n\n return undefined;\n });\n };\n\n busyIncomingCall = () => {\n return this.declineToIncomingCall({ statusCode: BUSY_HERE_STATUS_CODE });\n };\n\n removeIncomingSession = () => {\n delete this.incomingSession;\n };\n\n askPermissionToEnableCam(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const extraHeaders = [HEADER_ENABLE_MAIN_CAM];\n\n return this.session\n .sendInfo(CONTENT_TYPE_MAIN_CAM, undefined, {\n ...options,\n extraHeaders,\n })\n .catch((error) => {\n if (hasDeclineResponseFromServer(error)) {\n throw error;\n }\n\n return;\n });\n }\n\n get isPendingPresentation(): boolean {\n return !!this.promisePendingStartPresentation || !!this.promisePendingStopPresentation;\n }\n\n private _sendPresentation(\n session: RTCSession,\n stream: MediaStream,\n {\n maxBitrate,\n degradationPreference,\n isNeedReinvite = true,\n isP2P = false,\n }: {\n isNeedReinvite?: boolean;\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n },\n ) {\n const streamPresentationCurrent = prepareMediaStream(stream) as MediaStream;\n\n this._streamPresentationCurrent = streamPresentationCurrent;\n\n const preparatoryHeaders = isP2P\n ? [HEADER_START_PRESENTATION_P2P]\n : [HEADER_START_PRESENTATION];\n\n const result = session\n .sendInfo(CONTENT_TYPE_SHARE_STATE, undefined, {\n extraHeaders: preparatoryHeaders,\n })\n .then(() => {\n return session.startPresentation(\n streamPresentationCurrent,\n isNeedReinvite,\n degradationPreference,\n );\n })\n // @ts-ignore\n .then(() => {\n const { connection } = this;\n\n if (!connection || maxBitrate === undefined) {\n return undefined;\n }\n\n const senders = connection.getSenders();\n\n return scaleBitrate(senders, stream, maxBitrate);\n })\n .then(() => {\n return stream;\n })\n .catch((error) => {\n this._sessionEvents.trigger(PRESENTATION_FAILED, error);\n\n throw error;\n });\n\n this.promisePendingStartPresentation = result;\n\n return result.finally(() => {\n this.promisePendingStartPresentation = undefined;\n });\n }\n\n startPresentation(\n stream: MediaStream,\n {\n isNeedReinvite = true,\n isP2P = false,\n maxBitrate,\n degradationPreference,\n }: {\n isNeedReinvite?: boolean;\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n } = {},\n ): Promise<void | MediaStream> {\n const session = this.establishedSession;\n\n if (!session) {\n return Promise.reject(new Error('No session established'));\n }\n\n if (this._streamPresentationCurrent) {\n return Promise.reject(new Error('Presentation is already started'));\n }\n\n return this._sendPresentation(session, stream, {\n isNeedReinvite,\n isP2P,\n maxBitrate,\n degradationPreference,\n });\n }\n\n stopPresentation({\n isP2P = false,\n }: {\n isP2P?: boolean;\n } = {}): Promise<MediaStream | void> {\n const streamPresentationPrev = this._streamPresentationCurrent;\n let result: Promise<MediaStream | void> =\n this.promisePendingStartPresentation || Promise.resolve();\n\n const preparatoryHeaders = isP2P ? [HEADER_STOP_PRESENTATION_P2P] : [HEADER_STOP_PRESENTATION];\n\n const session = this.establishedSession;\n\n if (session && streamPresentationPrev) {\n result = result\n .then(() => {\n return session.sendInfo(CONTENT_TYPE_SHARE_STATE, undefined, {\n extraHeaders: preparatoryHeaders,\n });\n })\n .then(() => {\n return session.stopPresentation(streamPresentationPrev);\n })\n .catch((error) => {\n this._sessionEvents.trigger(PRESENTATION_FAILED, error);\n\n throw error;\n });\n }\n\n if (!session && streamPresentationPrev) {\n this._sessionEvents.trigger(PRESENTATION_ENDED, streamPresentationPrev);\n }\n\n this.promisePendingStopPresentation = result;\n\n return result.finally(() => {\n this._resetPresentation();\n });\n }\n\n async updatePresentation(\n stream: MediaStream,\n {\n isP2P = false,\n maxBitrate,\n degradationPreference,\n }: {\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n } = {},\n ): Promise<void | MediaStream> {\n const session = this.establishedSession;\n\n if (!session) {\n return Promise.reject(new Error('No session established'));\n }\n\n if (!this._streamPresentationCurrent) {\n return Promise.reject(new Error('Presentation has not started yet'));\n }\n\n if (this.promisePendingStartPresentation) {\n await this.promisePendingStartPresentation;\n }\n\n return this._sendPresentation(session, stream, {\n isP2P,\n maxBitrate,\n degradationPreference,\n isNeedReinvite: false,\n });\n }\n\n _resetPresentation(): void {\n delete this._streamPresentationCurrent;\n\n this.promisePendingStartPresentation = undefined;\n this.promisePendingStopPresentation = undefined;\n }\n\n handleNewRTCSession = ({ originator, session }: IncomingRTCSessionEvent) => {\n if (originator === ORIGINATOR_REMOTE) {\n this.incomingSession = session;\n\n const callerData = this.remoteCallerData;\n\n session.on(FAILED, ({ originator }) => {\n this.removeIncomingSession();\n\n if (originator !== ORIGINATOR_LOCAL) {\n this._uaEvents.trigger(FAILED_INCOMING_CALL, callerData);\n } else {\n this._uaEvents.trigger(TERMINATED_INCOMING_CALL, callerData);\n }\n });\n\n this._uaEvents.trigger(INCOMING_CALL, callerData);\n }\n };\n\n on(eventName: TEventUA, handler) {\n return this._uaEvents.on(eventName, handler);\n }\n\n once(eventName: TEventUA, handler) {\n return this._uaEvents.once(eventName, handler);\n }\n\n onceRace(eventNames: TEventUA[], handler) {\n return this._uaEvents.onceRace(eventNames, handler);\n }\n\n wait(eventName: TEventUA): Promise<any> {\n return this._uaEvents.wait(eventName);\n }\n\n off(eventName: TEventUA, handler) {\n this._uaEvents.off(eventName, handler);\n }\n\n onSession(eventName: TEventSession, handler) {\n return this._sessionEvents.on(eventName, handler);\n }\n\n onceSession(eventName: TEventSession, handler) {\n return this._sessionEvents.once(eventName, handler);\n }\n\n onceRaceSession(eventNames: TEventSession[], handler) {\n return this._sessionEvents.onceRace(eventNames, handler);\n }\n\n waitSession(eventName: TEventSession): Promise<any> {\n return this._sessionEvents.wait(eventName);\n }\n\n offSession(eventName: TEventSession, handler) {\n this._sessionEvents.off(eventName, handler);\n }\n\n isConfigured() {\n return !!this.ua;\n }\n\n getConnectionConfiguration() {\n return { ...this._connectionConfiguration };\n }\n\n getRemoteStreams(): MediaStream[] | undefined {\n if (!this.connection) {\n return undefined;\n }\n\n const receivers = this.connection.getReceivers();\n const remoteTracks = receivers.map(({ track }) => {\n return track;\n });\n\n if (hasVideoTracks(remoteTracks)) {\n return this._generateStreams(remoteTracks);\n }\n\n return this._generateAudioStreams(remoteTracks);\n }\n\n get connection(): RTCPeerConnection | undefined {\n const connection = this?.session?.connection;\n\n return connection;\n }\n\n get remoteCallerData() {\n return {\n // eslint-disable-next-line camelcase\n displayName: this?.incomingSession?.remote_identity?.display_name,\n // eslint-disable-next-line camelcase\n host: this?.incomingSession?.remote_identity?.uri.host,\n // eslint-disable-next-line camelcase\n incomingNumber: this?.incomingSession?.remote_identity?.uri.user,\n session: this?.incomingSession,\n };\n }\n\n get requested() {\n return (\n this._cancelableConnect.requested ||\n this._cancelableCreateUa.requested ||\n this._cancelableCall.requested ||\n this._cancelableAnswer.requested\n );\n }\n\n get establishedSession(): RTCSession | undefined {\n return this.session && this.session.isEstablished() ? this.session : undefined;\n }\n\n get isRegistered() {\n return !!this.ua && this.ua.isRegistered();\n }\n\n get isRegisterConfig() {\n return !!this.ua && this._isRegisterConfig;\n }\n\n get isCallActive() {\n return !!(this.ua && this.session);\n }\n\n get isAvailableIncomingCall() {\n return !!this.incomingSession;\n }\n\n _connect: TConnect = (params) => {\n return this.createUa(params).then(() => {\n return this._start();\n });\n };\n\n _createUa: TCreateUa = async ({\n displayName = '',\n user,\n password,\n register = false,\n sipServerUrl,\n sipWebSocketServerURL,\n remoteAddress,\n extraHeaders = [],\n sdpSemantics = 'plan-b',\n sessionTimers = false,\n registerExpires = 60 * 5, // 5 minutes in sec\n connectionRecoveryMinInterval = 2,\n connectionRecoveryMaxInterval = 6,\n userAgent,\n }) => {\n if (!sipServerUrl) {\n throw new Error('sipServerUrl is required');\n }\n\n if (!sipWebSocketServerURL) {\n throw new Error('sipWebSocketServerURL is required');\n }\n\n if (register && !user) {\n throw new Error('user is required for authorized connection');\n }\n\n if (register && !password) {\n throw new Error('password is required for authorized connection');\n }\n\n this._connectionConfiguration = {\n sipServerUrl,\n displayName,\n register,\n user,\n password,\n };\n\n this._init({ sipServerUrl, sipWebSocketServerURL });\n\n let authorizationUser;\n\n if (register && user) {\n authorizationUser = user.trim();\n } else {\n authorizationUser = generateUserId();\n }\n\n const configuration = {\n password,\n register,\n display_name: parseDisplayName(displayName),\n user_agent: userAgent,\n sdp_semantics: sdpSemantics,\n sockets: [this.socket as WebSocketInterface],\n uri: this.getSipServerUrl(authorizationUser),\n session_timers: sessionTimers,\n register_expires: registerExpires,\n\n connection_recovery_min_interval: connectionRecoveryMinInterval,\n connection_recovery_max_interval: connectionRecoveryMaxInterval,\n };\n\n if (this.ua) {\n await this._disconnectWithoutCancelRequests();\n }\n\n this._isRegisterConfig = !!configuration.register;\n this.ua = new this.JsSIP.UA(configuration);\n\n this._uaEvents.eachTriggers((trigger, eventName) => {\n const uaJsSipEvent = UA_JSSIP_EVENT_NAMES.find((jsSipEvent) => {\n return jsSipEvent === eventName;\n });\n\n if (uaJsSipEvent) {\n this.ua!.on(uaJsSipEvent, trigger);\n }\n });\n\n const extraHeadersRemoteAddress = getExtraHeadersRemoteAddress(remoteAddress);\n const extraHeadersBase = [...extraHeadersRemoteAddress, ...extraHeaders];\n\n this.ua!.registrator().setExtraHeaders(extraHeadersBase);\n\n return this.ua;\n };\n\n _init({ sipServerUrl, sipWebSocketServerURL }) {\n this.getSipServerUrl = resolveSipUrl(sipServerUrl);\n this.socket = new this.JsSIP.WebSocketInterface(sipWebSocketServerURL);\n }\n\n _start: TStart = () => {\n return new Promise((resolve, reject) => {\n const resolveUa = () => {\n removeEventListeners();\n resolve(this.ua as UA);\n };\n const rejectError = (error) => {\n removeEventListeners();\n reject(error);\n };\n const addEventListeners = () => {\n if (this.isRegisterConfig) {\n this.on(REGISTERED, resolveUa);\n this.on(REGISTRATION_FAILED, rejectError);\n } else {\n this.on(CONNECTED, resolveUa);\n }\n\n this.on(DISCONNECTED, rejectError);\n };\n const removeEventListeners = () => {\n this.off(REGISTERED, resolveUa);\n this.off(REGISTRATION_FAILED, rejectError);\n this.off(CONNECTED, resolveUa);\n this.off(DISCONNECTED, rejectError);\n };\n\n addEventListeners();\n this.on(NEW_RTC_SESSION, this.handleNewRTCSession);\n\n this.ua!.start();\n });\n };\n\n _set: TSet = ({ displayName, password }) => {\n return new Promise((resolve, reject) => {\n let changedDisplayName = false;\n let changedPassword = false;\n\n if (displayName !== undefined && displayName !== this._connectionConfiguration.displayName) {\n changedDisplayName = this.ua!.set('display_name', parseDisplayName(displayName));\n this._connectionConfiguration.displayName = displayName;\n }\n\n if (password !== undefined && password !== this._connectionConfiguration.password) {\n changedPassword = this.ua!.set('password', password);\n this._connectionConfiguration.password = password;\n }\n\n const changedSome = changedDisplayName || changedPassword;\n\n if (changedPassword && this.isRegisterConfig) {\n this.register()\n .then(() => {\n return resolve(changedSome);\n })\n .catch(reject);\n } else if (changedSome) {\n resolve(changedSome);\n } else {\n reject(changedSome);\n }\n });\n };\n\n _disconnectWithoutCancelRequests: TDisconnect = () => {\n return this._cancelableDisconnect.request();\n };\n\n _disconnect = async () => {\n this.off(NEW_RTC_SESSION, this.handleNewRTCSession);\n\n const disconnectedPromise = new Promise<void>((resolve) => {\n this.once(DISCONNECTED, () => {\n delete this.ua;\n resolve();\n });\n });\n\n if (this.ua) {\n await this._hangUpWithoutCancelRequests();\n\n if (this.ua) {\n this.ua.stop();\n } else {\n this._uaEvents.trigger(DISCONNECTED, undefined);\n }\n } else {\n this._uaEvents.trigger(DISCONNECTED, undefined);\n }\n\n return disconnectedPromise;\n };\n\n _call: TCall = ({\n number,\n mediaStream,\n extraHeaders = [],\n ontrack,\n iceServers,\n videoMode,\n audioMode,\n degradationPreference,\n offerToReceiveAudio = true,\n offerToReceiveVideo = true,\n }) => {\n return new Promise((resolve, reject) => {\n this._connectionConfiguration.number = number;\n this._connectionConfiguration.answer = false;\n this._handleCall({ ontrack }).then(resolve).catch(reject);\n\n this.session = this.ua!.call(this.getSipServerUrl(number), {\n extraHeaders,\n mediaStream: prepareMediaStream(mediaStream, {\n videoMode,\n audioMode,\n }),\n eventHandlers: this._sessionEvents.triggers,\n videoMode,\n audioMode,\n degradationPreference,\n pcConfig: {\n iceServers,\n },\n rtcOfferConstraints: {\n offerToReceiveAudio,\n offerToReceiveVideo,\n },\n });\n });\n };\n\n _answer: TAnswerToIncomingCall = ({\n mediaStream,\n ontrack,\n extraHeaders = [],\n iceServers,\n videoMode,\n audioMode,\n degradationPreference,\n }): Promise<RTCPeerConnection> => {\n return new Promise((resolve, reject) => {\n if (!this.isAvailableIncomingCall) {\n reject(new Error('no incomingSession'));\n\n return undefined;\n }\n\n this.session = this.incomingSession;\n this.removeIncomingSession();\n\n const session = this.session;\n\n if (!session) {\n reject(new Error('No session established'));\n\n return;\n }\n\n this._sessionEvents.eachTriggers((trigger, eventName) => {\n const sessionJsSipEvent = SESSION_JSSIP_EVENT_NAMES.find((jsSipEvent) => {\n return jsSipEvent === eventName;\n });\n\n if (sessionJsSipEvent) {\n session.on(sessionJsSipEvent, trigger);\n }\n });\n\n this._connectionConfiguration.answer = true;\n this._connectionConfiguration.number = session.remote_identity.uri.user;\n this._handleCall({ ontrack }).then(resolve).catch(reject);\n\n const preparedMediaStream = prepareMediaStream(mediaStream, {\n videoMode,\n audioMode,\n });\n\n session.answer({\n extraHeaders,\n videoMode,\n audioMode,\n degradationPreference,\n mediaStream: preparedMediaStream,\n pcConfig: {\n iceServers,\n },\n });\n\n return undefined;\n });\n };\n\n _handleCall = ({ ontrack }: { ontrack?: TOntrack }): Promise<RTCPeerConnection> => {\n return new Promise((resolve, reject) => {\n const addStartedEventListeners = () => {\n this.onSession(PEER_CONNECTION, handlePeerConnection);\n this.onSession(CONFIRMED, handleConfirmed);\n };\n const removeStartedEventListeners = () => {\n this.offSession(PEER_CONNECTION, handlePeerConnection);\n this.offSession(CONFIRMED, handleConfirmed);\n };\n const addEndedEventListeners = () => {\n this.onSession(FAILED, handleEnded);\n this.onSession(ENDED, handleEnded);\n };\n const removeEndedEventListeners = () => {\n this.offSession(FAILED, handleEnded);\n this.offSession(ENDED, handleEnded);\n };\n const handleEnded = (error: ICustomError) => {\n removeStartedEventListeners();\n removeEndedEventListeners();\n reject(error);\n };\n\n let savedPeerconnection: RTCPeerConnection;\n\n const handlePeerConnection = ({ peerconnection }) => {\n savedPeerconnection = peerconnection;\n\n savedPeerconnection.ontrack = (track) => {\n this._sessionEvents.trigger(PEER_CONNECTION_ONTRACK, savedPeerconnection);\n\n if (ontrack) {\n ontrack(track);\n }\n };\n };\n const handleConfirmed = () => {\n if (savedPeerconnection) {\n this._sessionEvents.trigger(PEER_CONNECTION_CONFIRMED, savedPeerconnection);\n }\n\n removeStartedEventListeners();\n removeEndedEventListeners();\n resolve(savedPeerconnection);\n };\n\n addStartedEventListeners();\n addEndedEventListeners();\n });\n };\n\n _restoreSession: () => void = () => {\n this._resetPresentation();\n\n delete this._connectionConfiguration.number;\n delete this.session;\n this._remoteStreams = {};\n };\n\n _sendDTMF: TSendDTMF = (tone) => {\n return new Promise<void>((resolve, reject) => {\n const session = this.session;\n\n if (!session) {\n reject(new Error('No session established'));\n\n return;\n }\n\n this.onceSession(NEW_DTMF, ({ originator }) => {\n if (originator === ORIGINATOR_LOCAL) {\n resolve();\n }\n });\n\n session.sendDTMF(tone, {\n duration: 120,\n interToneGap: 600,\n });\n });\n };\n\n _generateStream(videoTrack: MediaStreamTrack, audioTrack?: MediaStreamTrack): MediaStream {\n const id = videoTrack.id;\n\n const remoteStream: MediaStream = this._remoteStreams[id] || new MediaStream();\n\n if (audioTrack) {\n remoteStream.addTrack(audioTrack);\n }\n\n remoteStream.addTrack(videoTrack);\n this._remoteStreams[id] = remoteStream;\n\n return remoteStream;\n }\n\n _generateAudioStream(audioTrack: MediaStreamTrack): MediaStream {\n const id = audioTrack.id;\n\n const remoteStream = this._remoteStreams[id] || new MediaStream();\n\n remoteStream.addTrack(audioTrack);\n\n this._remoteStreams[id] = remoteStream;\n\n return remoteStream;\n }\n\n _generateStreams(remoteTracks: MediaStreamTrack[]): MediaStream[] {\n const remoteStreams: MediaStream[] = [];\n\n remoteTracks.forEach((track, index) => {\n if (track.kind === 'audio') {\n return;\n }\n\n const videoTrack = track;\n const prevTrack = remoteTracks[index - 1];\n let audioTrack;\n\n if (prevTrack && prevTrack.kind === 'audio') {\n audioTrack = prevTrack;\n }\n\n const remoteStream = this._generateStream(videoTrack, audioTrack);\n\n remoteStreams.push(remoteStream);\n }, []);\n\n return remoteStreams;\n }\n\n _generateAudioStreams(remoteTracks: MediaStreamTrack[]): MediaStream[] {\n const remoteStreams: MediaStream[] = remoteTracks.map((remoteTrack) => {\n return this._generateAudioStream(remoteTrack);\n });\n\n return remoteStreams;\n }\n\n _hangUpWithoutCancelRequests: THangUp = async () => {\n if (this.ua && this.session) {\n const { session } = this;\n\n if (this._streamPresentationCurrent) {\n await this.stopPresentation();\n }\n\n this._restoreSession();\n\n if (!session.isEnded()) {\n session.terminate();\n }\n }\n };\n\n _cancelRequests() {\n this._cancelActionsRequests();\n this._cancelCallRequests();\n this._cancelConnectRequests();\n }\n\n _cancelConnectRequests() {\n this._cancelableConnect.cancelRequest();\n }\n\n _cancelCallRequests() {\n this._cancelableCall.cancelRequest();\n this._cancelableAnswer.cancelRequest();\n }\n\n _cancelActionsRequests() {\n this._cancelableAnswer.cancelRequest();\n this._cancelableSendDTMF.cancelRequest();\n }\n\n _handleShareState = (eventName) => {\n switch (eventName) {\n case AVAILABLE_SECOND_REMOTE_STREAM:\n this._sessionEvents.trigger(AVAILABLE_SECOND_REMOTE_STREAM_EVENT, undefined);\n break;\n case NOT_AVAILABLE_SECOND_REMOTE_STREAM:\n this._sessionEvents.trigger(NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT, undefined);\n break;\n case MUST_STOP_PRESENTATION:\n this._sessionEvents.trigger(MUST_STOP_PRESENTATION_EVENT, undefined);\n break;\n\n default:\n break;\n }\n };\n\n _maybeTriggerChannels = (request: IncomingRequest) => {\n const inputChannels = request.getHeader(HEADER_INPUT_CHANNELS);\n const outputChannels = request.getHeader(HEADER_OUTPUT_CHANNELS);\n\n if (inputChannels && outputChannels) {\n const headersChannels: TChannels = {\n inputChannels,\n outputChannels,\n };\n\n this._sessionEvents.trigger(CHANNELS, headersChannels);\n }\n };\n\n _handleNotify = (header: TInfoNotify) => {\n if (header.cmd === CMD_CHANNELS) {\n const channelsInfo = header as TChannelsInfoNotify;\n\n this._triggerChannelsNotify(channelsInfo);\n } else if (header.cmd === CMD_WEBCAST_STARTED) {\n const webcastInfo = header as TWebcastInfoNotify;\n\n this._triggerWebcastStartedNotify(webcastInfo);\n } else if (header.cmd === CMD_WEBCAST_STOPPED) {\n const webcastInfo = header as TWebcastInfoNotify;\n\n this._triggerWebcastStoppedNotify(webcastInfo);\n } else if (header.cmd === CMD_ADDED_TO_LIST_MODERATORS) {\n const data = header as TAddedToListModeratorsInfoNotify;\n\n this._triggerAddedToListModeratorsNotify(data);\n } else if (header.cmd === CMD_REMOVED_FROM_LIST_MODERATORS) {\n const data = header as TRemovedFromListModeratorsInfoNotify;\n\n this._triggerRemovedFromListModeratorsNotify(data);\n } else if (header.cmd === CMD_MOVE_REQUEST_TO_CONFERENCE) {\n const data = header as TMoveRequestToConferenceInfoNotify;\n\n this._triggerParticipantMoveRequestToConference(data);\n } else if (header.cmd === CMD_CANCELLING_WORD_REQUEST) {\n const data = header as TCancelingWordRequestInfoNotify;\n\n this._triggerParticipantCancelingWordRequest(data);\n } else if (header.cmd === CMD_MOVE_REQUEST_TO_STREAM) {\n const data = header as TMoveRequestToStreamInfoNotify;\n\n this._triggerParticipantMoveRequestToStream(data);\n } else if (header.cmd === CMD_ACCOUNT_CHANGED) {\n this._triggerAccountChangedNotify();\n } else if (header.cmd === CMD_ACCOUNT_DELETED) {\n this._triggerAccountDeletedNotify();\n } else if (header.cmd === CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED) {\n const data = header as TConferenceParticipantTokenIssued;\n\n this._triggerConferenceParticipantTokenIssued(data);\n }\n };\n\n _triggerRemovedFromListModeratorsNotify = ({\n conference,\n }: TRemovedFromListModeratorsInfoNotify) => {\n const headersParametersModeratorsList: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n headersParametersModeratorsList,\n );\n };\n\n _triggerAddedToListModeratorsNotify = ({ conference }: TAddedToListModeratorsInfoNotify) => {\n const headersParametersModeratorsList: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_ADDED_TO_LIST_MODERATORS, headersParametersModeratorsList);\n };\n\n _triggerWebcastStartedNotify = ({ body: { conference, type } }: TWebcastInfoNotify) => {\n const headersParametersWebcast: TParametersWebcast = {\n conference,\n type,\n };\n\n this._uaEvents.trigger(WEBCAST_STARTED, headersParametersWebcast);\n };\n\n _triggerWebcastStoppedNotify = ({ body: { conference, type } }: TWebcastInfoNotify) => {\n const headersParametersWebcast: TParametersWebcast = {\n conference,\n type,\n };\n\n this._uaEvents.trigger(WEBCAST_STOPPED, headersParametersWebcast);\n };\n\n _triggerAccountChangedNotify = () => {\n this._uaEvents.trigger(ACCOUNT_CHANGED, undefined);\n };\n\n _triggerAccountDeletedNotify = () => {\n this._uaEvents.trigger(ACCOUNT_DELETED, undefined);\n };\n\n _triggerConferenceParticipantTokenIssued = ({\n body: { conference, participant, jwt },\n }: TConferenceParticipantTokenIssued) => {\n const headersConferenceParticipantTokenIssued: TParametersConferenceParticipantTokenIssued = {\n conference,\n participant,\n jwt,\n };\n\n this._uaEvents.trigger(\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n headersConferenceParticipantTokenIssued,\n );\n };\n\n _triggerChannelsNotify = (channelsInfo: TChannelsInfoNotify) => {\n const inputChannels = channelsInfo.input;\n const outputChannels = channelsInfo.output;\n\n const data: TChannels = {\n inputChannels,\n outputChannels,\n };\n\n this._uaEvents.trigger(CHANNELS_NOTIFY, data);\n };\n\n _triggerParticipantMoveRequestToConference = ({\n body: { conference },\n }: TMoveRequestToConferenceInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE, data);\n };\n\n _triggerParticipantCancelingWordRequest = ({\n body: { conference },\n }: TCancelingWordRequestInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_CANCELLING_WORD_REQUEST, data);\n };\n\n _triggerParticipantMoveRequestToStream = ({\n body: { conference },\n }: TMoveRequestToStreamInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_MOVE_REQUEST_TO_STREAM, data);\n };\n\n _triggerEnterRoom = (request: IncomingRequest) => {\n const room = request.getHeader(HEADER_CONTENT_ENTER_ROOM);\n\n this._sessionEvents.trigger(ENTER_ROOM, room);\n };\n\n _triggerShareState = (request: IncomingRequest) => {\n const eventName = request.getHeader(HEADER_CONTENT_SHARE_STATE);\n\n this._sessionEvents.trigger(SHARE_STATE, eventName);\n };\n\n _triggerMainCamControl = (request: IncomingRequest) => {\n const mainCam = request.getHeader(HEADER_MAIN_CAM) as EEventsMainCAM;\n\n const syncState = request.getHeader(HEADER_MEDIA_SYNC);\n const isSyncForced = syncState === EEventsSyncMediaState.ADMIN_SYNC_FORCED ? true : false;\n\n if (mainCam === EEventsMainCAM.ADMIN_START_MAIN_CAM) {\n this._sessionEvents.trigger(ADMIN_START_MAIN_CAM, { isSyncForced });\n } else if (mainCam === EEventsMainCAM.ADMIN_STOP_MAIN_CAM) {\n this._sessionEvents.trigger(ADMIN_STOP_MAIN_CAM, { isSyncForced });\n } else if (\n (mainCam === EEventsMainCAM.RESUME_MAIN_CAM || mainCam === EEventsMainCAM.PAUSE_MAIN_CAM) &&\n !!syncState\n ) {\n this._sessionEvents.trigger(ADMIN_FORCE_SYNC_MEDIA_STATE, { isSyncForced });\n } else {\n const resolutionMainCam = request.getHeader(HEADER_MAIN_CAM_RESOLUTION);\n\n this._sessionEvents.trigger(MAIN_CAM_CONTROL, {\n mainCam,\n resolutionMainCam,\n });\n }\n };\n\n _triggerMicControl = (request: IncomingRequest) => {\n const mic = request.getHeader(HEADER_MIC);\n const syncState = request.getHeader(HEADER_MEDIA_SYNC);\n const isSyncForced = syncState === EEventsSyncMediaState.ADMIN_SYNC_FORCED ? true : false;\n\n if (mic === EEventsMic.ADMIN_START_MIC) {\n this._sessionEvents.trigger(ADMIN_START_MIC, { isSyncForced });\n } else if (mic === EEventsMic.ADMIN_STOP_MIC) {\n this._sessionEvents.trigger(ADMIN_STOP_MIC, { isSyncForced });\n }\n };\n\n _triggerUseLicense = (request: IncomingRequest) => {\n const license: EUseLicense = request.getHeader(HEADER_CONTENT_USE_LICENSE) as EUseLicense;\n\n this._sessionEvents.trigger(USE_LICENSE, license);\n };\n\n _handleNewInfo = (info: IncomingInfoEvent | OutgoingInfoEvent) => {\n const { originator } = info;\n\n if (originator !== 'remote') {\n return;\n }\n\n const request = info.request as IncomingRequest;\n const contentType = request.getHeader(HEADER_CONTENT_TYPE_NAME);\n\n if (contentType) {\n switch (contentType) {\n case CONTENT_TYPE_ENTER_ROOM:\n this._triggerEnterRoom(request);\n this._maybeTriggerChannels(request);\n break;\n case CONTENT_TYPE_NOTIFY:\n this._maybeHandleNotify(request);\n break;\n case CONTENT_TYPE_SHARE_STATE:\n this._triggerShareState(request);\n break;\n case CONTENT_TYPE_MAIN_CAM:\n this._triggerMainCamControl(request);\n break;\n case CONTENT_TYPE_MIC:\n this._triggerMicControl(request);\n break;\n case CONTENT_TYPE_USE_LICENSE:\n this._triggerUseLicense(request);\n break;\n\n default:\n break;\n }\n }\n };\n\n _handleSipEvent = ({ request }: { request: IncomingRequest }) => {\n this._maybeHandleNotify(request);\n };\n\n _maybeHandleNotify = (request: IncomingRequest) => {\n const headerNotify = request.getHeader(HEADER_NOTIFY);\n\n if (headerNotify) {\n const headerNotifyParsed: TInfoNotify = JSON.parse(headerNotify);\n\n this._handleNotify(headerNotifyParsed);\n }\n };\n\n waitChannels(): Promise<TChannels> {\n return this.waitSession(CHANNELS);\n }\n\n waitSyncMediaState(): Promise<{ isSyncForced: boolean }> {\n return this.waitSession(ADMIN_FORCE_SYNC_MEDIA_STATE);\n }\n\n sendChannels({ inputChannels, outputChannels }: TChannels): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const headerInputChannels = `${HEADER_INPUT_CHANNELS}: ${inputChannels}`;\n const headerOutputChannels = `${HEADER_OUTPUT_CHANNELS}: ${outputChannels}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [\n headerInputChannels,\n headerOutputChannels,\n ];\n\n return this.session.sendInfo(CONTENT_TYPE_CHANNELS, undefined, { extraHeaders });\n }\n\n sendMediaState(\n { cam, mic }: TMediaState,\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const headerMediaState = `${HEADER_MEDIA_STATE}: currentstate`;\n const headerCam = `${HEADER_MAIN_CAM_STATE}: ${+cam}`;\n const headerMic = `${HEADER_MIC_STATE}: ${+mic}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [\n headerMediaState,\n headerCam,\n headerMic,\n ];\n\n return this.session.sendInfo(CONTENT_TYPE_MEDIA_STATE, undefined, { ...options, extraHeaders });\n }\n\n _sendRefusalToTurnOn(\n type: 'cam' | 'mic',\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const typeMicOnServer = 0;\n const typeCamOnServer = 1;\n const typeToSend = type == 'mic' ? typeMicOnServer : typeCamOnServer;\n\n const headerMediaType = `${HEADER_MEDIA_TYPE}: ${typeToSend}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [headerMediaType];\n\n return this.session.sendInfo(CONTENT_TYPE_REFUSAL, undefined, { ...options, extraHeaders });\n }\n\n sendRefusalToTurnOnMic(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this._sendRefusalToTurnOn('mic', options);\n }\n\n sendRefusalToTurnOnCam(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this._sendRefusalToTurnOn('cam', options);\n }\n\n _handleEnded = (error: ICustomError) => {\n const { originator } = error;\n\n if (originator === ORIGINATOR_REMOTE) {\n this._sessionEvents.trigger(ENDED_FROM_SERVER, error);\n }\n\n this._restoreSession();\n };\n}\n","const getExtraHeadersRegistration = (remoteAddress?: string) => {\n const headers: string[] = [];\n\n if (remoteAddress) {\n headers.push(`X-Vinteo-Remote: ${remoteAddress}`);\n }\n\n return headers;\n};\n\nexport default getExtraHeadersRegistration;\n","export const HEADER_CONTENT_TYPE_NAME = 'content-type';\n\nexport const HEADER_CONTENT_ENTER_ROOM = 'x-webrtc-enter-room';\nexport const CONTENT_TYPE_SHARE_STATE = 'application/vinteo.webrtc.sharedesktop';\nexport const CONTENT_TYPE_ENTER_ROOM = 'application/vinteo.webrtc.roomname';\nexport const CONTENT_TYPE_CHANNELS = 'application/vinteo.webrtc.channels';\nexport const CONTENT_TYPE_MEDIA_STATE = 'application/vinteo.webrtc.mediastate';\nexport const CONTENT_TYPE_REFUSAL = 'application/vinteo.webrtc.refusal';\nexport const CONTENT_TYPE_MAIN_CAM = 'application/vinteo.webrtc.maincam';\nexport const CONTENT_TYPE_MIC = 'application/vinteo.webrtc.mic';\nexport const CONTENT_TYPE_USE_LICENSE = 'application/vinteo.webrtc.uselic';\nexport const HEADER_CONTENT_USE_LICENSE = 'X-WEBRTC-USE-LICENSE';\nexport const HEADER_INPUT_CHANNELS = 'X-WEBRTC-INPUT-CHANNELS';\nexport const HEADER_OUTPUT_CHANNELS = 'X-WEBRTC-OUTPUT-CHANNELS';\nexport const HEADER_MAIN_CAM = 'X-WEBRTC-MAINCAM';\nexport const HEADER_MIC = 'X-WEBRTC-MIC';\nexport const HEADER_MEDIA_SYNC = 'X-WEBRTC-SYNC';\nexport const HEADER_MAIN_CAM_RESOLUTION = 'X-WEBRTC-MAINCAM-RESOLUTION';\nexport const HEADER_MEDIA_STATE = 'X-WEBRTC-MEDIA-STATE';\nexport const HEADER_MEDIA_TYPE = 'X-Vinteo-Media-Type';\nexport const HEADER_MAIN_CAM_STATE = 'X-Vinteo-MainCam-State';\nexport const HEADER_MIC_STATE = 'X-Vinteo-Mic-State';\n\nexport const CONTENT_TYPE_NOTIFY = 'application/vinteo.webrtc.notify';\nexport const HEADER_NOTIFY = 'X-VINTEO-NOTIFY';\n\nexport const HEADER_CONTENT_SHARE_STATE = 'x-webrtc-share-state';\nexport const HEADER_START_PRESENTATION = `${HEADER_CONTENT_SHARE_STATE}: LETMESTARTPRESENTATION`;\nexport const HEADER_STOP_PRESENTATION = `${HEADER_CONTENT_SHARE_STATE}: STOPPRESENTATION`;\nexport const AVAILABLE_SECOND_REMOTE_STREAM = 'YOUCANRECEIVECONTENT';\nexport const NOT_AVAILABLE_SECOND_REMOTE_STREAM = 'CONTENTEND';\nexport const MUST_STOP_PRESENTATION = 'YOUMUSTSTOPSENDCONTENT';\nexport const HEADER_START_PRESENTATION_P2P = `${HEADER_CONTENT_SHARE_STATE}: ${AVAILABLE_SECOND_REMOTE_STREAM}`;\nexport const HEADER_STOP_PRESENTATION_P2P = `${HEADER_CONTENT_SHARE_STATE}: ${NOT_AVAILABLE_SECOND_REMOTE_STREAM}`;\n\nexport const HEADER_CONTENT_ENABLE_MEDIA_DEVICE = 'X-WEBRTC-REQUEST-ENABLE-MEDIA-DEVICE';\nexport const HEADER_ENABLE_MAIN_CAM = `${HEADER_CONTENT_ENABLE_MEDIA_DEVICE}: LETMESTARTMAINCAM`;\n","const DECLINE_ERROR_MESSAGE = 'Error decline with 603';\n\nexport const hasDeclineResponseFromServer = (error: Error): boolean => {\n return error.message === DECLINE_ERROR_MESSAGE;\n};\n","import findSenderByStream from '../utils/findSenderByStream';\nimport setEncodingsToSender from './setEncodingsToSender';\n\nconst scaleMaxBitrateBySender = (\n senders: RTCRtpSender[],\n mediaStream: MediaStream,\n maxBitrate: number,\n) => {\n const sender = findSenderByStream(senders, mediaStream);\n\n if (sender) {\n return setEncodingsToSender(sender, { maxBitrate });\n }\n\n return Promise.resolve();\n};\n\nexport default scaleMaxBitrateBySender;\n","const findSenderByStream = (\n senders: RTCRtpSender[],\n stream: MediaStream,\n): RTCRtpSender | undefined => {\n return senders.find((sender) => {\n return sender.track && stream.getTracks().includes(sender.track);\n });\n};\n\nexport default findSenderByStream;\n","const findVideoSender = (senders: RTCRtpSender[]): RTCRtpSender | undefined => {\n return senders.find((sender) => {\n return sender?.track?.kind === 'video';\n });\n};\n\nexport default findVideoSender;\n","const hasIncludesString = (source?: string, target?: string): boolean => {\n return !!source && !!target && source.toLowerCase().includes(target.toLowerCase());\n};\n\nexport default hasIncludesString;\n","const ONE_MEGABIT_IN_BITS = 1e6;\n\nconst megabitsToBits = (mb: number): number => {\n return mb * ONE_MEGABIT_IN_BITS;\n};\n\nexport const MINIMUM_BITRATE = megabitsToBits(0.06);\nconst MAXIMUM_BITRATE = megabitsToBits(4);\n\nconst getMaxBitrateByWidth = (maxWidth: number): number => {\n if (maxWidth <= 64) {\n return MINIMUM_BITRATE;\n }\n\n if (maxWidth <= 128) {\n return megabitsToBits(0.12);\n }\n\n if (maxWidth <= 256) {\n return megabitsToBits(0.25);\n }\n\n if (maxWidth <= 384) {\n return megabitsToBits(0.32);\n }\n\n if (maxWidth <= 426) {\n return megabitsToBits(0.38);\n }\n\n if (maxWidth <= 640) {\n return megabitsToBits(0.5);\n }\n\n if (maxWidth <= 848) {\n return megabitsToBits(0.7);\n }\n\n if (maxWidth <= 1280) {\n return megabitsToBits(1);\n }\n\n if (maxWidth <= 1920) {\n return megabitsToBits(2);\n }\n\n return MAXIMUM_BITRATE;\n};\n\nexport default getMaxBitrateByWidth;\n","import hasAv1Codec from './hasAv1Codec';\n\nconst FACTOR_CODEC_AV1 = 0.6;\n\nconst scaleBitrateByCodec = (bitrate: number, codec?: string): number => {\n if (hasAv1Codec(codec)) {\n return bitrate * FACTOR_CODEC_AV1;\n }\n\n return bitrate;\n};\n\nexport default scaleBitrateByCodec;\n","import hasIncludesString from './hasIncludesString';\n\nconst CODEC_AV1 = 'av1';\n\nconst hasAv1Codec = (codec?: string): boolean => {\n return hasIncludesString(codec, CODEC_AV1);\n};\n\nexport default hasAv1Codec;\n","import getMaxBitrateByWidth, { MINIMUM_BITRATE } from './getMaxBitrateByWidth';\nimport scaleBitrateByCodec from './scaleBitrateByCodec';\n\nexport const getMinimumBitrate = (codec?: string) => {\n return scaleBitrateByCodec(MINIMUM_BITRATE, codec);\n};\n\nconst getMaxBitrateByWidthAndCodec = (maxWidth: number, codec?: string): number => {\n const maxBitrate = getMaxBitrateByWidth(maxWidth);\n\n return scaleBitrateByCodec(maxBitrate, codec);\n};\n\nexport default getMaxBitrateByWidthAndCodec;\n","import createStackPromises from 'stack-promises';\nimport { EEventsMainCAM } from '../SipConnector';\nimport getMaxBitrateByWidthAndCodec, { getMinimumBitrate } from './getMaxBitrateByWidthAndCodec';\nimport type { TOnSetParameters, TResult } from './setEncodingsToSender';\nimport setEncodingsToSender from './setEncodingsToSender';\n\nconst stackPromises = createStackPromises<TResult>();\n\nconst runStackPromises = (): Promise<TResult> => {\n // @ts-ignore\n return stackPromises().catch((error) => {\n // eslint-disable-next-line no-console\n console.debug('videoSendingBalancer: error', error);\n });\n};\n\nconst run = (action: () => Promise<TResult>): Promise<TResult> => {\n stackPromises.add(action);\n\n return runStackPromises();\n};\n\nconst addToStackScaleResolutionDownBySender = ({\n sender,\n scaleResolutionDownBy,\n maxBitrate,\n onSetParameters,\n}: {\n sender: RTCRtpSender;\n scaleResolutionDownBy: number;\n maxBitrate: number;\n onSetParameters?: TOnSetParameters;\n}): Promise<TResult> => {\n return run(() => {\n return setEncodingsToSender(sender, { scaleResolutionDownBy, maxBitrate }, onSetParameters);\n });\n};\n\nconst downgradeResolutionSender = (\n { sender, codec }: { sender: RTCRtpSender; codec?: string },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const scaleResolutionDownByTarget = 200;\n const maxBitrate = getMinimumBitrate(codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst setBitrateByTrackResolution = (\n { sender, track, codec }: { sender: RTCRtpSender; track: MediaStreamTrack; codec?: string },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const scaleResolutionDownByTarget = 1;\n\n const settings = track.getSettings();\n const widthCurrent = settings.width!;\n\n const maxBitrate = getMaxBitrateByWidthAndCodec(widthCurrent, codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst setResolutionSender = (\n {\n sender,\n track,\n resolution,\n codec,\n }: {\n sender: RTCRtpSender;\n track: MediaStreamTrack;\n resolution: string;\n codec?: string;\n },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const settings = track.getSettings();\n const widthCurrent = settings.width!;\n const heightCurrent = settings.height!;\n const [widthTarget, heightTarget] = resolution.split('x');\n\n const scaleByWidth = widthCurrent / +widthTarget;\n const scaleByHeight = heightCurrent / +heightTarget!;\n const SCALE_MIN = 1;\n\n const scaleResolutionDownByTarget = Math.max(scaleByWidth, scaleByHeight, SCALE_MIN);\n\n const maxBitrate = getMaxBitrateByWidthAndCodec(+widthTarget, codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst processSender = (\n {\n mainCam,\n resolutionMainCam,\n sender,\n track,\n codec,\n }: {\n mainCam?: EEventsMainCAM;\n resolutionMainCam?: string;\n sender: RTCRtpSender;\n track: MediaStreamTrack;\n codec?: string;\n },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n switch (mainCam) {\n case EEventsMainCAM.PAUSE_MAIN_CAM:\n return downgradeResolutionSender({ sender, codec }, onSetParameters);\n case EEventsMainCAM.RESUME_MAIN_CAM:\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n case EEventsMainCAM.MAX_MAIN_CAM_RESOLUTION:\n if (resolutionMainCam) {\n return setResolutionSender(\n { sender, track, codec, resolution: resolutionMainCam },\n onSetParameters,\n );\n }\n\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n default:\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n }\n};\n\nexport default processSender;\n","import type { EEventsMainCAM } from '../SipConnector';\nimport findVideoSender from '../utils/findVideoSender';\nimport getCodecFromSender from '../utils/getCodecFromSender';\nimport hasIncludesString from './hasIncludesString';\nimport processSender from './processSender';\nimport type { TOnSetParameters, TResult } from './setEncodingsToSender';\n\nconst resultNoChanged: TResult = {\n isChanged: false,\n parameters: {\n encodings: [{}],\n transactionId: '0',\n codecs: [],\n headerExtensions: [],\n rtcp: {},\n },\n};\n\nconst balance = async ({\n mainCam,\n resolutionMainCam,\n connection,\n onSetParameters,\n ignoreForCodec,\n}: {\n mainCam?: EEventsMainCAM;\n resolutionMainCam?: string;\n connection: RTCPeerConnection;\n onSetParameters?: TOnSetParameters;\n ignoreForCodec?: string;\n}) => {\n const senders = connection.getSenders();\n const sender = findVideoSender(senders);\n\n if (!sender || !sender.track) {\n return resultNoChanged;\n }\n\n const codec = await getCodecFromSender(sender);\n\n if (hasIncludesString(codec, ignoreForCodec)) {\n return resultNoChanged;\n }\n\n return processSender(\n { mainCam, resolutionMainCam, sender, codec, track: sender.track },\n onSetParameters,\n );\n};\n\nexport default balance;\n","import type SipConnector from '../SipConnector';\nimport type { EEventsMainCAM } from '../SipConnector';\nimport balance from './balance';\nimport type { TOnSetParameters } from './setEncodingsToSender';\n\nconst resolveVideoSendingBalancer = (\n sipConnector: SipConnector,\n {\n ignoreForCodec,\n onSetParameters,\n }: {\n ignoreForCodec?: string;\n onSetParameters?: TOnSetParameters;\n } = {},\n) => {\n const balanceByTrack = () => {\n const { connection } = sipConnector;\n\n if (!connection) {\n return Promise.reject(new Error('connection is not exist'));\n }\n\n return balance({\n connection,\n onSetParameters,\n ignoreForCodec,\n });\n };\n\n let reBalance = balanceByTrack;\n\n const handleMainCamControl = (headers: {\n mainCam: EEventsMainCAM;\n resolutionMainCam?: string;\n }) => {\n reBalance = () => {\n const { mainCam, resolutionMainCam } = headers;\n const { connection } = sipConnector;\n\n if (!connection) {\n return Promise.reject(new Error('connection is not exist'));\n }\n\n return balance({\n mainCam,\n resolutionMainCam,\n connection,\n onSetParameters,\n ignoreForCodec,\n });\n };\n\n reBalance();\n };\n\n const subscribe = () => {\n sipConnector.onSession('main-cam-control', handleMainCamControl);\n };\n\n const unsubscribe = () => {\n sipConnector.offSession('main-cam-control', handleMainCamControl);\n };\n\n return {\n subscribe,\n unsubscribe,\n balanceByTrack,\n resetMainCamControl() {\n reBalance = balanceByTrack;\n },\n reBalance() {\n return reBalance();\n },\n };\n};\n\nexport default resolveVideoSendingBalancer;\n"],"names":["getCodecFromSender","sender","getStats","then","stats","codec","type","results","keys","map","key","get","statsReportToArray","find","value","mimeType","BYE","UA_SYNTHETICS_EVENT_NAMES","UA_JSSIP_EVENT_NAMES","SESSION_SYNTHETICS_EVENT_NAMES","SESSION_JSSIP_EVENT_NAMES","UA_EVENT_NAMES","SESSION_EVENT_NAMES","parseDisplayName","displayName","trim","replace","generateUserId","min","max","Math","floor","random","prepareMediaStream","mediaStream","videoMode","audioMode","tracks","getAudioTracks","getVideoTracks","newStream","MediaStream","getTracks","resolveHasNeedToUpdateItemEncoding","defaultValue","itemEncodingTarget","itemEncodingCurrent","undefined","hasNeedToUpdateScaleResolutionDownBy","hasNeedToUpdateMaxBitrate","setEncodingsToSender","encodingsTarget","onSetParameters","parameters","getParameters","encodings","length","encoding","scaleResolutionDownByCurrent","scaleResolutionDownBy","scaleResolutionDownByTarget","scaleResolutionDownByTargetParsed","performUpdateScaleResolutionDownBy","isChanged","maxBitrateCurrent","maxBitrate","maxBitrateTarget","performUpdateMaxBitrate","setParameters","Promise","resolve","EEventsMainCAM","EEventsMic","EEventsSyncMediaState","EUseLicense","hasCanceledCallError","error","Error","originator","cause","isCanceledError","moduleName","SipConnector","constructor","JsSIP","this","_isRegisterConfig","_connectionConfiguration","_remoteStreams","getSipServerUrl","id","connect","data","_cancelRequests","_cancelableConnect","request","createUa","_cancelableCreateUa","set","_cancelableSet","call","_cancelableCall","disconnect","_disconnectWithoutCancelRequests","answerToIncomingCall","_cancelableAnswer","sendDTMF","tone","_cancelableSendDTMF","hangUp","_hangUpWithoutCancelRequests","tryRegister","isRegisterConfig","_uaEvents","trigger","unregister","finally","register","reject","declineToIncomingCall","statusCode","isAvailableIncomingCall","incomingSession","callerData","remoteCallerData","cancelRequest","removeIncomingSession","terminate","status_code","busyIncomingCall","handleNewRTCSession","session","on","_connect","params","_start","_createUa","user","password","sipServerUrl","sipWebSocketServerURL","remoteAddress","extraHeaders","sdpSemantics","sessionTimers","registerExpires","connectionRecoveryMinInterval","connectionRecoveryMaxInterval","userAgent","__awaiter","authorizationUser","_init","configuration","display_name","user_agent","sdp_semantics","sockets","socket","uri","session_timers","register_expires","connection_recovery_min_interval","connection_recovery_max_interval","ua","UA","eachTriggers","eventName","uaJsSipEvent","jsSipEvent","extraHeadersRemoteAddress","headers","push","getExtraHeadersRemoteAddress","extraHeadersBase","registrator","setExtraHeaders","resolveUa","removeEventListeners","rejectError","off","addEventListeners","start","_set","changedDisplayName","changedPassword","changedSome","catch","_cancelableDisconnect","_disconnect","disconnectedPromise","once","stop","_call","number","ontrack","iceServers","degradationPreference","offerToReceiveAudio","offerToReceiveVideo","answer","_handleCall","eventHandlers","_sessionEvents","triggers","pcConfig","rtcOfferConstraints","_answer","sessionJsSipEvent","remote_identity","preparedMediaStream","removeStartedEventListeners","offSession","handlePeerConnection","handleConfirmed","removeEndedEventListeners","handleEnded","savedPeerconnection","peerconnection","track","onSession","addStartedEventListeners","addEndedEventListeners","_restoreSession","_resetPresentation","_sendDTMF","onceSession","duration","interToneGap","_streamPresentationCurrent","stopPresentation","isEnded","_handleShareState","_maybeTriggerChannels","inputChannels","getHeader","outputChannels","headersChannels","_handleNotify","header","cmd","channelsInfo","_triggerChannelsNotify","webcastInfo","_triggerWebcastStartedNotify","_triggerWebcastStoppedNotify","_triggerAddedToListModeratorsNotify","_triggerRemovedFromListModeratorsNotify","_triggerParticipantMoveRequestToConference","_triggerParticipantCancelingWordRequest","_triggerParticipantMoveRequestToStream","_triggerAccountChangedNotify","_triggerAccountDeletedNotify","_triggerConferenceParticipantTokenIssued","conference","headersParametersModeratorsList","body","headersParametersWebcast","participant","jwt","headersConferenceParticipantTokenIssued","input","output","_triggerEnterRoom","room","_triggerShareState","_triggerMainCamControl","mainCam","syncState","isSyncForced","ADMIN_SYNC_FORCED","ADMIN_START_MAIN_CAM","ADMIN_STOP_MAIN_CAM","RESUME_MAIN_CAM","PAUSE_MAIN_CAM","resolutionMainCam","_triggerMicControl","mic","ADMIN_START_MIC","ADMIN_STOP_MIC","_triggerUseLicense","license","_handleNewInfo","info","contentType","_maybeHandleNotify","_handleSipEvent","headerNotify","headerNotifyParsed","JSON","parse","_handleEnded","Events","CancelableRequest","afterCancelRequest","isRegistered","sendOptions","target","succeeded","failed","ping","replaceMediaStream","options","askPermissionToEnableCam","noTerminateWhenError","sendInfo","message","hasDeclineResponseFromServer","isPendingPresentation","promisePendingStartPresentation","promisePendingStopPresentation","_sendPresentation","stream","isNeedReinvite","isP2P","streamPresentationCurrent","preparatoryHeaders","result","startPresentation","connection","senders","includes","findSenderByStream","scaleBitrate","getSenders","establishedSession","streamPresentationPrev","updatePresentation","handler","onceRace","eventNames","wait","onceRaceSession","waitSession","isConfigured","getConnectionConfiguration","Object","assign","getRemoteStreams","remoteTracks","getReceivers","some","remoteTrack","kind","hasVideoTracks","_generateStreams","_generateAudioStreams","_a","_b","host","_d","_c","incomingNumber","_f","_e","requested","isEstablished","isCallActive","serverUrl","WebSocketInterface","_generateStream","videoTrack","audioTrack","remoteStream","addTrack","_generateAudioStream","remoteStreams","forEach","index","prevTrack","_cancelActionsRequests","_cancelCallRequests","_cancelConnectRequests","waitChannels","waitSyncMediaState","sendChannels","sendMediaState","cam","_sendRefusalToTurnOn","sendRefusalToTurnOnMic","sendRefusalToTurnOnCam","hasIncludesString","source","toLowerCase","megabitsToBits","mb","MINIMUM_BITRATE","MAXIMUM_BITRATE","scaleBitrateByCodec","bitrate","hasAv1Codec","getMaxBitrateByWidthAndCodec","maxWidth","getMaxBitrateByWidth","stackPromises","createStackPromises","run","action","add","console","debug","addToStackScaleResolutionDownBySender","downgradeResolutionSender","getMinimumBitrate","setBitrateByTrackResolution","widthCurrent","getSettings","width","processSender","MAX_MAIN_CAM_RESOLUTION","resolution","settings","heightCurrent","height","widthTarget","heightTarget","split","scaleByWidth","scaleByHeight","setResolutionSender","resultNoChanged","transactionId","codecs","headerExtensions","rtcp","balance","ignoreForCodec","findVideoSender","resolveVideoSendingBalancer","sipConnector","balanceByTrack","reBalance","handleMainCamControl","subscribe","unsubscribe","resetMainCamControl"],"mappings":"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"}
|
|
1
|
+
{"version":3,"file":"index.es5.js","sources":["../src/utils/getCodecFromSender.ts","../src/causes.ts","../src/constants.ts","../src/eventNames.ts","../src/utils.ts","../src/videoSendingBalancer/setEncodingsToSender.ts","../src/SipConnector.ts","../src/getExtraHeadersRemoteAddress.ts","../src/headers.ts","../src/utils/errors.ts","../src/videoSendingBalancer/scaleBitrate.ts","../src/utils/findSenderByStream.ts","../src/utils/findVideoSender.ts","../src/videoSendingBalancer/hasIncludesString.ts","../src/videoSendingBalancer/getMaxBitrateByWidth.ts","../src/videoSendingBalancer/scaleBitrateByCodec.ts","../src/videoSendingBalancer/hasAv1Codec.ts","../src/videoSendingBalancer/getMaxBitrateByWidthAndCodec.ts","../src/videoSendingBalancer/processSender.ts","../src/videoSendingBalancer/balance.ts","../src/videoSendingBalancer/index.ts","../src/tools/error/getLinkError.ts","../src/tools/error/getTypeFromError.ts","../src/tools/error/getValuesFromError.ts","../src/logger.ts","../src/tools/hasPurgatory.ts","../src/tools/resolveGetRemoteStreams.ts","../src/tools/resolveHandleChangeTracks.ts","../src/tools/resolveUpdateRemoteStreams.ts","../src/tools/syncMediaState/index.ts","../src/tools/syncMediaState/resolveOnStartMainCam.ts","../src/tools/syncMediaState/resolveOnStopMainCam.ts","../src/tools/syncMediaState/resolveOnStartMic.ts","../src/tools/syncMediaState/resolveOnStopMic.ts","../src/tools/answerIncomingCall.ts","../src/tools/callToServer.ts","../src/tools/disconnectFromServer.ts","../src/tools/resolveAskPermissionToEnableCam.ts","../src/tools/resolveStopShareSipConnector.ts","../src/tools/resolveOnMustStopPresentation.ts","../src/tools/resolveOnUseLicense.ts","../src/tools/resolveSendMediaState.ts","../src/tools/resolveSendRefusalToTurnOnCam.ts","../src/tools/resolveSendRefusalToTurnOnMic.ts","../src/tools/resolveStartPresentation.ts","../src/tools/resolveUpdatePresentation.ts","../src/tools/sendDTMFAccumulated.ts"],"sourcesContent":["const statsReportToArray = (results: RTCStatsReport) => {\n return [...results.keys()].map((key) => {\n return results.get(key);\n });\n};\n\nconst findInResultByType = (results: RTCStatsReport, type: string) => {\n return statsReportToArray(results).find((value) => {\n return value.type === type;\n });\n};\n\nconst getCodecFromSender = (sender: RTCRtpSender): Promise<string | undefined> => {\n return sender.getStats().then((stats: RTCStatsReport) => {\n const codec = findInResultByType(stats, 'codec');\n\n return codec?.mimeType;\n });\n};\n\nexport default getCodecFromSender;\n","// Generic error causes.\nexport const CONNECTION_ERROR = 'Connection Error';\nexport const REQUEST_TIMEOUT = 'Request Timeout';\nexport const SIP_FAILURE_CODE = 'SIP Failure Code';\nexport const INTERNAL_ERROR = 'Internal Error';\n// SIP error causes.\nexport const BUSY = 'Busy';\nexport const REJECTED = 'Rejected';\nexport const REDIRECTED = 'Redirected';\nexport const UNAVAILABLE = 'Unavailable';\nexport const NOT_FOUND = 'Not Found';\nexport const ADDRESS_INCOMPLETE = 'Address Incomplete';\nexport const INCOMPATIBLE_SDP = 'Incompatible SDP';\nexport const MISSING_SDP = 'Missing SDP';\nexport const AUTHENTICATION_ERROR = 'Authentication Error';\n// Session error causes.\nexport const BYE = 'Terminated';\nexport const WEBRTC_ERROR = 'WebRTC Error';\nexport const CANCELED = 'Canceled';\nexport const NO_ANSWER = 'No Answer';\nexport const EXPIRES = 'Expires';\nexport const NO_ACK = 'No ACK';\nexport const DIALOG_ERROR = 'Dialog Error';\nexport const USER_DENIED_MEDIA_ACCESS = 'User Denied Media Access';\nexport const BAD_MEDIA_DESCRIPTION = 'Bad Media Description';\nexport const RTP_TIMEOUT = 'RTP Timeout';\n","export const INCOMING_CALL = 'incomingCall';\nexport const DECLINED_INCOMING_CALL = 'declinedIncomingCall';\nexport const FAILED_INCOMING_CALL = 'failedIncomingCall';\nexport const TERMINATED_INCOMING_CALL = 'terminatedIncomingCall';\nexport const CONNECTING = 'connecting';\nexport const CONNECTED = 'connected';\nexport const DISCONNECTED = 'disconnected';\nexport const NEW_RTC_SESSION = 'newRTCSession';\nexport const REGISTERED = 'registered';\nexport const UNREGISTERED = 'unregistered';\nexport const REGISTRATION_FAILED = 'registrationFailed';\nexport const NEW_MESSAGE = 'newMessage';\nexport const SIP_EVENT = 'sipEvent';\nexport const AVAILABLE_SECOND_REMOTE_STREAM_EVENT = 'availableSecondRemoteStream';\nexport const NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT = 'notAvailableSecondRemoteStream';\nexport const MUST_STOP_PRESENTATION_EVENT = 'mustStopPresentation';\nexport const SHARE_STATE = 'shareState';\nexport const ENTER_ROOM = 'enterRoom';\nexport const USE_LICENSE = 'useLicense';\nexport const PEER_CONNECTION_CONFIRMED = 'peerconnection:confirmed';\nexport const PEER_CONNECTION_ONTRACK = 'peerconnection:ontrack';\nexport const CHANNELS = 'channels';\nexport const CHANNELS_NOTIFY = 'channels:notify';\nexport const ENDED_FROM_SERVER = 'ended:fromserver';\nexport const MAIN_CAM_CONTROL = 'main-cam-control';\nexport const ADMIN_STOP_MAIN_CAM = 'admin-stop-main-cam';\nexport const ADMIN_START_MAIN_CAM = 'admin-start-main-cam';\nexport const ADMIN_STOP_MIC = 'admin-stop-mic';\nexport const ADMIN_START_MIC = 'admin-start-mic';\nexport const ADMIN_FORCE_SYNC_MEDIA_STATE = 'admin-force-sync-media-state';\nexport const PARTICIPANT_ADDED_TO_LIST_MODERATORS = 'participant:added-to-list-moderators';\nexport const PARTICIPANT_REMOVED_FROM_LIST_MODERATORS = 'participant:removed-from-list-moderators';\nexport const PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE = 'participant:move-request-to-conference';\nexport const PARTICIPANT_MOVE_REQUEST_TO_STREAM = 'participant:move-request-to-stream';\nexport const PARTICIPANT_CANCELLING_WORD_REQUEST = 'participant:canceling-word-request';\nexport const WEBCAST_STARTED = 'webcast:started';\nexport const WEBCAST_STOPPED = 'webcast:stopped';\nexport const ACCOUNT_CHANGED = 'account:changed';\nexport const ACCOUNT_DELETED = 'account:deleted';\nexport const CONFERENCE_PARTICIPANT_TOKEN_ISSUED = 'conference:participant-token-issued';\nexport const ENDED = 'ended';\nexport const SENDING = 'sending';\nexport const REINVITE = 'reinvite';\nexport const REPLACES = 'replaces';\nexport const REFER = 'refer';\nexport const PROGRESS = 'progress';\nexport const ACCEPTED = 'accepted';\nexport const CONFIRMED = 'confirmed';\nexport const PEER_CONNECTION = 'peerconnection';\nexport const FAILED = 'failed';\nexport const MUTED = 'muted';\nexport const UNMUTED = 'unmuted';\nexport const NEW_DTMF = 'newDTMF';\nexport const NEW_INFO = 'newInfo';\nexport const HOLD = 'hold';\nexport const UNHOLD = 'unhold';\nexport const UPDATE = 'update';\nexport const SDP = 'sdp';\nexport const ICE_CANDIDATE = 'icecandidate';\nexport const GET_USER_MEDIA_FAILED = 'getusermediafailed';\nexport const PEER_CONNECTION_CREATE_OFFER_FAILED = 'peerconnection:createofferfailed';\nexport const PEER_CONNECTION_CREATE_ANSWER_FAILED = 'peerconnection:createanswerfailed';\nexport const PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED =\n 'peerconnection:setlocaldescriptionfailed';\nexport const PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED =\n 'peerconnection:setremotedescriptionfailed';\nexport const PRESENTATION_START = 'presentation:start';\nexport const PRESENTATION_STARTED = 'presentation:started';\nexport const PRESENTATION_END = 'presentation:end';\nexport const PRESENTATION_ENDED = 'presentation:ended';\nexport const PRESENTATION_FAILED = 'presentation:failed';\n","import {\n INCOMING_CALL,\n DECLINED_INCOMING_CALL,\n TERMINATED_INCOMING_CALL,\n FAILED_INCOMING_CALL,\n CONNECTING,\n CONNECTED,\n DISCONNECTED,\n NEW_RTC_SESSION,\n REGISTERED,\n UNREGISTERED,\n REGISTRATION_FAILED,\n NEW_MESSAGE,\n SIP_EVENT,\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n MUST_STOP_PRESENTATION_EVENT,\n SHARE_STATE,\n ENTER_ROOM,\n USE_LICENSE,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n CHANNELS,\n CHANNELS_NOTIFY,\n ENDED_FROM_SERVER,\n MAIN_CAM_CONTROL,\n ADMIN_START_MAIN_CAM,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n ADMIN_START_MIC,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n ENDED,\n SENDING,\n REINVITE,\n REPLACES,\n REFER,\n PROGRESS,\n ACCEPTED,\n CONFIRMED,\n PEER_CONNECTION,\n FAILED,\n MUTED,\n UNMUTED,\n NEW_DTMF,\n NEW_INFO,\n HOLD,\n UNHOLD,\n UPDATE,\n SDP,\n ICE_CANDIDATE,\n GET_USER_MEDIA_FAILED,\n PEER_CONNECTION_CREATE_OFFER_FAILED,\n PEER_CONNECTION_CREATE_ANSWER_FAILED,\n PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED,\n PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED,\n PRESENTATION_START,\n PRESENTATION_STARTED,\n PRESENTATION_END,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n} from './constants';\n\nexport const UA_SYNTHETICS_EVENT_NAMES = [\n INCOMING_CALL,\n DECLINED_INCOMING_CALL,\n TERMINATED_INCOMING_CALL,\n FAILED_INCOMING_CALL,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n CHANNELS_NOTIFY,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n] as const;\n\nexport const UA_JSSIP_EVENT_NAMES = [\n CONNECTING,\n CONNECTED,\n DISCONNECTED,\n NEW_RTC_SESSION,\n REGISTERED,\n UNREGISTERED,\n REGISTRATION_FAILED,\n NEW_MESSAGE,\n SIP_EVENT,\n] as const;\n\nexport const SESSION_SYNTHETICS_EVENT_NAMES = [\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n MUST_STOP_PRESENTATION_EVENT,\n SHARE_STATE,\n ENTER_ROOM,\n USE_LICENSE,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n CHANNELS,\n ENDED_FROM_SERVER,\n MAIN_CAM_CONTROL,\n ADMIN_START_MAIN_CAM,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n ADMIN_START_MIC,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n] as const;\n\nexport const SESSION_JSSIP_EVENT_NAMES = [\n ENDED,\n CONNECTING,\n SENDING,\n REINVITE,\n REPLACES,\n REFER,\n PROGRESS,\n ACCEPTED,\n CONFIRMED,\n PEER_CONNECTION,\n FAILED,\n MUTED,\n UNMUTED,\n NEW_DTMF,\n NEW_INFO,\n HOLD,\n UNHOLD,\n UPDATE,\n SDP,\n ICE_CANDIDATE,\n GET_USER_MEDIA_FAILED,\n PEER_CONNECTION_CREATE_OFFER_FAILED,\n PEER_CONNECTION_CREATE_ANSWER_FAILED,\n PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED,\n PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED,\n PRESENTATION_START,\n PRESENTATION_STARTED,\n PRESENTATION_END,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n] as const;\n\nexport const UA_EVENT_NAMES = [...UA_JSSIP_EVENT_NAMES, ...UA_SYNTHETICS_EVENT_NAMES];\n\nexport const SESSION_EVENT_NAMES = [\n ...SESSION_JSSIP_EVENT_NAMES,\n ...SESSION_SYNTHETICS_EVENT_NAMES,\n] as const;\n\nexport type TEventUA = (typeof UA_EVENT_NAMES)[number];\n\nexport type TEventSession = (typeof SESSION_EVENT_NAMES)[number];\n","export function resolveSipUrl(serverUrl: string): (string) => string {\n return (id: string): string => {\n return `sip:${id}@${serverUrl}`;\n };\n}\n\nconst resolveRandomInt = (min: number, max: number) => {\n return () => {\n return Math.floor(Math.random() * (max - min)) + min;\n };\n};\nexport const parseDisplayName = (displayName: string) => {\n return displayName.trim().replace(/ /g, '_');\n};\nexport const generateUserId = resolveRandomInt(100000, 99999999);\n\nexport const prepareMediaStream = (\n mediaStream?: MediaStream,\n {\n videoMode,\n audioMode,\n }: {\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n } = {},\n): MediaStream | undefined => {\n if (!mediaStream || (videoMode === 'recvonly' && audioMode === 'recvonly')) {\n return undefined;\n }\n\n const audioTracks = audioMode === 'recvonly' ? [] : mediaStream.getAudioTracks();\n const videoTracks = videoMode === 'recvonly' ? [] : mediaStream.getVideoTracks();\n const tracks = [...audioTracks, ...videoTracks];\n const newStream = new MediaStream(tracks);\n\n newStream.getTracks = () => {\n return [...newStream.getAudioTracks(), ...newStream.getVideoTracks()]; // for garante audio first order\n };\n\n return newStream;\n};\n\nexport const hasVideoTracks = (remoteTracks: MediaStreamTrack[]): boolean => {\n const isVideoTracksExists = remoteTracks.some((remoteTrack: MediaStreamTrack): boolean => {\n const { kind } = remoteTrack;\n\n return kind === 'video';\n });\n\n return isVideoTracksExists;\n};\n","export type TOnSetParameters = (parameters: RTCRtpSendParameters) => void;\nexport type TResult = { parameters: RTCRtpSendParameters; isChanged: boolean };\n\nconst MIN_SCALE_RESOLUTION_DOWN_BY = 1;\nconst resolveHasNeedToUpdateItemEncoding = (defaultValue: number | undefined) => {\n return (itemEncodingTarget: typeof defaultValue, itemEncodingCurrent?: number): boolean => {\n const isChangedDefaultScale =\n itemEncodingCurrent === undefined && itemEncodingTarget !== defaultValue;\n const isChangedPrevScale =\n itemEncodingCurrent !== undefined && itemEncodingTarget !== itemEncodingCurrent;\n\n const isNeedToChange = isChangedPrevScale || isChangedDefaultScale;\n\n return isNeedToChange;\n };\n};\n\nconst hasNeedToUpdateScaleResolutionDownBy = resolveHasNeedToUpdateItemEncoding(\n MIN_SCALE_RESOLUTION_DOWN_BY,\n);\nconst performUpdateScaleResolutionDownBy = (\n scaleResolutionDownByTarget?: number,\n scaleResolutionDownByCurrent?: number,\n): number | undefined => {\n const scaleResolutionDownByTargetParsed: number | null =\n scaleResolutionDownByTarget !== undefined\n ? Math.max(scaleResolutionDownByTarget, MIN_SCALE_RESOLUTION_DOWN_BY)\n : null;\n\n if (\n scaleResolutionDownByTargetParsed !== null &&\n hasNeedToUpdateScaleResolutionDownBy(\n scaleResolutionDownByTargetParsed,\n scaleResolutionDownByCurrent,\n )\n ) {\n return scaleResolutionDownByTargetParsed;\n }\n\n return undefined;\n};\n\nconst hasNeedToUpdateMaxBitrate = resolveHasNeedToUpdateItemEncoding(undefined);\nconst performUpdateMaxBitrate = (\n maxBitrateTarget?: number,\n maxBitrateCurrent?: number,\n): number | undefined => {\n if (hasNeedToUpdateMaxBitrate(maxBitrateTarget, maxBitrateCurrent)) {\n return maxBitrateTarget;\n }\n\n return undefined;\n};\n\nconst setEncodingsToSender = (\n sender: RTCRtpSender,\n encodingsTarget: { scaleResolutionDownBy?: number; maxBitrate?: number },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const parameters: RTCRtpSendParameters = sender.getParameters();\n\n if (!parameters.encodings || parameters.encodings.length === 0) {\n parameters.encodings = [{}];\n }\n\n const [encoding] = parameters.encodings;\n const scaleResolutionDownByCurrent = encoding.scaleResolutionDownBy;\n const scaleResolutionDownByTarget = performUpdateScaleResolutionDownBy(\n encodingsTarget.scaleResolutionDownBy,\n scaleResolutionDownByCurrent,\n );\n\n let isChanged = false;\n\n if (scaleResolutionDownByTarget !== undefined) {\n parameters.encodings[0].scaleResolutionDownBy = scaleResolutionDownByTarget;\n isChanged = true;\n }\n\n const maxBitrateCurrent = encoding.maxBitrate;\n const maxBitrateTarget = performUpdateMaxBitrate(encodingsTarget.maxBitrate, maxBitrateCurrent);\n\n if (maxBitrateTarget !== undefined) {\n parameters.encodings[0].maxBitrate = maxBitrateTarget;\n isChanged = true;\n }\n\n if (isChanged) {\n if (onSetParameters) {\n onSetParameters(parameters);\n }\n\n return sender.setParameters(parameters).then(() => {\n return { parameters, isChanged };\n });\n }\n\n return Promise.resolve({ parameters, isChanged });\n};\n\nexport default setEncodingsToSender;\n","import { CancelableRequest, isCanceledError } from '@krivega/cancelable-promise';\nimport type { UA, URI, WebSocketInterface } from '@krivega/jssip';\nimport type RTCSession from '@krivega/jssip/lib/RTCSession';\nimport type { IncomingInfoEvent, OutgoingInfoEvent } from '@krivega/jssip/lib/RTCSession';\nimport type { IncomingRequest } from '@krivega/jssip/lib/SIPMessage';\nimport type {\n IncomingRTCSessionEvent,\n RegisteredEvent,\n UnRegisteredEvent,\n} from '@krivega/jssip/lib/UA';\nimport Events from 'events-constructor';\nimport { BYE, CANCELED, REJECTED, REQUEST_TIMEOUT } from './causes';\nimport {\n ACCOUNT_CHANGED,\n ACCOUNT_DELETED,\n ADMIN_FORCE_SYNC_MEDIA_STATE,\n ADMIN_START_MAIN_CAM,\n ADMIN_START_MIC,\n ADMIN_STOP_MAIN_CAM,\n ADMIN_STOP_MIC,\n AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n CHANNELS,\n CHANNELS_NOTIFY,\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n CONFIRMED,\n CONNECTED,\n CONNECTING,\n DECLINED_INCOMING_CALL,\n DISCONNECTED,\n ENDED,\n ENDED_FROM_SERVER,\n ENTER_ROOM,\n FAILED,\n FAILED_INCOMING_CALL,\n INCOMING_CALL,\n MAIN_CAM_CONTROL,\n MUST_STOP_PRESENTATION_EVENT,\n NEW_DTMF,\n NEW_INFO,\n NEW_RTC_SESSION,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT,\n PARTICIPANT_ADDED_TO_LIST_MODERATORS,\n PARTICIPANT_CANCELLING_WORD_REQUEST,\n PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE,\n PARTICIPANT_MOVE_REQUEST_TO_STREAM,\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n PEER_CONNECTION,\n PEER_CONNECTION_CONFIRMED,\n PEER_CONNECTION_ONTRACK,\n PRESENTATION_ENDED,\n PRESENTATION_FAILED,\n REGISTERED,\n REGISTRATION_FAILED,\n SHARE_STATE,\n SIP_EVENT,\n TERMINATED_INCOMING_CALL,\n UNREGISTERED,\n USE_LICENSE,\n WEBCAST_STARTED,\n WEBCAST_STOPPED,\n} from './constants';\nimport type { TEventSession, TEventUA } from './eventNames';\nimport {\n SESSION_EVENT_NAMES,\n SESSION_JSSIP_EVENT_NAMES,\n UA_EVENT_NAMES,\n UA_JSSIP_EVENT_NAMES,\n} from './eventNames';\nimport getExtraHeadersRemoteAddress from './getExtraHeadersRemoteAddress';\nimport {\n AVAILABLE_SECOND_REMOTE_STREAM,\n CONTENT_TYPE_CHANNELS,\n CONTENT_TYPE_ENTER_ROOM,\n CONTENT_TYPE_MAIN_CAM,\n CONTENT_TYPE_MEDIA_STATE,\n CONTENT_TYPE_MIC,\n CONTENT_TYPE_NOTIFY,\n CONTENT_TYPE_REFUSAL,\n CONTENT_TYPE_SHARE_STATE,\n CONTENT_TYPE_USE_LICENSE,\n HEADER_CONTENT_ENTER_ROOM,\n HEADER_CONTENT_SHARE_STATE,\n HEADER_CONTENT_TYPE_NAME,\n HEADER_CONTENT_USE_LICENSE,\n HEADER_ENABLE_MAIN_CAM,\n HEADER_INPUT_CHANNELS,\n HEADER_MAIN_CAM,\n HEADER_MAIN_CAM_RESOLUTION,\n HEADER_MAIN_CAM_STATE,\n HEADER_MEDIA_STATE,\n HEADER_MEDIA_SYNC,\n HEADER_MEDIA_TYPE,\n HEADER_MIC,\n HEADER_MIC_STATE,\n HEADER_NOTIFY,\n HEADER_OUTPUT_CHANNELS,\n HEADER_START_PRESENTATION,\n HEADER_START_PRESENTATION_P2P,\n HEADER_STOP_PRESENTATION,\n HEADER_STOP_PRESENTATION_P2P,\n MUST_STOP_PRESENTATION,\n NOT_AVAILABLE_SECOND_REMOTE_STREAM,\n} from './headers';\nimport {\n generateUserId,\n hasVideoTracks,\n parseDisplayName,\n prepareMediaStream,\n resolveSipUrl,\n} from './utils';\nimport { hasDeclineResponseFromServer } from './utils/errors';\nimport scaleBitrate from './videoSendingBalancer/scaleBitrate';\n\nconst BUSY_HERE_STATUS_CODE = 486;\nconst REQUEST_TERMINATED_STATUS_CODE = 487;\nconst ORIGINATOR_LOCAL = 'local';\nconst ORIGINATOR_REMOTE = 'remote';\n\nexport enum EEventsMainCAM {\n PAUSE_MAIN_CAM = 'PAUSEMAINCAM',\n RESUME_MAIN_CAM = 'RESUMEMAINCAM',\n MAX_MAIN_CAM_RESOLUTION = 'MAXMAINCAMRESOLUTION',\n ADMIN_STOP_MAIN_CAM = 'ADMINSTOPMAINCAM',\n ADMIN_START_MAIN_CAM = 'ADMINSTARTMAINCAM',\n}\n\nexport enum EEventsMic {\n ADMIN_STOP_MIC = 'ADMINSTOPMIC',\n ADMIN_START_MIC = 'ADMINSTARTMIC',\n}\n\nexport enum EEventsSyncMediaState {\n ADMIN_SYNC_FORCED = '1',\n ADMIN_SYNC_NOT_FORCED = '0',\n}\n\nexport enum EUseLicense {\n AUDIO = 'AUDIO',\n VIDEO = 'VIDEO',\n AUDIOPLUSPRESENTATION = 'AUDIOPLUSPRESENTATION',\n}\n\nexport interface ICustomError extends Error {\n originator?: string;\n cause?: unknown;\n message: any;\n socket?: any;\n url?: string;\n code?: string;\n}\n\nexport const hasCanceledCallError = (error: ICustomError = new Error()): boolean => {\n const { originator, cause } = error;\n\n if (isCanceledError(error)) {\n return true;\n }\n\n if (typeof cause === 'string') {\n return (\n cause === REQUEST_TIMEOUT ||\n cause === REJECTED ||\n (originator === ORIGINATOR_LOCAL && (cause === CANCELED || cause === BYE))\n );\n }\n\n return false;\n};\n\nconst moduleName = 'SipConnector';\n\nexport type TJsSIP = {\n UA: typeof UA;\n WebSocketInterface: typeof WebSocketInterface;\n};\n\ntype TChannels = {\n inputChannels: string;\n outputChannels: string;\n};\n\ntype TMediaState = {\n cam: boolean;\n mic: boolean;\n};\n\ntype TParametersModeratorsList = {\n conference: string;\n};\n\ntype TParametersWebcast = {\n conference: string;\n type: string;\n};\n\ntype TParametersConferenceParticipantTokenIssued = {\n conference: string;\n participant: string;\n jwt: string;\n};\n\ntype TOptionsInfoMediaState = {\n noTerminateWhenError: boolean;\n};\n\nconst CMD_CHANNELS = 'channels' as const;\nconst CMD_WEBCAST_STARTED = 'WebcastStarted' as const;\nconst CMD_WEBCAST_STOPPED = 'WebcastStopped' as const;\nconst CMD_ACCOUNT_CHANGED = 'accountChanged' as const;\nconst CMD_ACCOUNT_DELETED = 'accountDeleted' as const;\nconst CMD_ADDED_TO_LIST_MODERATORS = 'addedToListModerators' as const;\nconst CMD_REMOVED_FROM_LIST_MODERATORS = 'removedFromListModerators' as const;\nconst CMD_MOVE_REQUEST_TO_CONFERENCE = 'WebcastParticipationAccepted' as const;\nconst CMD_CANCELLING_WORD_REQUEST = 'WebcastParticipationRejected' as const;\nconst CMD_MOVE_REQUEST_TO_STREAM = 'ParticipantMovedToWebcast' as const;\nconst CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED = 'ConferenceParticipantTokenIssued' as const;\n\ntype TAddedToListModeratorsInfoNotify = {\n cmd: typeof CMD_ADDED_TO_LIST_MODERATORS;\n conference: string;\n};\ntype TRemovedFromListModeratorsInfoNotify = {\n cmd: typeof CMD_REMOVED_FROM_LIST_MODERATORS;\n conference: string;\n};\ntype TMoveRequestToConferenceInfoNotify = {\n cmd: typeof CMD_MOVE_REQUEST_TO_CONFERENCE;\n body: { conference: string };\n};\ntype TCancelingWordRequestInfoNotify = {\n cmd: typeof CMD_CANCELLING_WORD_REQUEST;\n body: { conference: string };\n};\ntype TMoveRequestToStreamInfoNotify = {\n cmd: typeof CMD_MOVE_REQUEST_TO_STREAM;\n body: { conference: string };\n};\n\ntype TConferenceParticipantTokenIssued = {\n cmd: typeof CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED;\n body: { conference: string; participant: string; jwt: string };\n};\n\ntype TWebcastInfoNotify = {\n cmd: typeof CMD_WEBCAST_STARTED;\n body: { conference: string; type: string };\n};\ntype TChannelsInfoNotify = { cmd: typeof CMD_CHANNELS; input: string; output: string };\ntype TInfoNotify = Omit<\n TChannelsInfoNotify | TAddedToListModeratorsInfoNotify | TRemovedFromListModeratorsInfoNotify,\n 'cmd'\n> & { cmd: string };\n\ntype TOptionsExtraHeaders = {\n extraHeaders?: string[];\n};\n\ntype TOntrack = (track: RTCTrackEvent) => void;\n\ntype TParametersConnection = {\n displayName?: string;\n user?: string;\n password?: string;\n register?: boolean;\n sipServerUrl: string;\n sipWebSocketServerURL: string;\n remoteAddress?: string;\n sdpSemantics?: 'plan-b' | 'unified-plan';\n sessionTimers?: boolean;\n registerExpires?: number;\n connectionRecoveryMinInterval?: number;\n connectionRecoveryMaxInterval?: number;\n userAgent?: string;\n} & TOptionsExtraHeaders;\n\ntype TConnect = (parameters: TParametersConnection) => Promise<UA>;\ntype TCreateUa = (parameters: TParametersConnection) => Promise<UA>;\ntype TStart = () => Promise<UA>;\ntype TSet = ({\n displayName,\n password,\n}: {\n displayName?: string;\n password?: string;\n}) => Promise<boolean>;\n\ntype TDegradationPreference = 'maintain-framerate' | 'maintain-resolution' | 'balanced';\ntype TCall = ({\n number,\n mediaStream,\n extraHeaders,\n ontrack,\n iceServers,\n videoMode,\n audioMode,\n offerToReceiveAudio,\n offerToReceiveVideo,\n degradationPreference,\n}: {\n number: string;\n mediaStream?: MediaStream;\n extraHeaders?: TOptionsExtraHeaders['extraHeaders'];\n ontrack?: TOntrack;\n iceServers?: RTCIceServer[];\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n offerToReceiveAudio?: boolean;\n offerToReceiveVideo?: boolean;\n degradationPreference?: TDegradationPreference;\n}) => Promise<RTCPeerConnection>;\n\ntype TDisconnect = () => Promise<void>;\n\ntype TParametersAnswerToIncomingCall = {\n mediaStream: MediaStream;\n extraHeaders?: TOptionsExtraHeaders['extraHeaders'];\n ontrack?: TOntrack;\n iceServers?: RTCIceServer[];\n videoMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n audioMode?: 'sendrecv' | 'sendonly' | 'recvonly';\n degradationPreference?: TDegradationPreference;\n};\n\ntype TAnswerToIncomingCall = (\n parameters: TParametersAnswerToIncomingCall,\n) => Promise<RTCPeerConnection>;\n\ntype TSendDTMF = (tone: number | string) => Promise<void>;\n\ntype THangUp = () => Promise<void>;\n\nexport default class SipConnector {\n private _isRegisterConfig = false;\n\n private _connectionConfiguration: {\n sipServerUrl?: string;\n displayName?: string;\n register?: boolean;\n user?: string;\n password?: string;\n number?: string;\n answer?: boolean;\n } = {};\n\n private _remoteStreams: { [key: string]: MediaStream } = {};\n\n private JsSIP: TJsSIP;\n\n private _sessionEvents: Events<typeof SESSION_EVENT_NAMES>;\n\n private _uaEvents: Events<typeof UA_EVENT_NAMES>;\n\n private _cancelableConnect: CancelableRequest<Parameters<TConnect>[0], ReturnType<TConnect>>;\n\n private _cancelableCreateUa: CancelableRequest<Parameters<TCreateUa>[0], ReturnType<TCreateUa>>;\n\n private _cancelableDisconnect: CancelableRequest<void, ReturnType<TDisconnect>>;\n\n private _cancelableSet: CancelableRequest<Parameters<TSet>[0], ReturnType<TSet>>;\n\n private _cancelableCall: CancelableRequest<Parameters<TCall>[0], ReturnType<TCall>>;\n\n private _cancelableAnswer: CancelableRequest<\n Parameters<TAnswerToIncomingCall>[0],\n ReturnType<TAnswerToIncomingCall>\n >;\n\n private _cancelableSendDTMF: CancelableRequest<Parameters<TSendDTMF>[0], ReturnType<TSendDTMF>>;\n\n private getSipServerUrl: (id: string) => string = (id: string) => {\n return id;\n };\n\n promisePendingStartPresentation?: Promise<MediaStream>;\n promisePendingStopPresentation?: Promise<void | MediaStream>;\n\n ua?: UA;\n\n session?: RTCSession;\n\n incomingSession?: RTCSession;\n\n _streamPresentationCurrent?: MediaStream;\n\n socket?: WebSocketInterface;\n\n constructor({ JsSIP }: { JsSIP: TJsSIP }) {\n this.JsSIP = JsSIP;\n\n this._sessionEvents = new Events<typeof SESSION_EVENT_NAMES>(SESSION_EVENT_NAMES);\n this._uaEvents = new Events<typeof UA_EVENT_NAMES>(UA_EVENT_NAMES);\n\n this._cancelableConnect = new CancelableRequest<Parameters<TConnect>[0], ReturnType<TConnect>>(\n this._connect,\n {\n moduleName,\n afterCancelRequest: () => {\n this._cancelableCreateUa.cancelRequest();\n this._cancelableDisconnect.cancelRequest();\n },\n },\n );\n\n this._cancelableCreateUa = new CancelableRequest<\n Parameters<TCreateUa>[0],\n ReturnType<TCreateUa>\n >(this._createUa, { moduleName });\n\n this._cancelableDisconnect = new CancelableRequest<void, ReturnType<TDisconnect>>(\n this._disconnect,\n { moduleName },\n );\n\n this._cancelableSet = new CancelableRequest<Parameters<TSet>[0], ReturnType<TSet>>(this._set, {\n moduleName,\n });\n\n this._cancelableCall = new CancelableRequest<Parameters<TCall>[0], ReturnType<TCall>>(\n this._call,\n { moduleName },\n );\n\n this._cancelableAnswer = new CancelableRequest<\n Parameters<TAnswerToIncomingCall>[0],\n ReturnType<TAnswerToIncomingCall>\n >(this._answer, { moduleName });\n\n this._cancelableSendDTMF = new CancelableRequest<\n Parameters<TSendDTMF>[0],\n ReturnType<TSendDTMF>\n >(this._sendDTMF, { moduleName });\n\n this.onSession(SHARE_STATE, this._handleShareState);\n this.onSession(NEW_INFO, this._handleNewInfo);\n this.on(SIP_EVENT, this._handleSipEvent);\n\n this.onSession(FAILED, this._handleEnded);\n this.onSession(ENDED, this._handleEnded);\n }\n\n connect: TConnect = (data) => {\n this._cancelRequests();\n\n return this._cancelableConnect.request(data);\n };\n\n createUa: TCreateUa = (data) => {\n return this._cancelableCreateUa.request(data);\n };\n\n set: TSet = (data) => {\n return this._cancelableSet.request(data);\n };\n\n call: TCall = (data) => {\n return this._cancelableCall.request(data);\n };\n\n disconnect: TDisconnect = () => {\n this._cancelRequests();\n\n return this._disconnectWithoutCancelRequests();\n };\n\n answerToIncomingCall: TAnswerToIncomingCall = (data) => {\n return this._cancelableAnswer.request(data);\n };\n\n sendDTMF: TSendDTMF = (tone) => {\n return this._cancelableSendDTMF.request(tone);\n };\n\n hangUp: THangUp = () => {\n this._cancelRequests();\n\n return this._hangUpWithoutCancelRequests();\n };\n\n register(): Promise<RegisteredEvent> {\n return new Promise((resolve, reject) => {\n if (this.isRegisterConfig) {\n this.ua!.on(REGISTERED, resolve);\n this.ua!.on(REGISTRATION_FAILED, reject);\n this.ua!.register();\n } else {\n reject(new Error('Config is not registered'));\n }\n });\n }\n\n unregister(): Promise<UnRegisteredEvent> {\n return new Promise((resolve, reject) => {\n if (this.isRegistered) {\n this.ua!.on(UNREGISTERED, resolve);\n this.ua!.unregister();\n } else {\n reject(new Error('ua is not registered'));\n }\n });\n }\n\n tryRegister = () => {\n if (!this.isRegisterConfig) {\n return Promise.reject(new Error('Config is not registered'));\n }\n\n this._uaEvents.trigger(CONNECTING, undefined);\n\n return this.unregister()\n .finally(() => {\n return this.register();\n })\n .finally(() => {\n return undefined;\n });\n };\n\n sendOptions(target: string | URI, body?: string, extraHeaders?: string[]): Promise<void> {\n if (!this.ua) {\n return Promise.reject(new Error('is not connected'));\n }\n\n return new Promise((resolve, reject) => {\n try {\n this.ua.sendOptions(target, body, {\n extraHeaders,\n eventHandlers: {\n succeeded: () => {\n resolve();\n },\n failed: (error) => {\n reject(error);\n },\n },\n });\n } catch (error) {\n reject(error);\n }\n });\n }\n\n ping(body?: string, extraHeaders?: string[]): Promise<void> {\n if (!this.ua || !this.ua.configuration || !this.ua.configuration.uri) {\n return Promise.reject(new Error('is not connected'));\n }\n\n const target = this.ua.configuration.uri;\n\n return this.sendOptions(target, body, extraHeaders);\n }\n\n replaceMediaStream(\n mediaStream: MediaStream,\n options?: {\n deleteExisting: boolean;\n addMissing: boolean;\n forceRenegotiation: boolean;\n degradationPreference?: TDegradationPreference;\n },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this.session.replaceMediaStream(mediaStream, options);\n }\n\n declineToIncomingCall = ({ statusCode = REQUEST_TERMINATED_STATUS_CODE } = {}) => {\n return new Promise((resolve, reject) => {\n if (!this.isAvailableIncomingCall) {\n reject(new Error('no incomingSession'));\n\n return undefined;\n }\n\n const incomingSession = this!.incomingSession as RTCSession;\n const callerData = this.remoteCallerData;\n\n this._cancelableCall.cancelRequest();\n this._cancelableAnswer.cancelRequest();\n\n this.removeIncomingSession();\n this._uaEvents.trigger(DECLINED_INCOMING_CALL, callerData);\n resolve(incomingSession.terminate({ status_code: statusCode }));\n\n return undefined;\n });\n };\n\n busyIncomingCall = () => {\n return this.declineToIncomingCall({ statusCode: BUSY_HERE_STATUS_CODE });\n };\n\n removeIncomingSession = () => {\n delete this.incomingSession;\n };\n\n askPermissionToEnableCam(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const extraHeaders = [HEADER_ENABLE_MAIN_CAM];\n\n return this.session\n .sendInfo(CONTENT_TYPE_MAIN_CAM, undefined, {\n ...options,\n extraHeaders,\n })\n .catch((error) => {\n if (hasDeclineResponseFromServer(error)) {\n throw error;\n }\n\n return;\n });\n }\n\n get isPendingPresentation(): boolean {\n return !!this.promisePendingStartPresentation || !!this.promisePendingStopPresentation;\n }\n\n private _sendPresentation(\n session: RTCSession,\n stream: MediaStream,\n {\n maxBitrate,\n degradationPreference,\n isNeedReinvite = true,\n isP2P = false,\n }: {\n isNeedReinvite?: boolean;\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n },\n ) {\n const streamPresentationCurrent = prepareMediaStream(stream) as MediaStream;\n\n this._streamPresentationCurrent = streamPresentationCurrent;\n\n const preparatoryHeaders = isP2P\n ? [HEADER_START_PRESENTATION_P2P]\n : [HEADER_START_PRESENTATION];\n\n const result = session\n .sendInfo(CONTENT_TYPE_SHARE_STATE, undefined, {\n extraHeaders: preparatoryHeaders,\n })\n .then(() => {\n return session.startPresentation(\n streamPresentationCurrent,\n isNeedReinvite,\n degradationPreference,\n );\n })\n // @ts-ignore\n .then(() => {\n const { connection } = this;\n\n if (!connection || maxBitrate === undefined) {\n return undefined;\n }\n\n const senders = connection.getSenders();\n\n return scaleBitrate(senders, stream, maxBitrate);\n })\n .then(() => {\n return stream;\n })\n .catch((error) => {\n this._sessionEvents.trigger(PRESENTATION_FAILED, error);\n\n throw error;\n });\n\n this.promisePendingStartPresentation = result;\n\n return result.finally(() => {\n this.promisePendingStartPresentation = undefined;\n });\n }\n\n startPresentation(\n stream: MediaStream,\n {\n isNeedReinvite = true,\n isP2P = false,\n maxBitrate,\n degradationPreference,\n }: {\n isNeedReinvite?: boolean;\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n } = {},\n ): Promise<void | MediaStream> {\n const session = this.establishedSession;\n\n if (!session) {\n return Promise.reject(new Error('No session established'));\n }\n\n if (this._streamPresentationCurrent) {\n return Promise.reject(new Error('Presentation is already started'));\n }\n\n return this._sendPresentation(session, stream, {\n isNeedReinvite,\n isP2P,\n maxBitrate,\n degradationPreference,\n });\n }\n\n stopPresentation({\n isP2P = false,\n }: {\n isP2P?: boolean;\n } = {}): Promise<MediaStream | void> {\n const streamPresentationPrev = this._streamPresentationCurrent;\n let result: Promise<MediaStream | void> =\n this.promisePendingStartPresentation || Promise.resolve();\n\n const preparatoryHeaders = isP2P ? [HEADER_STOP_PRESENTATION_P2P] : [HEADER_STOP_PRESENTATION];\n\n const session = this.establishedSession;\n\n if (session && streamPresentationPrev) {\n result = result\n .then(() => {\n return session.sendInfo(CONTENT_TYPE_SHARE_STATE, undefined, {\n extraHeaders: preparatoryHeaders,\n });\n })\n .then(() => {\n return session.stopPresentation(streamPresentationPrev);\n })\n .catch((error) => {\n this._sessionEvents.trigger(PRESENTATION_FAILED, error);\n\n throw error;\n });\n }\n\n if (!session && streamPresentationPrev) {\n this._sessionEvents.trigger(PRESENTATION_ENDED, streamPresentationPrev);\n }\n\n this.promisePendingStopPresentation = result;\n\n return result.finally(() => {\n this._resetPresentation();\n });\n }\n\n async updatePresentation(\n stream: MediaStream,\n {\n isP2P = false,\n maxBitrate,\n degradationPreference,\n }: {\n isP2P?: boolean;\n maxBitrate?: number;\n degradationPreference?: TDegradationPreference;\n } = {},\n ): Promise<void | MediaStream> {\n const session = this.establishedSession;\n\n if (!session) {\n return Promise.reject(new Error('No session established'));\n }\n\n if (!this._streamPresentationCurrent) {\n return Promise.reject(new Error('Presentation has not started yet'));\n }\n\n if (this.promisePendingStartPresentation) {\n await this.promisePendingStartPresentation;\n }\n\n return this._sendPresentation(session, stream, {\n isP2P,\n maxBitrate,\n degradationPreference,\n isNeedReinvite: false,\n });\n }\n\n _resetPresentation(): void {\n delete this._streamPresentationCurrent;\n\n this.promisePendingStartPresentation = undefined;\n this.promisePendingStopPresentation = undefined;\n }\n\n handleNewRTCSession = ({ originator, session }: IncomingRTCSessionEvent) => {\n if (originator === ORIGINATOR_REMOTE) {\n this.incomingSession = session;\n\n const callerData = this.remoteCallerData;\n\n session.on(FAILED, ({ originator }) => {\n this.removeIncomingSession();\n\n if (originator !== ORIGINATOR_LOCAL) {\n this._uaEvents.trigger(FAILED_INCOMING_CALL, callerData);\n } else {\n this._uaEvents.trigger(TERMINATED_INCOMING_CALL, callerData);\n }\n });\n\n this._uaEvents.trigger(INCOMING_CALL, callerData);\n }\n };\n\n on(eventName: TEventUA, handler) {\n return this._uaEvents.on(eventName, handler);\n }\n\n once(eventName: TEventUA, handler) {\n return this._uaEvents.once(eventName, handler);\n }\n\n onceRace(eventNames: TEventUA[], handler) {\n return this._uaEvents.onceRace(eventNames, handler);\n }\n\n wait(eventName: TEventUA): Promise<any> {\n return this._uaEvents.wait(eventName);\n }\n\n off(eventName: TEventUA, handler) {\n this._uaEvents.off(eventName, handler);\n }\n\n onSession(eventName: TEventSession, handler) {\n return this._sessionEvents.on(eventName, handler);\n }\n\n onceSession(eventName: TEventSession, handler) {\n return this._sessionEvents.once(eventName, handler);\n }\n\n onceRaceSession(eventNames: TEventSession[], handler) {\n return this._sessionEvents.onceRace(eventNames, handler);\n }\n\n waitSession(eventName: TEventSession): Promise<any> {\n return this._sessionEvents.wait(eventName);\n }\n\n offSession(eventName: TEventSession, handler) {\n this._sessionEvents.off(eventName, handler);\n }\n\n isConfigured() {\n return !!this.ua;\n }\n\n getConnectionConfiguration() {\n return { ...this._connectionConfiguration };\n }\n\n getRemoteStreams(): MediaStream[] | undefined {\n if (!this.connection) {\n return undefined;\n }\n\n const receivers = this.connection.getReceivers();\n const remoteTracks = receivers.map(({ track }) => {\n return track;\n });\n\n if (hasVideoTracks(remoteTracks)) {\n return this._generateStreams(remoteTracks);\n }\n\n return this._generateAudioStreams(remoteTracks);\n }\n\n get connection(): RTCPeerConnection | undefined {\n const connection = this?.session?.connection;\n\n return connection;\n }\n\n get remoteCallerData() {\n return {\n // eslint-disable-next-line camelcase\n displayName: this?.incomingSession?.remote_identity?.display_name,\n // eslint-disable-next-line camelcase\n host: this?.incomingSession?.remote_identity?.uri.host,\n // eslint-disable-next-line camelcase\n incomingNumber: this?.incomingSession?.remote_identity?.uri.user,\n session: this?.incomingSession,\n };\n }\n\n get requested() {\n return (\n this._cancelableConnect.requested ||\n this._cancelableCreateUa.requested ||\n this._cancelableCall.requested ||\n this._cancelableAnswer.requested\n );\n }\n\n get establishedSession(): RTCSession | undefined {\n return this.session && this.session.isEstablished() ? this.session : undefined;\n }\n\n get isRegistered() {\n return !!this.ua && this.ua.isRegistered();\n }\n\n get isRegisterConfig() {\n return !!this.ua && this._isRegisterConfig;\n }\n\n get isCallActive() {\n return !!(this.ua && this.session);\n }\n\n get isAvailableIncomingCall() {\n return !!this.incomingSession;\n }\n\n _connect: TConnect = (params) => {\n return this.createUa(params).then(() => {\n return this._start();\n });\n };\n\n _createUa: TCreateUa = async ({\n displayName = '',\n user,\n password,\n register = false,\n sipServerUrl,\n sipWebSocketServerURL,\n remoteAddress,\n extraHeaders = [],\n sdpSemantics = 'plan-b',\n sessionTimers = false,\n registerExpires = 60 * 5, // 5 minutes in sec\n connectionRecoveryMinInterval = 2,\n connectionRecoveryMaxInterval = 6,\n userAgent,\n }) => {\n if (!sipServerUrl) {\n throw new Error('sipServerUrl is required');\n }\n\n if (!sipWebSocketServerURL) {\n throw new Error('sipWebSocketServerURL is required');\n }\n\n if (register && !user) {\n throw new Error('user is required for authorized connection');\n }\n\n if (register && !password) {\n throw new Error('password is required for authorized connection');\n }\n\n this._connectionConfiguration = {\n sipServerUrl,\n displayName,\n register,\n user,\n password,\n };\n\n this._init({ sipServerUrl, sipWebSocketServerURL });\n\n let authorizationUser;\n\n if (register && user) {\n authorizationUser = user.trim();\n } else {\n authorizationUser = generateUserId();\n }\n\n const configuration = {\n password,\n register,\n display_name: parseDisplayName(displayName),\n user_agent: userAgent,\n sdp_semantics: sdpSemantics,\n sockets: [this.socket as WebSocketInterface],\n uri: this.getSipServerUrl(authorizationUser),\n session_timers: sessionTimers,\n register_expires: registerExpires,\n\n connection_recovery_min_interval: connectionRecoveryMinInterval,\n connection_recovery_max_interval: connectionRecoveryMaxInterval,\n };\n\n if (this.ua) {\n await this._disconnectWithoutCancelRequests();\n }\n\n this._isRegisterConfig = !!configuration.register;\n this.ua = new this.JsSIP.UA(configuration);\n\n this._uaEvents.eachTriggers((trigger, eventName) => {\n const uaJsSipEvent = UA_JSSIP_EVENT_NAMES.find((jsSipEvent) => {\n return jsSipEvent === eventName;\n });\n\n if (uaJsSipEvent) {\n this.ua!.on(uaJsSipEvent, trigger);\n }\n });\n\n const extraHeadersRemoteAddress = getExtraHeadersRemoteAddress(remoteAddress);\n const extraHeadersBase = [...extraHeadersRemoteAddress, ...extraHeaders];\n\n this.ua!.registrator().setExtraHeaders(extraHeadersBase);\n\n return this.ua;\n };\n\n _init({ sipServerUrl, sipWebSocketServerURL }) {\n this.getSipServerUrl = resolveSipUrl(sipServerUrl);\n this.socket = new this.JsSIP.WebSocketInterface(sipWebSocketServerURL);\n }\n\n _start: TStart = () => {\n return new Promise((resolve, reject) => {\n const resolveUa = () => {\n removeEventListeners();\n resolve(this.ua as UA);\n };\n const rejectError = (error) => {\n removeEventListeners();\n reject(error);\n };\n const addEventListeners = () => {\n if (this.isRegisterConfig) {\n this.on(REGISTERED, resolveUa);\n this.on(REGISTRATION_FAILED, rejectError);\n } else {\n this.on(CONNECTED, resolveUa);\n }\n\n this.on(DISCONNECTED, rejectError);\n };\n const removeEventListeners = () => {\n this.off(REGISTERED, resolveUa);\n this.off(REGISTRATION_FAILED, rejectError);\n this.off(CONNECTED, resolveUa);\n this.off(DISCONNECTED, rejectError);\n };\n\n addEventListeners();\n this.on(NEW_RTC_SESSION, this.handleNewRTCSession);\n\n this.ua!.start();\n });\n };\n\n _set: TSet = ({ displayName, password }) => {\n return new Promise((resolve, reject) => {\n let changedDisplayName = false;\n let changedPassword = false;\n\n if (displayName !== undefined && displayName !== this._connectionConfiguration.displayName) {\n changedDisplayName = this.ua!.set('display_name', parseDisplayName(displayName));\n this._connectionConfiguration.displayName = displayName;\n }\n\n if (password !== undefined && password !== this._connectionConfiguration.password) {\n changedPassword = this.ua!.set('password', password);\n this._connectionConfiguration.password = password;\n }\n\n const changedSome = changedDisplayName || changedPassword;\n\n if (changedPassword && this.isRegisterConfig) {\n this.register()\n .then(() => {\n return resolve(changedSome);\n })\n .catch(reject);\n } else if (changedSome) {\n resolve(changedSome);\n } else {\n reject(changedSome);\n }\n });\n };\n\n _disconnectWithoutCancelRequests: TDisconnect = () => {\n return this._cancelableDisconnect.request();\n };\n\n _disconnect = async () => {\n this.off(NEW_RTC_SESSION, this.handleNewRTCSession);\n\n const disconnectedPromise = new Promise<void>((resolve) => {\n this.once(DISCONNECTED, () => {\n delete this.ua;\n resolve();\n });\n });\n\n if (this.ua) {\n await this._hangUpWithoutCancelRequests();\n\n if (this.ua) {\n this.ua.stop();\n } else {\n this._uaEvents.trigger(DISCONNECTED, undefined);\n }\n } else {\n this._uaEvents.trigger(DISCONNECTED, undefined);\n }\n\n return disconnectedPromise;\n };\n\n _call: TCall = ({\n number,\n mediaStream,\n extraHeaders = [],\n ontrack,\n iceServers,\n videoMode,\n audioMode,\n degradationPreference,\n offerToReceiveAudio = true,\n offerToReceiveVideo = true,\n }) => {\n return new Promise((resolve, reject) => {\n this._connectionConfiguration.number = number;\n this._connectionConfiguration.answer = false;\n this._handleCall({ ontrack }).then(resolve).catch(reject);\n\n this.session = this.ua!.call(this.getSipServerUrl(number), {\n extraHeaders,\n mediaStream: prepareMediaStream(mediaStream, {\n videoMode,\n audioMode,\n }),\n eventHandlers: this._sessionEvents.triggers,\n videoMode,\n audioMode,\n degradationPreference,\n pcConfig: {\n iceServers,\n },\n rtcOfferConstraints: {\n offerToReceiveAudio,\n offerToReceiveVideo,\n },\n });\n });\n };\n\n _answer: TAnswerToIncomingCall = ({\n mediaStream,\n ontrack,\n extraHeaders = [],\n iceServers,\n videoMode,\n audioMode,\n degradationPreference,\n }): Promise<RTCPeerConnection> => {\n return new Promise((resolve, reject) => {\n if (!this.isAvailableIncomingCall) {\n reject(new Error('no incomingSession'));\n\n return undefined;\n }\n\n this.session = this.incomingSession;\n this.removeIncomingSession();\n\n const session = this.session;\n\n if (!session) {\n reject(new Error('No session established'));\n\n return;\n }\n\n this._sessionEvents.eachTriggers((trigger, eventName) => {\n const sessionJsSipEvent = SESSION_JSSIP_EVENT_NAMES.find((jsSipEvent) => {\n return jsSipEvent === eventName;\n });\n\n if (sessionJsSipEvent) {\n session.on(sessionJsSipEvent, trigger);\n }\n });\n\n this._connectionConfiguration.answer = true;\n this._connectionConfiguration.number = session.remote_identity.uri.user;\n this._handleCall({ ontrack }).then(resolve).catch(reject);\n\n const preparedMediaStream = prepareMediaStream(mediaStream, {\n videoMode,\n audioMode,\n });\n\n session.answer({\n extraHeaders,\n videoMode,\n audioMode,\n degradationPreference,\n mediaStream: preparedMediaStream,\n pcConfig: {\n iceServers,\n },\n });\n\n return undefined;\n });\n };\n\n _handleCall = ({ ontrack }: { ontrack?: TOntrack }): Promise<RTCPeerConnection> => {\n return new Promise((resolve, reject) => {\n const addStartedEventListeners = () => {\n this.onSession(PEER_CONNECTION, handlePeerConnection);\n this.onSession(CONFIRMED, handleConfirmed);\n };\n const removeStartedEventListeners = () => {\n this.offSession(PEER_CONNECTION, handlePeerConnection);\n this.offSession(CONFIRMED, handleConfirmed);\n };\n const addEndedEventListeners = () => {\n this.onSession(FAILED, handleEnded);\n this.onSession(ENDED, handleEnded);\n };\n const removeEndedEventListeners = () => {\n this.offSession(FAILED, handleEnded);\n this.offSession(ENDED, handleEnded);\n };\n const handleEnded = (error: ICustomError) => {\n removeStartedEventListeners();\n removeEndedEventListeners();\n reject(error);\n };\n\n let savedPeerconnection: RTCPeerConnection;\n\n const handlePeerConnection = ({ peerconnection }) => {\n savedPeerconnection = peerconnection;\n\n savedPeerconnection.ontrack = (track) => {\n this._sessionEvents.trigger(PEER_CONNECTION_ONTRACK, savedPeerconnection);\n\n if (ontrack) {\n ontrack(track);\n }\n };\n };\n const handleConfirmed = () => {\n if (savedPeerconnection) {\n this._sessionEvents.trigger(PEER_CONNECTION_CONFIRMED, savedPeerconnection);\n }\n\n removeStartedEventListeners();\n removeEndedEventListeners();\n resolve(savedPeerconnection);\n };\n\n addStartedEventListeners();\n addEndedEventListeners();\n });\n };\n\n _restoreSession: () => void = () => {\n this._resetPresentation();\n\n delete this._connectionConfiguration.number;\n delete this.session;\n this._remoteStreams = {};\n };\n\n _sendDTMF: TSendDTMF = (tone) => {\n return new Promise<void>((resolve, reject) => {\n const session = this.session;\n\n if (!session) {\n reject(new Error('No session established'));\n\n return;\n }\n\n this.onceSession(NEW_DTMF, ({ originator }) => {\n if (originator === ORIGINATOR_LOCAL) {\n resolve();\n }\n });\n\n session.sendDTMF(tone, {\n duration: 120,\n interToneGap: 600,\n });\n });\n };\n\n _generateStream(videoTrack: MediaStreamTrack, audioTrack?: MediaStreamTrack): MediaStream {\n const id = videoTrack.id;\n\n const remoteStream: MediaStream = this._remoteStreams[id] || new MediaStream();\n\n if (audioTrack) {\n remoteStream.addTrack(audioTrack);\n }\n\n remoteStream.addTrack(videoTrack);\n this._remoteStreams[id] = remoteStream;\n\n return remoteStream;\n }\n\n _generateAudioStream(audioTrack: MediaStreamTrack): MediaStream {\n const id = audioTrack.id;\n\n const remoteStream = this._remoteStreams[id] || new MediaStream();\n\n remoteStream.addTrack(audioTrack);\n\n this._remoteStreams[id] = remoteStream;\n\n return remoteStream;\n }\n\n _generateStreams(remoteTracks: MediaStreamTrack[]): MediaStream[] {\n const remoteStreams: MediaStream[] = [];\n\n remoteTracks.forEach((track, index) => {\n if (track.kind === 'audio') {\n return;\n }\n\n const videoTrack = track;\n const prevTrack = remoteTracks[index - 1];\n let audioTrack;\n\n if (prevTrack && prevTrack.kind === 'audio') {\n audioTrack = prevTrack;\n }\n\n const remoteStream = this._generateStream(videoTrack, audioTrack);\n\n remoteStreams.push(remoteStream);\n }, []);\n\n return remoteStreams;\n }\n\n _generateAudioStreams(remoteTracks: MediaStreamTrack[]): MediaStream[] {\n const remoteStreams: MediaStream[] = remoteTracks.map((remoteTrack) => {\n return this._generateAudioStream(remoteTrack);\n });\n\n return remoteStreams;\n }\n\n _hangUpWithoutCancelRequests: THangUp = async () => {\n if (this.ua && this.session) {\n const { session } = this;\n\n if (this._streamPresentationCurrent) {\n await this.stopPresentation();\n }\n\n this._restoreSession();\n\n if (!session.isEnded()) {\n session.terminate();\n }\n }\n };\n\n _cancelRequests() {\n this._cancelActionsRequests();\n this._cancelCallRequests();\n this._cancelConnectRequests();\n }\n\n _cancelConnectRequests() {\n this._cancelableConnect.cancelRequest();\n }\n\n _cancelCallRequests() {\n this._cancelableCall.cancelRequest();\n this._cancelableAnswer.cancelRequest();\n }\n\n _cancelActionsRequests() {\n this._cancelableAnswer.cancelRequest();\n this._cancelableSendDTMF.cancelRequest();\n }\n\n _handleShareState = (eventName) => {\n switch (eventName) {\n case AVAILABLE_SECOND_REMOTE_STREAM:\n this._sessionEvents.trigger(AVAILABLE_SECOND_REMOTE_STREAM_EVENT, undefined);\n break;\n case NOT_AVAILABLE_SECOND_REMOTE_STREAM:\n this._sessionEvents.trigger(NOT_AVAILABLE_SECOND_REMOTE_STREAM_EVENT, undefined);\n break;\n case MUST_STOP_PRESENTATION:\n this._sessionEvents.trigger(MUST_STOP_PRESENTATION_EVENT, undefined);\n break;\n\n default:\n break;\n }\n };\n\n _maybeTriggerChannels = (request: IncomingRequest) => {\n const inputChannels = request.getHeader(HEADER_INPUT_CHANNELS);\n const outputChannels = request.getHeader(HEADER_OUTPUT_CHANNELS);\n\n if (inputChannels && outputChannels) {\n const headersChannels: TChannels = {\n inputChannels,\n outputChannels,\n };\n\n this._sessionEvents.trigger(CHANNELS, headersChannels);\n }\n };\n\n _handleNotify = (header: TInfoNotify) => {\n if (header.cmd === CMD_CHANNELS) {\n const channelsInfo = header as TChannelsInfoNotify;\n\n this._triggerChannelsNotify(channelsInfo);\n } else if (header.cmd === CMD_WEBCAST_STARTED) {\n const webcastInfo = header as TWebcastInfoNotify;\n\n this._triggerWebcastStartedNotify(webcastInfo);\n } else if (header.cmd === CMD_WEBCAST_STOPPED) {\n const webcastInfo = header as TWebcastInfoNotify;\n\n this._triggerWebcastStoppedNotify(webcastInfo);\n } else if (header.cmd === CMD_ADDED_TO_LIST_MODERATORS) {\n const data = header as TAddedToListModeratorsInfoNotify;\n\n this._triggerAddedToListModeratorsNotify(data);\n } else if (header.cmd === CMD_REMOVED_FROM_LIST_MODERATORS) {\n const data = header as TRemovedFromListModeratorsInfoNotify;\n\n this._triggerRemovedFromListModeratorsNotify(data);\n } else if (header.cmd === CMD_MOVE_REQUEST_TO_CONFERENCE) {\n const data = header as TMoveRequestToConferenceInfoNotify;\n\n this._triggerParticipantMoveRequestToConference(data);\n } else if (header.cmd === CMD_CANCELLING_WORD_REQUEST) {\n const data = header as TCancelingWordRequestInfoNotify;\n\n this._triggerParticipantCancelingWordRequest(data);\n } else if (header.cmd === CMD_MOVE_REQUEST_TO_STREAM) {\n const data = header as TMoveRequestToStreamInfoNotify;\n\n this._triggerParticipantMoveRequestToStream(data);\n } else if (header.cmd === CMD_ACCOUNT_CHANGED) {\n this._triggerAccountChangedNotify();\n } else if (header.cmd === CMD_ACCOUNT_DELETED) {\n this._triggerAccountDeletedNotify();\n } else if (header.cmd === CMD_CONFERENCE_PARTICIPANT_TOKEN_ISSUED) {\n const data = header as TConferenceParticipantTokenIssued;\n\n this._triggerConferenceParticipantTokenIssued(data);\n }\n };\n\n _triggerRemovedFromListModeratorsNotify = ({\n conference,\n }: TRemovedFromListModeratorsInfoNotify) => {\n const headersParametersModeratorsList: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(\n PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,\n headersParametersModeratorsList,\n );\n };\n\n _triggerAddedToListModeratorsNotify = ({ conference }: TAddedToListModeratorsInfoNotify) => {\n const headersParametersModeratorsList: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_ADDED_TO_LIST_MODERATORS, headersParametersModeratorsList);\n };\n\n _triggerWebcastStartedNotify = ({ body: { conference, type } }: TWebcastInfoNotify) => {\n const headersParametersWebcast: TParametersWebcast = {\n conference,\n type,\n };\n\n this._uaEvents.trigger(WEBCAST_STARTED, headersParametersWebcast);\n };\n\n _triggerWebcastStoppedNotify = ({ body: { conference, type } }: TWebcastInfoNotify) => {\n const headersParametersWebcast: TParametersWebcast = {\n conference,\n type,\n };\n\n this._uaEvents.trigger(WEBCAST_STOPPED, headersParametersWebcast);\n };\n\n _triggerAccountChangedNotify = () => {\n this._uaEvents.trigger(ACCOUNT_CHANGED, undefined);\n };\n\n _triggerAccountDeletedNotify = () => {\n this._uaEvents.trigger(ACCOUNT_DELETED, undefined);\n };\n\n _triggerConferenceParticipantTokenIssued = ({\n body: { conference, participant, jwt },\n }: TConferenceParticipantTokenIssued) => {\n const headersConferenceParticipantTokenIssued: TParametersConferenceParticipantTokenIssued = {\n conference,\n participant,\n jwt,\n };\n\n this._uaEvents.trigger(\n CONFERENCE_PARTICIPANT_TOKEN_ISSUED,\n headersConferenceParticipantTokenIssued,\n );\n };\n\n _triggerChannelsNotify = (channelsInfo: TChannelsInfoNotify) => {\n const inputChannels = channelsInfo.input;\n const outputChannels = channelsInfo.output;\n\n const data: TChannels = {\n inputChannels,\n outputChannels,\n };\n\n this._uaEvents.trigger(CHANNELS_NOTIFY, data);\n };\n\n _triggerParticipantMoveRequestToConference = ({\n body: { conference },\n }: TMoveRequestToConferenceInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_MOVE_REQUEST_TO_CONFERENCE, data);\n };\n\n _triggerParticipantCancelingWordRequest = ({\n body: { conference },\n }: TCancelingWordRequestInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_CANCELLING_WORD_REQUEST, data);\n };\n\n _triggerParticipantMoveRequestToStream = ({\n body: { conference },\n }: TMoveRequestToStreamInfoNotify) => {\n const data: TParametersModeratorsList = {\n conference,\n };\n\n this._uaEvents.trigger(PARTICIPANT_MOVE_REQUEST_TO_STREAM, data);\n };\n\n _triggerEnterRoom = (request: IncomingRequest) => {\n const room = request.getHeader(HEADER_CONTENT_ENTER_ROOM);\n\n this._sessionEvents.trigger(ENTER_ROOM, room);\n };\n\n _triggerShareState = (request: IncomingRequest) => {\n const eventName = request.getHeader(HEADER_CONTENT_SHARE_STATE);\n\n this._sessionEvents.trigger(SHARE_STATE, eventName);\n };\n\n _triggerMainCamControl = (request: IncomingRequest) => {\n const mainCam = request.getHeader(HEADER_MAIN_CAM) as EEventsMainCAM;\n\n const syncState = request.getHeader(HEADER_MEDIA_SYNC);\n const isSyncForced = syncState === EEventsSyncMediaState.ADMIN_SYNC_FORCED ? true : false;\n\n if (mainCam === EEventsMainCAM.ADMIN_START_MAIN_CAM) {\n this._sessionEvents.trigger(ADMIN_START_MAIN_CAM, { isSyncForced });\n } else if (mainCam === EEventsMainCAM.ADMIN_STOP_MAIN_CAM) {\n this._sessionEvents.trigger(ADMIN_STOP_MAIN_CAM, { isSyncForced });\n } else if (\n (mainCam === EEventsMainCAM.RESUME_MAIN_CAM || mainCam === EEventsMainCAM.PAUSE_MAIN_CAM) &&\n !!syncState\n ) {\n this._sessionEvents.trigger(ADMIN_FORCE_SYNC_MEDIA_STATE, { isSyncForced });\n } else {\n const resolutionMainCam = request.getHeader(HEADER_MAIN_CAM_RESOLUTION);\n\n this._sessionEvents.trigger(MAIN_CAM_CONTROL, {\n mainCam,\n resolutionMainCam,\n });\n }\n };\n\n _triggerMicControl = (request: IncomingRequest) => {\n const mic = request.getHeader(HEADER_MIC);\n const syncState = request.getHeader(HEADER_MEDIA_SYNC);\n const isSyncForced = syncState === EEventsSyncMediaState.ADMIN_SYNC_FORCED ? true : false;\n\n if (mic === EEventsMic.ADMIN_START_MIC) {\n this._sessionEvents.trigger(ADMIN_START_MIC, { isSyncForced });\n } else if (mic === EEventsMic.ADMIN_STOP_MIC) {\n this._sessionEvents.trigger(ADMIN_STOP_MIC, { isSyncForced });\n }\n };\n\n _triggerUseLicense = (request: IncomingRequest) => {\n const license: EUseLicense = request.getHeader(HEADER_CONTENT_USE_LICENSE) as EUseLicense;\n\n this._sessionEvents.trigger(USE_LICENSE, license);\n };\n\n _handleNewInfo = (info: IncomingInfoEvent | OutgoingInfoEvent) => {\n const { originator } = info;\n\n if (originator !== 'remote') {\n return;\n }\n\n const request = info.request as IncomingRequest;\n const contentType = request.getHeader(HEADER_CONTENT_TYPE_NAME);\n\n if (contentType) {\n switch (contentType) {\n case CONTENT_TYPE_ENTER_ROOM:\n this._triggerEnterRoom(request);\n this._maybeTriggerChannels(request);\n break;\n case CONTENT_TYPE_NOTIFY:\n this._maybeHandleNotify(request);\n break;\n case CONTENT_TYPE_SHARE_STATE:\n this._triggerShareState(request);\n break;\n case CONTENT_TYPE_MAIN_CAM:\n this._triggerMainCamControl(request);\n break;\n case CONTENT_TYPE_MIC:\n this._triggerMicControl(request);\n break;\n case CONTENT_TYPE_USE_LICENSE:\n this._triggerUseLicense(request);\n break;\n\n default:\n break;\n }\n }\n };\n\n _handleSipEvent = ({ request }: { request: IncomingRequest }) => {\n this._maybeHandleNotify(request);\n };\n\n _maybeHandleNotify = (request: IncomingRequest) => {\n const headerNotify = request.getHeader(HEADER_NOTIFY);\n\n if (headerNotify) {\n const headerNotifyParsed: TInfoNotify = JSON.parse(headerNotify);\n\n this._handleNotify(headerNotifyParsed);\n }\n };\n\n waitChannels(): Promise<TChannels> {\n return this.waitSession(CHANNELS);\n }\n\n waitSyncMediaState(): Promise<{ isSyncForced: boolean }> {\n return this.waitSession(ADMIN_FORCE_SYNC_MEDIA_STATE);\n }\n\n sendChannels({ inputChannels, outputChannels }: TChannels): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const headerInputChannels = `${HEADER_INPUT_CHANNELS}: ${inputChannels}`;\n const headerOutputChannels = `${HEADER_OUTPUT_CHANNELS}: ${outputChannels}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [\n headerInputChannels,\n headerOutputChannels,\n ];\n\n return this.session.sendInfo(CONTENT_TYPE_CHANNELS, undefined, { extraHeaders });\n }\n\n sendMediaState(\n { cam, mic }: TMediaState,\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const headerMediaState = `${HEADER_MEDIA_STATE}: currentstate`;\n const headerCam = `${HEADER_MAIN_CAM_STATE}: ${+cam}`;\n const headerMic = `${HEADER_MIC_STATE}: ${+mic}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [\n headerMediaState,\n headerCam,\n headerMic,\n ];\n\n return this.session.sendInfo(CONTENT_TYPE_MEDIA_STATE, undefined, { ...options, extraHeaders });\n }\n\n _sendRefusalToTurnOn(\n type: 'cam' | 'mic',\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n const typeMicOnServer = 0;\n const typeCamOnServer = 1;\n const typeToSend = type == 'mic' ? typeMicOnServer : typeCamOnServer;\n\n const headerMediaType = `${HEADER_MEDIA_TYPE}: ${typeToSend}`;\n const extraHeaders: TOptionsExtraHeaders['extraHeaders'] = [headerMediaType];\n\n return this.session.sendInfo(CONTENT_TYPE_REFUSAL, undefined, { ...options, extraHeaders });\n }\n\n sendRefusalToTurnOnMic(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this._sendRefusalToTurnOn('mic', options);\n }\n\n sendRefusalToTurnOnCam(\n options: TOptionsInfoMediaState = { noTerminateWhenError: true },\n ): Promise<void> {\n if (!this.session) {\n throw new Error('No session established');\n }\n\n return this._sendRefusalToTurnOn('cam', options);\n }\n\n _handleEnded = (error: ICustomError) => {\n const { originator } = error;\n\n if (originator === ORIGINATOR_REMOTE) {\n this._sessionEvents.trigger(ENDED_FROM_SERVER, error);\n }\n\n this._restoreSession();\n };\n}\n","const getExtraHeadersRegistration = (remoteAddress?: string) => {\n const headers: string[] = [];\n\n if (remoteAddress) {\n headers.push(`X-Vinteo-Remote: ${remoteAddress}`);\n }\n\n return headers;\n};\n\nexport default getExtraHeadersRegistration;\n","export const HEADER_CONTENT_TYPE_NAME = 'content-type';\n\nexport const HEADER_CONTENT_ENTER_ROOM = 'x-webrtc-enter-room';\nexport const CONTENT_TYPE_SHARE_STATE = 'application/vinteo.webrtc.sharedesktop';\nexport const CONTENT_TYPE_ENTER_ROOM = 'application/vinteo.webrtc.roomname';\nexport const CONTENT_TYPE_CHANNELS = 'application/vinteo.webrtc.channels';\nexport const CONTENT_TYPE_MEDIA_STATE = 'application/vinteo.webrtc.mediastate';\nexport const CONTENT_TYPE_REFUSAL = 'application/vinteo.webrtc.refusal';\nexport const CONTENT_TYPE_MAIN_CAM = 'application/vinteo.webrtc.maincam';\nexport const CONTENT_TYPE_MIC = 'application/vinteo.webrtc.mic';\nexport const CONTENT_TYPE_USE_LICENSE = 'application/vinteo.webrtc.uselic';\nexport const HEADER_CONTENT_USE_LICENSE = 'X-WEBRTC-USE-LICENSE';\nexport const HEADER_INPUT_CHANNELS = 'X-WEBRTC-INPUT-CHANNELS';\nexport const HEADER_OUTPUT_CHANNELS = 'X-WEBRTC-OUTPUT-CHANNELS';\nexport const HEADER_MAIN_CAM = 'X-WEBRTC-MAINCAM';\nexport const HEADER_MIC = 'X-WEBRTC-MIC';\nexport const HEADER_MEDIA_SYNC = 'X-WEBRTC-SYNC';\nexport const HEADER_MAIN_CAM_RESOLUTION = 'X-WEBRTC-MAINCAM-RESOLUTION';\nexport const HEADER_MEDIA_STATE = 'X-WEBRTC-MEDIA-STATE';\nexport const HEADER_MEDIA_TYPE = 'X-Vinteo-Media-Type';\nexport const HEADER_MAIN_CAM_STATE = 'X-Vinteo-MainCam-State';\nexport const HEADER_MIC_STATE = 'X-Vinteo-Mic-State';\n\nexport const CONTENT_TYPE_NOTIFY = 'application/vinteo.webrtc.notify';\nexport const HEADER_NOTIFY = 'X-VINTEO-NOTIFY';\n\nexport const HEADER_CONTENT_SHARE_STATE = 'x-webrtc-share-state';\nexport const HEADER_START_PRESENTATION = `${HEADER_CONTENT_SHARE_STATE}: LETMESTARTPRESENTATION`;\nexport const HEADER_STOP_PRESENTATION = `${HEADER_CONTENT_SHARE_STATE}: STOPPRESENTATION`;\nexport const AVAILABLE_SECOND_REMOTE_STREAM = 'YOUCANRECEIVECONTENT';\nexport const NOT_AVAILABLE_SECOND_REMOTE_STREAM = 'CONTENTEND';\nexport const MUST_STOP_PRESENTATION = 'YOUMUSTSTOPSENDCONTENT';\nexport const HEADER_START_PRESENTATION_P2P = `${HEADER_CONTENT_SHARE_STATE}: ${AVAILABLE_SECOND_REMOTE_STREAM}`;\nexport const HEADER_STOP_PRESENTATION_P2P = `${HEADER_CONTENT_SHARE_STATE}: ${NOT_AVAILABLE_SECOND_REMOTE_STREAM}`;\n\nexport const HEADER_CONTENT_ENABLE_MEDIA_DEVICE = 'X-WEBRTC-REQUEST-ENABLE-MEDIA-DEVICE';\nexport const HEADER_ENABLE_MAIN_CAM = `${HEADER_CONTENT_ENABLE_MEDIA_DEVICE}: LETMESTARTMAINCAM`;\n","const DECLINE_ERROR_MESSAGE = 'Error decline with 603';\n\nexport const hasDeclineResponseFromServer = (error: Error): boolean => {\n return error.message === DECLINE_ERROR_MESSAGE;\n};\n","import findSenderByStream from '../utils/findSenderByStream';\nimport setEncodingsToSender from './setEncodingsToSender';\n\nconst scaleMaxBitrateBySender = (\n senders: RTCRtpSender[],\n mediaStream: MediaStream,\n maxBitrate: number,\n) => {\n const sender = findSenderByStream(senders, mediaStream);\n\n if (sender) {\n return setEncodingsToSender(sender, { maxBitrate });\n }\n\n return Promise.resolve();\n};\n\nexport default scaleMaxBitrateBySender;\n","const findSenderByStream = (\n senders: RTCRtpSender[],\n stream: MediaStream,\n): RTCRtpSender | undefined => {\n return senders.find((sender) => {\n return sender.track && stream.getTracks().includes(sender.track);\n });\n};\n\nexport default findSenderByStream;\n","const findVideoSender = (senders: RTCRtpSender[]): RTCRtpSender | undefined => {\n return senders.find((sender) => {\n return sender?.track?.kind === 'video';\n });\n};\n\nexport default findVideoSender;\n","const hasIncludesString = (source?: string, target?: string): boolean => {\n return !!source && !!target && source.toLowerCase().includes(target.toLowerCase());\n};\n\nexport default hasIncludesString;\n","const ONE_MEGABIT_IN_BITS = 1e6;\n\nconst megabitsToBits = (mb: number): number => {\n return mb * ONE_MEGABIT_IN_BITS;\n};\n\nexport const MINIMUM_BITRATE = megabitsToBits(0.06);\nconst MAXIMUM_BITRATE = megabitsToBits(4);\n\nconst getMaxBitrateByWidth = (maxWidth: number): number => {\n if (maxWidth <= 64) {\n return MINIMUM_BITRATE;\n }\n\n if (maxWidth <= 128) {\n return megabitsToBits(0.12);\n }\n\n if (maxWidth <= 256) {\n return megabitsToBits(0.25);\n }\n\n if (maxWidth <= 384) {\n return megabitsToBits(0.32);\n }\n\n if (maxWidth <= 426) {\n return megabitsToBits(0.38);\n }\n\n if (maxWidth <= 640) {\n return megabitsToBits(0.5);\n }\n\n if (maxWidth <= 848) {\n return megabitsToBits(0.7);\n }\n\n if (maxWidth <= 1280) {\n return megabitsToBits(1);\n }\n\n if (maxWidth <= 1920) {\n return megabitsToBits(2);\n }\n\n return MAXIMUM_BITRATE;\n};\n\nexport default getMaxBitrateByWidth;\n","import hasAv1Codec from './hasAv1Codec';\n\nconst FACTOR_CODEC_AV1 = 0.6;\n\nconst scaleBitrateByCodec = (bitrate: number, codec?: string): number => {\n if (hasAv1Codec(codec)) {\n return bitrate * FACTOR_CODEC_AV1;\n }\n\n return bitrate;\n};\n\nexport default scaleBitrateByCodec;\n","import hasIncludesString from './hasIncludesString';\n\nconst CODEC_AV1 = 'av1';\n\nconst hasAv1Codec = (codec?: string): boolean => {\n return hasIncludesString(codec, CODEC_AV1);\n};\n\nexport default hasAv1Codec;\n","import getMaxBitrateByWidth, { MINIMUM_BITRATE } from './getMaxBitrateByWidth';\nimport scaleBitrateByCodec from './scaleBitrateByCodec';\n\nexport const getMinimumBitrate = (codec?: string) => {\n return scaleBitrateByCodec(MINIMUM_BITRATE, codec);\n};\n\nconst getMaxBitrateByWidthAndCodec = (maxWidth: number, codec?: string): number => {\n const maxBitrate = getMaxBitrateByWidth(maxWidth);\n\n return scaleBitrateByCodec(maxBitrate, codec);\n};\n\nexport default getMaxBitrateByWidthAndCodec;\n","import createStackPromises from 'stack-promises';\nimport { EEventsMainCAM } from '../SipConnector';\nimport getMaxBitrateByWidthAndCodec, { getMinimumBitrate } from './getMaxBitrateByWidthAndCodec';\nimport type { TOnSetParameters, TResult } from './setEncodingsToSender';\nimport setEncodingsToSender from './setEncodingsToSender';\n\nconst stackPromises = createStackPromises<TResult>();\n\nconst runStackPromises = (): Promise<TResult> => {\n // @ts-ignore\n return stackPromises().catch((error) => {\n // eslint-disable-next-line no-console\n console.debug('videoSendingBalancer: error', error);\n });\n};\n\nconst run = (action: () => Promise<TResult>): Promise<TResult> => {\n stackPromises.add(action);\n\n return runStackPromises();\n};\n\nconst addToStackScaleResolutionDownBySender = ({\n sender,\n scaleResolutionDownBy,\n maxBitrate,\n onSetParameters,\n}: {\n sender: RTCRtpSender;\n scaleResolutionDownBy: number;\n maxBitrate: number;\n onSetParameters?: TOnSetParameters;\n}): Promise<TResult> => {\n return run(() => {\n return setEncodingsToSender(sender, { scaleResolutionDownBy, maxBitrate }, onSetParameters);\n });\n};\n\nconst downgradeResolutionSender = (\n { sender, codec }: { sender: RTCRtpSender; codec?: string },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const scaleResolutionDownByTarget = 200;\n const maxBitrate = getMinimumBitrate(codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst setBitrateByTrackResolution = (\n { sender, track, codec }: { sender: RTCRtpSender; track: MediaStreamTrack; codec?: string },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const scaleResolutionDownByTarget = 1;\n\n const settings = track.getSettings();\n const widthCurrent = settings.width!;\n\n const maxBitrate = getMaxBitrateByWidthAndCodec(widthCurrent, codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst setResolutionSender = (\n {\n sender,\n track,\n resolution,\n codec,\n }: {\n sender: RTCRtpSender;\n track: MediaStreamTrack;\n resolution: string;\n codec?: string;\n },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n const settings = track.getSettings();\n const widthCurrent = settings.width!;\n const heightCurrent = settings.height!;\n const [widthTarget, heightTarget] = resolution.split('x');\n\n const scaleByWidth = widthCurrent / +widthTarget;\n const scaleByHeight = heightCurrent / +heightTarget!;\n const SCALE_MIN = 1;\n\n const scaleResolutionDownByTarget = Math.max(scaleByWidth, scaleByHeight, SCALE_MIN);\n\n const maxBitrate = getMaxBitrateByWidthAndCodec(+widthTarget, codec);\n\n return addToStackScaleResolutionDownBySender({\n sender,\n maxBitrate,\n onSetParameters,\n scaleResolutionDownBy: scaleResolutionDownByTarget,\n });\n};\n\nconst processSender = (\n {\n mainCam,\n resolutionMainCam,\n sender,\n track,\n codec,\n }: {\n mainCam?: EEventsMainCAM;\n resolutionMainCam?: string;\n sender: RTCRtpSender;\n track: MediaStreamTrack;\n codec?: string;\n },\n onSetParameters?: TOnSetParameters,\n): Promise<TResult> => {\n switch (mainCam) {\n case EEventsMainCAM.PAUSE_MAIN_CAM:\n return downgradeResolutionSender({ sender, codec }, onSetParameters);\n case EEventsMainCAM.RESUME_MAIN_CAM:\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n case EEventsMainCAM.MAX_MAIN_CAM_RESOLUTION:\n if (resolutionMainCam) {\n return setResolutionSender(\n { sender, track, codec, resolution: resolutionMainCam },\n onSetParameters,\n );\n }\n\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n default:\n return setBitrateByTrackResolution({ sender, track, codec }, onSetParameters);\n }\n};\n\nexport default processSender;\n","import type { EEventsMainCAM } from '../SipConnector';\nimport findVideoSender from '../utils/findVideoSender';\nimport getCodecFromSender from '../utils/getCodecFromSender';\nimport hasIncludesString from './hasIncludesString';\nimport processSender from './processSender';\nimport type { TOnSetParameters, TResult } from './setEncodingsToSender';\n\nconst resultNoChanged: TResult = {\n isChanged: false,\n parameters: {\n encodings: [{}],\n transactionId: '0',\n codecs: [],\n headerExtensions: [],\n rtcp: {},\n },\n};\n\nconst balance = async ({\n mainCam,\n resolutionMainCam,\n connection,\n onSetParameters,\n ignoreForCodec,\n}: {\n mainCam?: EEventsMainCAM;\n resolutionMainCam?: string;\n connection: RTCPeerConnection;\n onSetParameters?: TOnSetParameters;\n ignoreForCodec?: string;\n}) => {\n const senders = connection.getSenders();\n const sender = findVideoSender(senders);\n\n if (!sender || !sender.track) {\n return resultNoChanged;\n }\n\n const codec = await getCodecFromSender(sender);\n\n if (hasIncludesString(codec, ignoreForCodec)) {\n return resultNoChanged;\n }\n\n return processSender(\n { mainCam, resolutionMainCam, sender, codec, track: sender.track },\n onSetParameters,\n );\n};\n\nexport default balance;\n","import type SipConnector from '../SipConnector';\nimport type { EEventsMainCAM } from '../SipConnector';\nimport balance from './balance';\nimport type { TOnSetParameters } from './setEncodingsToSender';\n\nconst resolveVideoSendingBalancer = (\n sipConnector: SipConnector,\n {\n ignoreForCodec,\n onSetParameters,\n }: {\n ignoreForCodec?: string;\n onSetParameters?: TOnSetParameters;\n } = {},\n) => {\n const balanceByTrack = () => {\n const { connection } = sipConnector;\n\n if (!connection) {\n return Promise.reject(new Error('connection is not exist'));\n }\n\n return balance({\n connection,\n onSetParameters,\n ignoreForCodec,\n });\n };\n\n let reBalance = balanceByTrack;\n\n const handleMainCamControl = (headers: {\n mainCam: EEventsMainCAM;\n resolutionMainCam?: string;\n }) => {\n reBalance = () => {\n const { mainCam, resolutionMainCam } = headers;\n const { connection } = sipConnector;\n\n if (!connection) {\n return Promise.reject(new Error('connection is not exist'));\n }\n\n return balance({\n mainCam,\n resolutionMainCam,\n connection,\n onSetParameters,\n ignoreForCodec,\n });\n };\n\n reBalance();\n };\n\n const subscribe = () => {\n sipConnector.onSession('main-cam-control', handleMainCamControl);\n };\n\n const unsubscribe = () => {\n sipConnector.offSession('main-cam-control', handleMainCamControl);\n };\n\n return {\n subscribe,\n unsubscribe,\n balanceByTrack,\n resetMainCamControl() {\n reBalance = balanceByTrack;\n },\n reBalance() {\n return reBalance();\n },\n };\n};\n\nexport default resolveVideoSendingBalancer;\n","import * as causes from '../../causes';\nimport type { ICustomError } from '../../SipConnector';\n\nconst getLinkError = (error: ICustomError): string | undefined => {\n const { url, cause } = error;\n\n let link = url;\n\n if (cause === causes.BAD_MEDIA_DESCRIPTION || cause === causes.NOT_FOUND) {\n link = `${error.message.to.uri.user}@${error.message.to.uri.host}`;\n }\n\n return link;\n};\n\nexport default getLinkError;\n","import * as causes from '../../causes';\nimport type { ICustomError } from '../../SipConnector';\nimport getLinkError from './getLinkError';\n\nexport enum EErrorTypes {\n CONNECT_SERVER_FAILED = 'CONNECT_SERVER_FAILED',\n WRONG_USER_OR_PASSWORD = 'WRONG_USER_OR_PASSWORD',\n BAD_MEDIA_ERROR = 'BAD_MEDIA_ERROR',\n NOT_FOUND_ERROR = 'NOT_FOUND_ERROR',\n WS_CONNECTION_FAILED = 'WS_CONNECTION_FAILED',\n CONNECT_SERVER_FAILED_BY_LINK = 'CONNECT_SERVER_FAILED_BY_LINK',\n}\n\nconst getTypeFromError = (error: ICustomError = new Error()): EErrorTypes => {\n const { cause, socket } = error;\n\n let type: EErrorTypes = EErrorTypes.CONNECT_SERVER_FAILED;\n\n if (cause === 'Forbidden') {\n type = EErrorTypes.WRONG_USER_OR_PASSWORD;\n } else if (cause === causes.BAD_MEDIA_DESCRIPTION) {\n type = EErrorTypes.BAD_MEDIA_ERROR;\n } else if (cause === causes.NOT_FOUND) {\n type = EErrorTypes.NOT_FOUND_ERROR;\n } else if (socket && socket?._ws?.readyState === 3) {\n type = EErrorTypes.WS_CONNECTION_FAILED;\n } else if (getLinkError(error)) {\n type = EErrorTypes.CONNECT_SERVER_FAILED_BY_LINK;\n }\n\n return type;\n};\n\nexport default getTypeFromError;\n","import type { ICustomError } from '../../SipConnector';\nimport getLinkError from './getLinkError';\n\nexport type TValues = {\n message?: string;\n link?: string;\n code?: string;\n cause?: string;\n};\n\nconst getValuesFromError = (error: ICustomError = new Error()): TValues => {\n const { code, cause, message } = error;\n const link = getLinkError(error);\n const values: TValues = {};\n\n if (message) {\n values.message = message;\n }\n\n if (link) {\n values.link = link;\n }\n\n if (code) {\n values.code = code;\n }\n\n if (cause) {\n values.cause = cause as string;\n }\n\n return values;\n};\n\nexport default getValuesFromError;\n","import debug from 'debug';\n\nconst NAME = 'sip-connector';\n\nconst logger = debug(NAME);\n\nexport default logger;\n\nexport { default as debug } from 'debug';\n\nexport const enableDebug = () => {\n debug.enable(`${NAME}`);\n};\n\nexport const disableDebug = () => {\n debug.enable(`-${NAME}`);\n};\n","export const PURGATORY_CONFERENCE_NUMBER = 'purgatory' as const;\n\nconst hasPurgatory = (room?: string) => {\n return room === PURGATORY_CONFERENCE_NUMBER;\n};\n\nexport default hasPurgatory;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveGetRemoteStreams = (sipConnector: SipConnector) => {\n const getRemoteStreams = (): MediaStream[] | undefined => {\n log('getRemoteStreams');\n\n return sipConnector.getRemoteStreams();\n };\n\n return getRemoteStreams;\n};\n\nexport default resolveGetRemoteStreams;\n","const hasVideoTrackReady = ({ kind, readyState }: MediaStreamTrack) => {\n return kind === 'video' && readyState === 'live';\n};\n\nconst resolveHandleChangeTracks = (updateRemoteStreams: () => void) => {\n return ({ track }: { track: MediaStreamTrack }) => {\n if (hasVideoTrackReady(track)) {\n updateRemoteStreams();\n }\n };\n};\n\nexport default resolveHandleChangeTracks;\n","import debounce from 'lodash/debounce';\nimport log from '../logger';\n\nconst resolveUpdateRemoteStreams = ({\n getRemoteStreams,\n setRemoteStreams,\n}: {\n getRemoteStreams: () => MediaStream[] | undefined;\n setRemoteStreams: (streams: MediaStream[]) => void;\n}) => {\n return debounce(() => {\n const remoteStreams = getRemoteStreams();\n\n log('remoteStreams', remoteStreams);\n\n if (remoteStreams) {\n setRemoteStreams(remoteStreams);\n }\n }, 200);\n};\n\nexport default resolveUpdateRemoteStreams;\n","import type SipConnector from '../../SipConnector';\nimport resolveOnStartMainCam from './resolveOnStartMainCam';\nimport resolveOnStartMic from './resolveOnStartMic';\nimport resolveOnStopMainCam from './resolveOnStopMainCam';\nimport resolveOnStopMic from './resolveOnStopMic';\n\ntype THandlers = {\n onStartMainCamForced: () => void;\n onStartMainCamNotForced: () => void;\n onStopMainCamForced: () => void;\n onStopMainCamNotForced: () => void;\n onStartMicForced: () => void;\n onStartMicNotForced: () => void;\n onStopMicForced: () => void;\n onStopMicNotForced: () => void;\n};\n\nconst createSyncMediaState = ({ sipConnector }: { sipConnector: SipConnector }) => {\n const resolveWhenElseSyncForced = (whenSyncForced: () => void, whenNotSyncForced: () => void) => {\n return (data: { isSyncForced: boolean } = { isSyncForced: false }) => {\n if (data.isSyncForced) {\n return whenSyncForced();\n }\n\n return whenNotSyncForced();\n };\n };\n\n const subscribeStartMainCam = resolveOnStartMainCam(sipConnector);\n const subscribeStopMainCam = resolveOnStopMainCam(sipConnector);\n const subscribeStartMic = resolveOnStartMic(sipConnector);\n const subscribeStopMic = resolveOnStopMic(sipConnector);\n\n let unsubscribeStartMainCam = () => {};\n let unsubscribeStopMainCam = () => {};\n let unsubscribeStartMic = () => {};\n let unsubscribeStopMic = () => {};\n const subscribeSyncCommands = ({\n onStartMainCamForced,\n onStartMainCamNotForced,\n onStopMainCamForced,\n onStopMainCamNotForced,\n onStartMicForced,\n onStartMicNotForced,\n onStopMicForced,\n onStopMicNotForced,\n }: THandlers) => {\n const handleStartMainCam = resolveWhenElseSyncForced(\n onStartMainCamForced,\n onStartMainCamNotForced,\n );\n\n unsubscribeStartMainCam = subscribeStartMainCam(handleStartMainCam);\n\n const handleStopMainCam = resolveWhenElseSyncForced(\n onStopMainCamForced,\n onStopMainCamNotForced,\n );\n\n unsubscribeStopMainCam = subscribeStopMainCam(handleStopMainCam);\n\n const handleStartMic = resolveWhenElseSyncForced(onStartMicForced, onStartMicNotForced);\n\n unsubscribeStartMic = subscribeStartMic(handleStartMic);\n\n const handleStopMic = resolveWhenElseSyncForced(onStopMicForced, onStopMicNotForced);\n\n unsubscribeStopMic = subscribeStopMic(handleStopMic);\n };\n\n const unsubscribeSyncCommands = () => {\n unsubscribeStartMainCam();\n unsubscribeStopMainCam();\n unsubscribeStartMic();\n unsubscribeStopMic();\n };\n\n const start = (handlers: THandlers) => {\n subscribeSyncCommands(handlers);\n };\n\n const stop = () => {\n unsubscribeSyncCommands();\n };\n\n return {\n start,\n stop,\n };\n};\n\nexport default createSyncMediaState;\n","import type SipConnector from '../../SipConnector';\nimport log from '../../logger';\n\nconst resolveOnStartMainCam = (sipConnector: SipConnector) => {\n const onStartMainCam = (\n handler: ({ isSyncForced }: { isSyncForced: boolean }) => void,\n ): (() => void) => {\n log('onStartMainCam');\n\n return sipConnector.onSession('admin-start-main-cam', handler);\n };\n\n return onStartMainCam;\n};\n\nexport default resolveOnStartMainCam;\n","import type SipConnector from '../../SipConnector';\nimport log from '../../logger';\n\nconst resolveOnStopMainCam = (sipConnector: SipConnector) => {\n const onStopMainCam = (\n handler: ({ isSyncForced }: { isSyncForced: boolean }) => void,\n ): (() => void) => {\n log('onStopMainCam');\n\n return sipConnector.onSession('admin-stop-main-cam', handler);\n };\n\n return onStopMainCam;\n};\n\nexport default resolveOnStopMainCam;\n","import type SipConnector from '../../SipConnector';\nimport log from '../../logger';\n\nconst resolveOnStartMic = (sipConnector: SipConnector) => {\n const onStartMic = (\n handler: ({ isSyncForced }: { isSyncForced: boolean }) => void,\n ): (() => void) => {\n log('onStartMic');\n\n return sipConnector.onSession('admin-start-mic', handler);\n };\n\n return onStartMic;\n};\n\nexport default resolveOnStartMic;\n","import type SipConnector from '../../SipConnector';\nimport log from '../../logger';\n\nconst resolveOnStopMic = (sipConnector: SipConnector) => {\n const onStopMic = (\n handler: ({ isSyncForced }: { isSyncForced: boolean }) => void,\n ): (() => void) => {\n log('onStopMic');\n\n return sipConnector.onSession('admin-stop-mic', handler);\n };\n\n return onStopMic;\n};\n\nexport default resolveOnStopMic;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\nimport hasPurgatory from './hasPurgatory';\nimport resolveGetRemoteStreams from './resolveGetRemoteStreams';\nimport resolveHandleChangeTracks from './resolveHandleChangeTracks';\nimport resolveUpdateRemoteStreams from './resolveUpdateRemoteStreams';\n\ntype TDegradationPreference = 'maintain-framerate' | 'maintain-resolution' | 'balanced';\n\nconst resolveAnswerIncomingCall = (sipConnector: SipConnector) => {\n const answerIncomingCall = (params: {\n mediaStream: MediaStream;\n extraHeaders?: string[] | undefined;\n iceServers?: RTCIceServer[];\n degradationPreference?: TDegradationPreference;\n setRemoteStreams: (streams: MediaStream[]) => void;\n onBeforeProgressCall?: (conference: string) => void;\n onSuccessProgressCall?: (params: { isPurgatory: boolean }) => void;\n onFailProgressCall?: () => void;\n onFinishProgressCall?: () => void;\n onEnterPurgatory?: () => void;\n onEnterConference?: (params: { isSuccessProgressCall: boolean }) => void;\n onEndedCall?: () => void;\n }): Promise<RTCPeerConnection | void> => {\n const {\n mediaStream,\n extraHeaders,\n iceServers,\n degradationPreference,\n setRemoteStreams,\n onBeforeProgressCall,\n onSuccessProgressCall,\n onEnterPurgatory,\n onEnterConference,\n onFailProgressCall,\n onFinishProgressCall,\n onEndedCall,\n } = params;\n const updateRemoteStreams = resolveUpdateRemoteStreams({\n setRemoteStreams,\n getRemoteStreams: resolveGetRemoteStreams(sipConnector),\n });\n const handleChangeTracks = resolveHandleChangeTracks(updateRemoteStreams);\n\n log('answerIncomingCall', params);\n\n const answer = (): Promise<RTCPeerConnection> => {\n return sipConnector.answerToIncomingCall({\n mediaStream,\n extraHeaders,\n iceServers,\n degradationPreference,\n ontrack: handleChangeTracks,\n });\n };\n\n const getIncomingNumber = (): string => {\n const { remoteCallerData } = sipConnector;\n const { incomingNumber } = remoteCallerData;\n\n return incomingNumber;\n };\n let isSuccessProgressCall = false;\n let room: string;\n\n const subscribeEnterConference = () => {\n log('subscribeEnterConference: onEnterConference', onEnterConference);\n\n if (onEnterPurgatory || onEnterConference) {\n return sipConnector.onSession('enterRoom', (_room: string) => {\n log('enterRoom', { _room, isSuccessProgressCall });\n\n room = _room;\n\n if (hasPurgatory(room)) {\n if (onEnterPurgatory) {\n onEnterPurgatory();\n }\n } else if (onEnterConference) {\n onEnterConference({ isSuccessProgressCall });\n }\n });\n }\n\n return () => {};\n };\n\n const unsubscribeEnterConference = subscribeEnterConference();\n\n const onSuccess = (peerConnection: RTCPeerConnection) => {\n log('onSuccess');\n\n isSuccessProgressCall = true;\n updateRemoteStreams();\n\n if (onSuccessProgressCall) {\n onSuccessProgressCall({ isPurgatory: hasPurgatory(room) });\n }\n\n sipConnector.onceRaceSession(['ended', 'failed'], () => {\n unsubscribeEnterConference();\n\n if (onEndedCall) {\n onEndedCall();\n }\n });\n\n return peerConnection;\n };\n\n const onFail = (error: Error): never => {\n log('onFail');\n\n if (onFailProgressCall) {\n onFailProgressCall();\n }\n\n unsubscribeEnterConference();\n\n throw error;\n };\n\n const onFinish = () => {\n log('onFinish');\n\n if (onFinishProgressCall) {\n onFinishProgressCall();\n }\n };\n\n log('onBeforeProgressCall');\n\n if (onBeforeProgressCall) {\n const conference = getIncomingNumber();\n\n onBeforeProgressCall(conference);\n }\n\n return answer().then(onSuccess).catch(onFail).finally(onFinish);\n };\n\n return answerIncomingCall;\n};\n\nexport default resolveAnswerIncomingCall;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\nimport hasPurgatory from './hasPurgatory';\nimport resolveGetRemoteStreams from './resolveGetRemoteStreams';\nimport resolveHandleChangeTracks from './resolveHandleChangeTracks';\nimport resolveUpdateRemoteStreams from './resolveUpdateRemoteStreams';\n\ntype TDegradationPreference = 'maintain-framerate' | 'maintain-resolution' | 'balanced';\n\nconst resolveCallToServer = (sipConnector: SipConnector) => {\n const callToServer = (params: {\n conference: string;\n mediaStream: MediaStream;\n extraHeaders?: string[] | undefined;\n iceServers?: RTCIceServer[];\n degradationPreference?: TDegradationPreference;\n setRemoteStreams: (streams: MediaStream[]) => void;\n onBeforeProgressCall?: (conference: string) => void;\n onSuccessProgressCall?: (params: { isPurgatory: boolean }) => void;\n onEnterPurgatory?: () => void;\n onEnterConference?: (params: { isSuccessProgressCall: boolean }) => void;\n onFailProgressCall?: () => void;\n onFinishProgressCall?: () => void;\n onEndedCall?: () => void;\n }): Promise<RTCPeerConnection> => {\n const {\n conference,\n mediaStream,\n extraHeaders,\n iceServers,\n degradationPreference,\n setRemoteStreams,\n onBeforeProgressCall,\n onSuccessProgressCall,\n onEnterPurgatory,\n onEnterConference,\n onFailProgressCall,\n onFinishProgressCall,\n onEndedCall,\n } = params;\n const updateRemoteStreams = resolveUpdateRemoteStreams({\n setRemoteStreams,\n getRemoteStreams: resolveGetRemoteStreams(sipConnector),\n });\n const handleChangeTracks = resolveHandleChangeTracks(updateRemoteStreams);\n\n log('callToServer', params);\n\n const startCall = (): Promise<RTCPeerConnection> => {\n log('startCall');\n\n return sipConnector.call({\n mediaStream,\n extraHeaders,\n iceServers,\n degradationPreference,\n number: conference,\n ontrack: handleChangeTracks,\n });\n };\n let isSuccessProgressCall = false;\n let room: string;\n\n const subscribeEnterConference = () => {\n log('subscribeEnterConference: onEnterConference', onEnterConference);\n\n if (onEnterPurgatory || onEnterConference) {\n return sipConnector.onSession('enterRoom', (_room: string) => {\n log('enterRoom', { _room, isSuccessProgressCall });\n\n room = _room;\n\n if (hasPurgatory(room)) {\n if (onEnterPurgatory) {\n onEnterPurgatory();\n }\n } else if (onEnterConference) {\n onEnterConference({ isSuccessProgressCall });\n }\n });\n }\n\n return () => {};\n };\n\n const unsubscribeEnterConference = subscribeEnterConference();\n\n const onSuccess = (peerConnection: RTCPeerConnection): RTCPeerConnection => {\n log('onSuccess');\n\n isSuccessProgressCall = true;\n updateRemoteStreams();\n\n if (onSuccessProgressCall) {\n onSuccessProgressCall({ isPurgatory: hasPurgatory(room) });\n }\n\n sipConnector.onceRaceSession(['ended', 'failed'], () => {\n unsubscribeEnterConference();\n\n if (onEndedCall) {\n onEndedCall();\n }\n });\n\n return peerConnection;\n };\n\n const onFail = (error: Error): never => {\n log('onFail');\n\n if (onFailProgressCall) {\n onFailProgressCall();\n }\n\n unsubscribeEnterConference();\n\n throw error;\n };\n\n const onFinish = () => {\n log('onFinish');\n\n if (onFinishProgressCall) {\n onFinishProgressCall();\n }\n };\n\n log('onBeforeProgressCall');\n\n if (onBeforeProgressCall) {\n onBeforeProgressCall(conference);\n }\n\n return startCall().then(onSuccess).catch(onFail).finally(onFinish);\n };\n\n return callToServer;\n};\n\nexport default resolveCallToServer;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveDisconnectFromServer = (sipConnector: SipConnector) => {\n return () => {\n log('disconnectFromServer');\n\n return sipConnector\n .disconnect()\n .then(() => {\n log('disconnectFromServer: then');\n\n return false;\n })\n .catch((error) => {\n log('disconnectFromServer: catch', error);\n\n return false;\n });\n };\n};\n\nexport default resolveDisconnectFromServer;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveAskPermissionToEnableCam = (sipConnector: SipConnector): (() => Promise<void>) => {\n const askPermissionToEnableCam = (): Promise<void> => {\n if (!sipConnector.isCallActive) {\n return Promise.resolve();\n }\n\n log('askPermissionToEnableCam');\n\n return sipConnector.askPermissionToEnableCam();\n };\n\n return askPermissionToEnableCam;\n};\n\nexport default resolveAskPermissionToEnableCam;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveStopShareSipConnector = ({ sipConnector }: { sipConnector: SipConnector }) => {\n const stopShareSipConnector = ({ isP2P = false }: { isP2P: boolean } = { isP2P: false }) => {\n log('stopShareSipConnector');\n\n return sipConnector\n .stopPresentation({\n isP2P,\n })\n .catch(log);\n };\n\n return stopShareSipConnector;\n};\n\nexport default resolveStopShareSipConnector;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveOnMustStopPresentation = (sipConnector: SipConnector) => {\n const onMustStopPresentation = (handler: () => void): (() => void) => {\n log('onMustStopPresentation');\n\n return sipConnector.onSession('mustStopPresentation', handler);\n };\n\n return onMustStopPresentation;\n};\n\nexport default resolveOnMustStopPresentation;\n","import type SipConnector from '../SipConnector';\nimport type { EUseLicense } from '../SipConnector';\nimport log from '../logger';\n\nconst resolveOnUseLicense = (sipConnector: SipConnector) => {\n const onUseLicense = (handler: (license: EUseLicense) => void): (() => void) => {\n log('onUseLicense');\n\n return sipConnector.onSession('useLicense', handler);\n };\n\n return onUseLicense;\n};\n\nexport default resolveOnUseLicense;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveSendMediaState = (sipConnector: SipConnector) => {\n const sendMediaState = ({ isEnabledCam, isEnabledMic }): Promise<void> => {\n if (!sipConnector.isCallActive) {\n return Promise.resolve();\n }\n\n log('sendMediaState');\n\n return sipConnector.sendMediaState({ cam: isEnabledCam, mic: isEnabledMic });\n };\n\n return sendMediaState;\n};\n\nexport default resolveSendMediaState;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveSendRefusalToTurnOnCam = (sipConnector: SipConnector) => {\n const sendRefusalToTurnOnCam = (): Promise<void> => {\n if (!sipConnector.isCallActive) {\n return Promise.resolve();\n }\n\n log('sendRefusalToTurnOnCam');\n\n return sipConnector.sendRefusalToTurnOnCam().catch((error) => {\n log('sendRefusalToTurnOnCam: error', error);\n });\n };\n\n return sendRefusalToTurnOnCam;\n};\n\nexport default resolveSendRefusalToTurnOnCam;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst resolveSendRefusalToTurnOnMic = (sipConnector: SipConnector) => {\n const sendRefusalToTurnOnMic = (): Promise<void> => {\n if (!sipConnector.isCallActive) {\n return Promise.resolve();\n }\n\n log('sendRefusalToTurnOnMic');\n\n return sipConnector.sendRefusalToTurnOnMic().catch((error) => {\n log('sendRefusalToTurnOnMic: error', error);\n });\n };\n\n return sendRefusalToTurnOnMic;\n};\n\nexport default resolveSendRefusalToTurnOnMic;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst ONE_MEGABIT_IN_BITS = 1e6;\n\nconst resolveStartPresentation = ({\n maxBitrate = ONE_MEGABIT_IN_BITS,\n sipConnector,\n}: {\n maxBitrate?: number;\n sipConnector: SipConnector;\n}) => {\n const startPresentation = ({\n mediaStream,\n isP2P = false,\n }: {\n mediaStream: MediaStream;\n isP2P: boolean;\n }): Promise<MediaStream | void> => {\n log('startPresentation');\n\n return sipConnector.startPresentation(mediaStream, {\n isP2P,\n maxBitrate,\n });\n };\n\n return startPresentation;\n};\n\nexport default resolveStartPresentation;\n","import type SipConnector from '../SipConnector';\nimport log from '../logger';\n\nconst ONE_MEGABIT_IN_BITS = 1e6;\n\nconst resolveUpdatePresentation = ({\n sipConnector,\n maxBitrate = ONE_MEGABIT_IN_BITS,\n}: {\n maxBitrate?: number;\n sipConnector: SipConnector;\n}) => {\n const updatePresentation = ({\n mediaStream,\n isP2P = false,\n }: {\n mediaStream: MediaStream;\n isP2P: boolean;\n }): Promise<MediaStream | void> => {\n log('updatePresentation');\n\n return sipConnector.updatePresentation(mediaStream, {\n isP2P,\n maxBitrate,\n });\n };\n\n return updatePresentation;\n};\n\nexport default resolveUpdatePresentation;\n","import sequentPromises from 'sequent-promises';\nimport flow from 'lodash/flow';\nimport split from 'lodash/split';\n\ntype TSendKey = (values: string) => Promise<void>;\n\nconst wrapKeysToSend = (sendKey: TSendKey) => {\n return flow(\n (keys: string): string[] => {\n return split(keys, '');\n },\n (keyArray: string[]) => {\n return keyArray.map((key) => {\n return () => {\n return sendKey(key);\n };\n });\n },\n );\n};\nconst sendDTMFAccumulated = ({\n accumulatedKeys,\n sendKey,\n canRunTask,\n}: {\n accumulatedKeys: string;\n sendKey: TSendKey;\n canRunTask?: () => boolean;\n}): Promise<{\n isSuccessful: boolean;\n}> => {\n const wrapperSendKeys = wrapKeysToSend(sendKey);\n const tasks = wrapperSendKeys(accumulatedKeys);\n\n return sequentPromises<void>(tasks, canRunTask);\n};\n\nexport default sendDTMFAccumulated;\n"],"names":["getCodecFromSender","sender","getStats","then","stats","codec","type","results","keys","map","key","get","statsReportToArray","find","value","mimeType","BYE","UA_SYNTHETICS_EVENT_NAMES","UA_JSSIP_EVENT_NAMES","SESSION_SYNTHETICS_EVENT_NAMES","SESSION_JSSIP_EVENT_NAMES","UA_EVENT_NAMES","SESSION_EVENT_NAMES","parseDisplayName","displayName","trim","replace","generateUserId","min","max","Math","floor","random","prepareMediaStream","mediaStream","videoMode","audioMode","tracks","getAudioTracks","getVideoTracks","newStream","MediaStream","getTracks","resolveHasNeedToUpdateItemEncoding","defaultValue","itemEncodingTarget","itemEncodingCurrent","undefined","hasNeedToUpdateScaleResolutionDownBy","hasNeedToUpdateMaxBitrate","setEncodingsToSender","encodingsTarget","onSetParameters","parameters","getParameters","encodings","length","encoding","scaleResolutionDownByCurrent","scaleResolutionDownBy","scaleResolutionDownByTarget","scaleResolutionDownByTargetParsed","performUpdateScaleResolutionDownBy","isChanged","maxBitrateCurrent","maxBitrate","maxBitrateTarget","performUpdateMaxBitrate","setParameters","Promise","resolve","EEventsMainCAM","EEventsMic","EEventsSyncMediaState","EUseLicense","hasCanceledCallError","error","Error","originator","cause","isCanceledError","moduleName","SipConnector","constructor","JsSIP","this","_isRegisterConfig","_connectionConfiguration","_remoteStreams","getSipServerUrl","id","connect","data","_cancelRequests","_cancelableConnect","request","createUa","_cancelableCreateUa","set","_cancelableSet","call","_cancelableCall","disconnect","_disconnectWithoutCancelRequests","answerToIncomingCall","_cancelableAnswer","sendDTMF","tone","_cancelableSendDTMF","hangUp","_hangUpWithoutCancelRequests","tryRegister","isRegisterConfig","_uaEvents","trigger","unregister","finally","register","reject","declineToIncomingCall","statusCode","isAvailableIncomingCall","incomingSession","callerData","remoteCallerData","cancelRequest","removeIncomingSession","terminate","status_code","busyIncomingCall","handleNewRTCSession","session","on","_connect","params","_start","_createUa","user","password","sipServerUrl","sipWebSocketServerURL","remoteAddress","extraHeaders","sdpSemantics","sessionTimers","registerExpires","connectionRecoveryMinInterval","connectionRecoveryMaxInterval","userAgent","__awaiter","authorizationUser","_init","configuration","display_name","user_agent","sdp_semantics","sockets","socket","uri","session_timers","register_expires","connection_recovery_min_interval","connection_recovery_max_interval","ua","UA","eachTriggers","eventName","uaJsSipEvent","jsSipEvent","extraHeadersRemoteAddress","headers","push","getExtraHeadersRemoteAddress","extraHeadersBase","registrator","setExtraHeaders","resolveUa","removeEventListeners","rejectError","off","addEventListeners","start","_set","changedDisplayName","changedPassword","changedSome","catch","_cancelableDisconnect","_disconnect","disconnectedPromise","once","stop","_call","number","ontrack","iceServers","degradationPreference","offerToReceiveAudio","offerToReceiveVideo","answer","_handleCall","eventHandlers","_sessionEvents","triggers","pcConfig","rtcOfferConstraints","_answer","sessionJsSipEvent","remote_identity","preparedMediaStream","removeStartedEventListeners","offSession","handlePeerConnection","handleConfirmed","removeEndedEventListeners","handleEnded","savedPeerconnection","peerconnection","track","onSession","addStartedEventListeners","addEndedEventListeners","_restoreSession","_resetPresentation","_sendDTMF","onceSession","duration","interToneGap","_streamPresentationCurrent","stopPresentation","isEnded","_handleShareState","_maybeTriggerChannels","inputChannels","getHeader","outputChannels","headersChannels","_handleNotify","header","cmd","channelsInfo","_triggerChannelsNotify","webcastInfo","_triggerWebcastStartedNotify","_triggerWebcastStoppedNotify","_triggerAddedToListModeratorsNotify","_triggerRemovedFromListModeratorsNotify","_triggerParticipantMoveRequestToConference","_triggerParticipantCancelingWordRequest","_triggerParticipantMoveRequestToStream","_triggerAccountChangedNotify","_triggerAccountDeletedNotify","_triggerConferenceParticipantTokenIssued","conference","headersParametersModeratorsList","body","headersParametersWebcast","participant","jwt","headersConferenceParticipantTokenIssued","input","output","_triggerEnterRoom","room","_triggerShareState","_triggerMainCamControl","mainCam","syncState","isSyncForced","ADMIN_SYNC_FORCED","ADMIN_START_MAIN_CAM","ADMIN_STOP_MAIN_CAM","RESUME_MAIN_CAM","PAUSE_MAIN_CAM","resolutionMainCam","_triggerMicControl","mic","ADMIN_START_MIC","ADMIN_STOP_MIC","_triggerUseLicense","license","_handleNewInfo","info","contentType","_maybeHandleNotify","_handleSipEvent","headerNotify","headerNotifyParsed","JSON","parse","_handleEnded","Events","CancelableRequest","afterCancelRequest","isRegistered","sendOptions","target","succeeded","failed","ping","replaceMediaStream","options","askPermissionToEnableCam","noTerminateWhenError","sendInfo","message","hasDeclineResponseFromServer","isPendingPresentation","promisePendingStartPresentation","promisePendingStopPresentation","_sendPresentation","stream","isNeedReinvite","isP2P","streamPresentationCurrent","preparatoryHeaders","result","startPresentation","connection","senders","includes","findSenderByStream","scaleBitrate","getSenders","establishedSession","streamPresentationPrev","updatePresentation","handler","onceRace","eventNames","wait","onceRaceSession","waitSession","isConfigured","getConnectionConfiguration","Object","assign","getRemoteStreams","remoteTracks","getReceivers","some","remoteTrack","kind","hasVideoTracks","_generateStreams","_generateAudioStreams","_a","_b","host","_d","_c","incomingNumber","_f","_e","requested","isEstablished","isCallActive","serverUrl","WebSocketInterface","_generateStream","videoTrack","audioTrack","remoteStream","addTrack","_generateAudioStream","remoteStreams","forEach","index","prevTrack","_cancelActionsRequests","_cancelCallRequests","_cancelConnectRequests","waitChannels","waitSyncMediaState","sendChannels","sendMediaState","cam","_sendRefusalToTurnOn","sendRefusalToTurnOnMic","sendRefusalToTurnOnCam","hasIncludesString","source","toLowerCase","megabitsToBits","mb","MINIMUM_BITRATE","MAXIMUM_BITRATE","scaleBitrateByCodec","bitrate","hasAv1Codec","getMaxBitrateByWidthAndCodec","maxWidth","getMaxBitrateByWidth","stackPromises","createStackPromises","run","action","add","console","debug","addToStackScaleResolutionDownBySender","downgradeResolutionSender","getMinimumBitrate","setBitrateByTrackResolution","widthCurrent","getSettings","width","processSender","MAX_MAIN_CAM_RESOLUTION","resolution","settings","heightCurrent","height","widthTarget","heightTarget","split","scaleByWidth","scaleByHeight","setResolutionSender","resultNoChanged","transactionId","codecs","headerExtensions","rtcp","balance","ignoreForCodec","findVideoSender","resolveVideoSendingBalancer","sipConnector","balanceByTrack","reBalance","handleMainCamControl","subscribe","unsubscribe","resetMainCamControl","getLinkError","url","link","to","EErrorTypes","CONNECT_SERVER_FAILED","WRONG_USER_OR_PASSWORD","BAD_MEDIA_ERROR","NOT_FOUND_ERROR","_ws","readyState","WS_CONNECTION_FAILED","CONNECT_SERVER_FAILED_BY_LINK","code","values","NAME","logger","enableDebug","enable","disableDebug","hasPurgatory","resolveGetRemoteStreams","log","resolveHandleChangeTracks","updateRemoteStreams","hasVideoTrackReady","resolveUpdateRemoteStreams","setRemoteStreams","debounce","resolveWhenElseSyncForced","whenSyncForced","whenNotSyncForced","subscribeStartMainCam","resolveOnStartMainCam","subscribeStopMainCam","resolveOnStopMainCam","subscribeStartMic","resolveOnStartMic","subscribeStopMic","resolveOnStopMic","unsubscribeStartMainCam","unsubscribeStopMainCam","unsubscribeStartMic","unsubscribeStopMic","handlers","onStartMainCamForced","onStartMainCamNotForced","onStopMainCamForced","onStopMainCamNotForced","onStartMicForced","onStartMicNotForced","onStopMicForced","onStopMicNotForced","handleStartMainCam","handleStopMainCam","handleStartMic","handleStopMic","subscribeSyncCommands","onBeforeProgressCall","onSuccessProgressCall","onEnterPurgatory","onEnterConference","onFailProgressCall","onFinishProgressCall","onEndedCall","handleChangeTracks","isSuccessProgressCall","unsubscribeEnterConference","_room","getIncomingNumber","peerConnection","isPurgatory","isEnabledCam","isEnabledMic","accumulatedKeys","sendKey","canRunTask","wrapperSendKeys","flow","keyArray","wrapKeysToSend","tasks","sequentPromises"],"mappings":"oUAAA,MAYMA,EAAsBC,GACnBA,EAAOC,WAAWC,MAAMC,IAC7B,MAAMC,GAR2CC,EAQT,QAdjB,CAACC,GACnB,IAAIA,EAAQC,QAAQC,KAAKC,GACvBH,EAAQI,IAAID,KAKdE,CAO4BR,GAPAS,MAAMC,GAChCA,EAAMR,OAASA,KAFC,IAA0BA,EAUjD,OAAOD,eAAAA,EAAOU,iTCfX,MAeMC,EAAM,kEAfa,mCACD,mCACC,kCACF,sBAEV,gBACI,sBACE,yBACC,wBACF,+BACS,sCACF,+BACL,mCACS,0CAGR,wBACJ,qBACC,oBACF,iBACD,sBACM,wCACY,iDACH,oCACV,gBCzBpB,MCwEMC,EAA4B,CDxEZ,eACS,uBAEE,yBADJ,qBAgCe,qCADD,qCADI,yCAVvB,kBAiBoB,sCAFpB,kBACA,kBAHA,kBACA,kBANqB,uCACI,4CC2D3CC,EAAuB,CDtFV,aACD,YACG,eACG,gBACL,aACE,eACO,qBACR,aACF,YC0FZC,EAAiC,CDzFM,8BACI,iCACZ,uBACjB,aACD,YACC,aACc,2BACF,yBACf,WAES,mBACD,mBAEI,uBADD,sBAEL,iBACC,kBACa,gCC4F/BC,EAA4B,CDjFpB,QApCK,aAqCH,UACC,WACA,WACH,QACG,WACA,WACC,YACM,iBACT,SACD,QACE,UACC,UACA,UACJ,OACE,SACA,SACH,MACU,eACQ,qBACc,mCACC,oCAElD,2CAEA,4CACgC,qBACE,uBACJ,mBACE,qBACC,uBCoFtBC,EAAiB,IAAIH,KAAyBD,GAE9CK,EAAsB,IAC9BF,KACAD,gMCxJL,MAKaI,EAAoBC,GACxBA,EAAYC,OAAOC,QAAQ,KAAM,KAE7BC,GARaC,EAQqB,IARRC,EAQgB,SAP9C,IACEC,KAAKC,MAAMD,KAAKE,UAAYH,EAAMD,IAAQA,GAF5B,IAACA,EAAaC,EAUhC,MAAMI,EAAqB,CAChCC,GAEEC,YACAC,aAIE,MAEJ,IAAKF,GAA8B,aAAdC,GAA0C,aAAdC,EAC/C,OAGF,MAEMC,EAAS,IAFmB,aAAdD,EAA2B,GAAKF,EAAYI,oBAC9B,aAAdH,EAA2B,GAAKD,EAAYK,kBAE1DC,EAAY,IAAIC,YAAYJ,GAMlC,OAJAG,EAAUE,UAAY,IACb,IAAIF,EAAUF,oBAAqBE,EAAUD,kBAG/CC,GCnCHG,EAAsCC,GACnC,CAACC,EAAyCC,SAIrBC,IAAxBD,GAAqCD,IAAuBC,QAFpCC,IAAxBD,GAAqCD,IAAuBD,EAU5DI,EAAuCL,EAdR,GAuC/BM,EAA4BN,OAAmCI,GAY/DG,EAAuB,CAC3BjD,EACAkD,EACAC,KAEA,MAAMC,EAAmCpD,EAAOqD,gBAE3CD,EAAWE,WAA6C,IAAhCF,EAAWE,UAAUC,SAChDH,EAAWE,UAAY,CAAC,KAG1B,MAAOE,GAAYJ,EAAWE,UACxBG,EAA+BD,EAASE,sBACxCC,EA/CmC,EACzCA,EACAF,KAEA,MAAMG,OAC4Bd,IAAhCa,EACI9B,KAAKD,IAAI+B,EAvBoB,GAwB7B,KAEN,GACwC,OAAtCC,GACAb,EACEa,EACAH,GAGF,OAAOG,GA+B2BC,CAClCX,EAAgBQ,sBAChBD,GAGF,IAAIK,GAAY,OAEoBhB,IAAhCa,IACFP,EAAWE,UAAU,GAAGI,sBAAwBC,EAChDG,GAAY,GAGd,MAAMC,EAAoBP,EAASQ,WAC7BC,EArCwB,EAC9BA,EACAF,KAEA,GAAIf,EAA0BiB,EAAkBF,GAC9C,OAAOE,GAgCgBC,CAAwBhB,EAAgBc,WAAYD,GAO7E,YALyBjB,IAArBmB,IACFb,EAAWE,UAAU,GAAGU,WAAaC,EACrCH,GAAY,GAGVA,GACEX,GACFA,EAAgBC,GAGXpD,EAAOmE,cAAcf,GAAYlD,MAAK,KACpC,CAAEkD,aAAYU,iBAIlBM,QAAQC,QAAQ,CAAEjB,aAAYU,eCqBvC,IAAYQ,EAQAC,EAKAC,EAKAC,GAlBZ,SAAYH,GACVA,EAAA,eAAA,eACAA,EAAA,gBAAA,gBACAA,EAAA,wBAAA,uBACAA,EAAA,oBAAA,mBACAA,EAAA,qBAAA,oBALF,CAAYA,IAAAA,EAMX,KAED,SAAYC,GACVA,EAAA,eAAA,eACAA,EAAA,gBAAA,gBAFF,CAAYA,IAAAA,EAGX,KAED,SAAYC,GACVA,EAAA,kBAAA,IACAA,EAAA,sBAAA,IAFF,CAAYA,IAAAA,EAGX,KAED,SAAYC,GACVA,EAAA,MAAA,QACAA,EAAA,MAAA,QACAA,EAAA,sBAAA,wBAHF,CAAYA,IAAAA,EAIX,KAWY,MAAAC,EAAuB,CAACC,EAAsB,IAAIC,SAC7D,MAAMC,WAAEA,EAAUC,MAAEA,GAAUH,EAE9B,QAAII,EAAgBJ,IAIC,iBAAVG,IL5JkB,oBK8JzBA,GLzJkB,aK0JlBA,GA9CmB,UA+ClBD,ILhJiB,aKgJmBC,GAAsBA,IAAU/D,KAOrEiE,EAAa,eAkKL,MAAOC,EAuDnBC,aAAYC,MAAEA,IAtDNC,KAAiBC,mBAAG,EAEpBD,KAAwBE,yBAQ5B,GAEIF,KAAcG,eAAmC,GAyBjDH,KAAAI,gBAA2CC,GAC1CA,EAsETL,KAAAM,QAAqBC,IACnBP,KAAKQ,kBAEER,KAAKS,mBAAmBC,QAAQH,IAGzCP,KAAAW,SAAuBJ,GACdP,KAAKY,oBAAoBF,QAAQH,GAG1CP,KAAAa,IAAaN,GACJP,KAAKc,eAAeJ,QAAQH,GAGrCP,KAAAe,KAAeR,GACNP,KAAKgB,gBAAgBN,QAAQH,GAGtCP,KAAUiB,WAAgB,KACxBjB,KAAKQ,kBAEER,KAAKkB,oCAGdlB,KAAAmB,qBAA+CZ,GACtCP,KAAKoB,kBAAkBV,QAAQH,GAGxCP,KAAAqB,SAAuBC,GACdtB,KAAKuB,oBAAoBb,QAAQY,GAG1CtB,KAAMwB,OAAY,KAChBxB,KAAKQ,kBAEER,KAAKyB,gCA0BdzB,KAAW0B,YAAG,IACP1B,KAAK2B,kBAIV3B,KAAK4B,UAAUC,QJtfO,kBIsfanE,GAE5BsC,KAAK8B,aACTC,SAAQ,IACA/B,KAAKgC,aAEbD,SAAQ,UATF/C,QAAQiD,OAAO,IAAIzC,MAAM,6BAgEpCQ,KAAqBkC,sBAAG,EAAGC,aArcU,KAqcsC,KAClE,IAAInD,SAAQ,CAACC,EAASgD,KAC3B,IAAKjC,KAAKoC,wBAGR,YAFAH,EAAO,IAAIzC,MAAM,uBAKnB,MAAM6C,EAAkBrC,KAAMqC,gBACxBC,EAAatC,KAAKuC,iBAExBvC,KAAKgB,gBAAgBwB,gBACrBxC,KAAKoB,kBAAkBoB,gBAEvBxC,KAAKyC,wBACLzC,KAAK4B,UAAUC,QJrkBiB,uBIqkBeS,GAC/CrD,EAAQoD,EAAgBK,UAAU,CAAEC,YAAaR,QAMrDnC,KAAgB4C,iBAAG,IACV5C,KAAKkC,sBAAsB,CAAEC,WA7dV,MAge5BnC,KAAqByC,sBAAG,YACfzC,KAAKqC,iBA8MdrC,KAAmB6C,oBAAG,EAAGpD,aAAYqD,cACnC,GA7qBsB,WA6qBlBrD,EAAkC,CACpCO,KAAKqC,gBAAkBS,EAEvB,MAAMR,EAAatC,KAAKuC,iBAExBO,EAAQC,GJrvBQ,UIqvBG,EAAGtD,iBACpBO,KAAKyC,wBAprBY,UAsrBbhD,EACFO,KAAK4B,UAAUC,QJxyBW,qBIwyBmBS,GAE7CtC,KAAK4B,UAAUC,QJzyBe,yBIyyBmBS,MAIrDtC,KAAK4B,UAAUC,QJhzBQ,eIgzBeS,KAoH1CtC,KAAAgD,SAAsBC,GACbjD,KAAKW,SAASsC,GAAQnI,MAAK,IACzBkF,KAAKkD,WAIhBlD,KAAAmD,UAAuB,EACrBhH,cAAc,GACdiH,OACAC,WACArB,YAAW,EACXsB,eACAC,wBACAC,gBACAC,eAAe,GACfC,eAAe,SACfC,iBAAgB,EAChBC,kBAAkB,IAClBC,gCAAgC,EAChCC,gCAAgC,EAChCC,eACGC,EAAAhE,UAAA,OAAA,GAAA,YACH,IAAKsD,EACH,MAAM,IAAI9D,MAAM,4BAGlB,IAAK+D,EACH,MAAM,IAAI/D,MAAM,qCAGlB,GAAIwC,IAAaoB,EACf,MAAM,IAAI5D,MAAM,8CAGlB,GAAIwC,IAAaqB,EACf,MAAM,IAAI7D,MAAM,kDAalB,IAAIyE,EAVJjE,KAAKE,yBAA2B,CAC9BoD,eACAnH,cACA6F,WACAoB,OACAC,YAGFrD,KAAKkE,MAAM,CAAEZ,eAAcC,0BAKzBU,EADEjC,GAAYoB,EACMA,EAAKhH,OAELE,IAGtB,MAAM6H,EAAgB,CACpBd,WACArB,WACAoC,aAAclI,EAAiBC,GAC/BkI,WAAYN,EACZO,cAAeZ,EACfa,QAAS,CAACvE,KAAKwE,QACfC,IAAKzE,KAAKI,gBAAgB6D,GAC1BS,eAAgBf,EAChBgB,iBAAkBf,EAElBgB,iCAAkCf,EAClCgB,iCAAkCf,GAGhC9D,KAAK8E,WACD9E,KAAKkB,oCAGblB,KAAKC,oBAAsBkE,EAAcnC,SACzChC,KAAK8E,GAAK,IAAI9E,KAAKD,MAAMgF,GAAGZ,GAE5BnE,KAAK4B,UAAUoD,cAAa,CAACnD,EAASoD,KACpC,MAAMC,EAAerJ,EAAqBL,MAAM2J,GACvCA,IAAeF,IAGpBC,GACFlF,KAAK8E,GAAI/B,GAAGmC,EAAcrD,MAI9B,MAAMuD,EC5/B0B,CAAC5B,IACnC,MAAM6B,EAAoB,GAM1B,OAJI7B,GACF6B,EAAQC,KAAK,oBAAoB9B,KAG5B6B,GDq/B6BE,CAA6B/B,GACzDgC,EAAmB,IAAIJ,KAA8B3B,GAI3D,OAFAzD,KAAK8E,GAAIW,cAAcC,gBAAgBF,GAEhCxF,KAAK8E,MAQd9E,KAAMkD,OAAW,IACR,IAAIlE,SAAQ,CAACC,EAASgD,KAC3B,MAAM0D,EAAY,KAChBC,IACA3G,EAAQe,KAAK8E,KAETe,EAAetG,IACnBqG,IACA3D,EAAO1C,IAYHqG,EAAuB,KAC3B5F,KAAK8F,IJthCa,aIshCGH,GACrB3F,KAAK8F,IJrhCsB,qBIqhCGD,GAC9B7F,KAAK8F,IJ3hCY,YI2hCGH,GACpB3F,KAAK8F,IJ3hCe,eI2hCGD,IAdC,MACpB7F,KAAK2B,kBACP3B,KAAK+C,GJ7gCW,aI6gCI4C,GACpB3F,KAAK+C,GJ5gCoB,qBI4gCI8C,IAE7B7F,KAAK+C,GJnhCU,YImhCI4C,GAGrB3F,KAAK+C,GJrhCe,eIqhCE8C,IASxBE,GACA/F,KAAK+C,GJ9hCoB,gBI8hCA/C,KAAK6C,qBAE9B7C,KAAK8E,GAAIkB,WAIbhG,KAAIiG,KAAS,EAAG9J,cAAakH,cACpB,IAAIrE,SAAQ,CAACC,EAASgD,KAC3B,IAAIiE,GAAqB,EACrBC,GAAkB,OAEFzI,IAAhBvB,GAA6BA,IAAgB6D,KAAKE,yBAAyB/D,cAC7E+J,EAAqBlG,KAAK8E,GAAIjE,IAAI,eAAgB3E,EAAiBC,IACnE6D,KAAKE,yBAAyB/D,YAAcA,QAG7BuB,IAAb2F,GAA0BA,IAAarD,KAAKE,yBAAyBmD,WACvE8C,EAAkBnG,KAAK8E,GAAIjE,IAAI,WAAYwC,GAC3CrD,KAAKE,yBAAyBmD,SAAWA,GAG3C,MAAM+C,EAAcF,GAAsBC,EAEtCA,GAAmBnG,KAAK2B,iBAC1B3B,KAAKgC,WACFlH,MAAK,IACGmE,EAAQmH,KAEhBC,MAAMpE,GACAmE,EACTnH,EAAQmH,GAERnE,EAAOmE,MAKbpG,KAAgCkB,iCAAgB,IACvClB,KAAKsG,sBAAsB5F,UAGpCV,KAAWuG,YAAG,IAAWvC,EAAAhE,UAAA,OAAA,GAAA,YACvBA,KAAK8F,IJxkCsB,gBIwkCD9F,KAAK6C,qBAE/B,MAAM2D,EAAsB,IAAIxH,SAAeC,IAC7Ce,KAAKyG,KJ5kCiB,gBI4kCE,YACfzG,KAAK8E,GACZ7F,UAgBJ,OAZIe,KAAK8E,UACD9E,KAAKyB,+BAEPzB,KAAK8E,GACP9E,KAAK8E,GAAG4B,OAER1G,KAAK4B,UAAUC,QJxlCK,oBIwlCiBnE,IAGvCsC,KAAK4B,UAAUC,QJ3lCO,oBI2lCenE,GAGhC8I,KAGTxG,KAAA2G,MAAe,EACbC,SACA/J,cACA4G,eAAe,GACfoD,UACAC,aACAhK,YACAC,YACAgK,wBACAC,uBAAsB,EACtBC,uBAAsB,KAEf,IAAIjI,SAAQ,CAACC,EAASgD,KAC3BjC,KAAKE,yBAAyB0G,OAASA,EACvC5G,KAAKE,yBAAyBgH,QAAS,EACvClH,KAAKmH,YAAY,CAAEN,YAAW/L,KAAKmE,GAASoH,MAAMpE,GAElDjC,KAAK8C,QAAU9C,KAAK8E,GAAI/D,KAAKf,KAAKI,gBAAgBwG,GAAS,CACzDnD,eACA5G,YAAaD,EAAmBC,EAAa,CAC3CC,YACAC,cAEFqK,cAAepH,KAAKqH,eAAeC,SACnCxK,YACAC,YACAgK,wBACAQ,SAAU,CACRT,cAEFU,oBAAqB,CACnBR,sBACAC,4BAMRjH,KAAOyH,QAA0B,EAC/B5K,cACAgK,UACApD,eAAe,GACfqD,aACAhK,YACAC,YACAgK,2BAEO,IAAI/H,SAAQ,CAACC,EAASgD,KAC3B,IAAKjC,KAAKoC,wBAGR,YAFAH,EAAO,IAAIzC,MAAM,uBAKnBQ,KAAK8C,QAAU9C,KAAKqC,gBACpBrC,KAAKyC,wBAEL,MAAMK,EAAU9C,KAAK8C,QAErB,IAAKA,EAGH,YAFAb,EAAO,IAAIzC,MAAM,2BAKnBQ,KAAKqH,eAAerC,cAAa,CAACnD,EAASoD,KACzC,MAAMyC,EAAoB3L,EAA0BP,MAAM2J,GACjDA,IAAeF,IAGpByC,GACF5E,EAAQC,GAAG2E,EAAmB7F,MAIlC7B,KAAKE,yBAAyBgH,QAAS,EACvClH,KAAKE,yBAAyB0G,OAAS9D,EAAQ6E,gBAAgBlD,IAAIrB,KACnEpD,KAAKmH,YAAY,CAAEN,YAAW/L,KAAKmE,GAASoH,MAAMpE,GAElD,MAAM2F,EAAsBhL,EAAmBC,EAAa,CAC1DC,YACAC,cAGF+F,EAAQoE,OAAO,CACbzD,eACA3G,YACAC,YACAgK,wBACAlK,YAAa+K,EACbL,SAAU,CACRT,mBAQR9G,KAAAmH,YAAc,EAAGN,aACR,IAAI7H,SAAQ,CAACC,EAASgD,KAC3B,MAIM4F,EAA8B,KAClC7H,KAAK8H,WJjqCkB,iBIiqCUC,GACjC/H,KAAK8H,WJnqCY,YImqCUE,IAMvBC,EAA4B,KAChCjI,KAAK8H,WJxqCS,SIwqCUI,GACxBlI,KAAK8H,WJlrCQ,QIkrCUI,IAEnBA,EAAe3I,IACnBsI,IACAI,IACAhG,EAAO1C,IAGT,IAAI4I,EAEJ,MAAMJ,EAAuB,EAAGK,qBAC9BD,EAAsBC,EAEtBD,EAAoBtB,QAAWwB,IAC7BrI,KAAKqH,eAAexF,QJptCS,yBIotCwBsG,GAEjDtB,GACFA,EAAQwB,KAIRL,EAAkB,KAClBG,GACFnI,KAAKqH,eAAexF,QJ9tCW,2BI8tCwBsG,GAGzDN,IACAI,IACAhJ,EAAQkJ,IA1CuB,MAC/BnI,KAAKsI,UJ7pCkB,iBI6pCSP,GAChC/H,KAAKsI,UJ/pCY,YI+pCSN,IA2C5BO,GArC+B,MAC7BvI,KAAKsI,UJpqCS,SIoqCSJ,GACvBlI,KAAKsI,UJ9qCQ,QI8qCSJ,IAoCxBM,MAIJxI,KAAeyI,gBAAe,KAC5BzI,KAAK0I,4BAEE1I,KAAKE,yBAAyB0G,cAC9B5G,KAAK8C,QACZ9C,KAAKG,eAAiB,IAGxBH,KAAA2I,UAAwBrH,GACf,IAAItC,SAAc,CAACC,EAASgD,KACjC,MAAMa,EAAU9C,KAAK8C,QAEhBA,GAML9C,KAAK4I,YJ5tCa,WI4tCS,EAAGnJ,iBA7pCX,UA8pCbA,GACFR,OAIJ6D,EAAQzB,SAASC,EAAM,CACrBuH,SAAU,IACVC,aAAc,OAbd7G,EAAO,IAAIzC,MAAM,8BA6EvBQ,KAA4ByB,6BAAY,IAAWuC,EAAAhE,UAAA,OAAA,GAAA,YACjD,GAAIA,KAAK8E,IAAM9E,KAAK8C,QAAS,CAC3B,MAAMA,QAAEA,GAAY9C,KAEhBA,KAAK+I,mCACD/I,KAAKgJ,oBAGbhJ,KAAKyI,kBAEA3F,EAAQmG,WACXnG,EAAQJ,gBAyBd1C,KAAAkJ,kBAAqBjE,IACnB,OAAQA,GACN,IEj2CwC,uBFk2CtCjF,KAAKqH,eAAexF,QJl3CwB,mCIk3CsBnE,GAClE,MACF,IEn2C4C,aFo2C1CsC,KAAKqH,eAAexF,QJp3C4B,sCIo3CsBnE,GACtE,MACF,IEr2CgC,yBFs2C9BsC,KAAKqH,eAAexF,QJt3CgB,4BIs3CsBnE,KAQhEsC,KAAAmJ,sBAAyBzI,IACvB,MAAM0I,EAAgB1I,EAAQ2I,UEl4CG,2BFm4C3BC,EAAiB5I,EAAQ2I,UEl4CG,4BFo4ClC,GAAID,GAAiBE,EAAgB,CACnC,MAAMC,EAA6B,CACjCH,gBACAE,kBAGFtJ,KAAKqH,eAAexF,QJl4CF,WIk4CoB0H,KAI1CvJ,KAAAwJ,cAAiBC,IACf,GA/sCiB,aA+sCbA,EAAOC,IAAsB,CAC/B,MAAMC,EAAeF,EAErBzJ,KAAK4J,uBAAuBD,QACvB,GAltCiB,mBAktCbF,EAAOC,IAA6B,CAC7C,MAAMG,EAAcJ,EAEpBzJ,KAAK8J,6BAA6BD,QAC7B,GArtCiB,mBAqtCbJ,EAAOC,IAA6B,CAC7C,MAAMG,EAAcJ,EAEpBzJ,KAAK+J,6BAA6BF,QAC7B,GAttC0B,0BAstCtBJ,EAAOC,IAAsC,CACtD,MAAMnJ,EAAOkJ,EAEbzJ,KAAKgK,oCAAoCzJ,QACpC,GAztC8B,8BAytC1BkJ,EAAOC,IAA0C,CAC1D,MAAMnJ,EAAOkJ,EAEbzJ,KAAKiK,wCAAwC1J,QACxC,GA5tC4B,iCA4tCxBkJ,EAAOC,IAAwC,CACxD,MAAMnJ,EAAOkJ,EAEbzJ,KAAKkK,2CAA2C3J,QAC3C,GA/tCyB,iCA+tCrBkJ,EAAOC,IAAqC,CACrD,MAAMnJ,EAAOkJ,EAEbzJ,KAAKmK,wCAAwC5J,QACxC,GAluCwB,8BAkuCpBkJ,EAAOC,IAAoC,CACpD,MAAMnJ,EAAOkJ,EAEbzJ,KAAKoK,uCAAuC7J,QACvC,GA5uCiB,mBA4uCbkJ,EAAOC,IAChB1J,KAAKqK,oCACA,GA7uCiB,mBA6uCbZ,EAAOC,IAChB1J,KAAKsK,oCACA,GAzuCqC,qCAyuCjCb,EAAOC,IAAiD,CACjE,MAAMnJ,EAAOkJ,EAEbzJ,KAAKuK,yCAAyChK,KAIlDP,KAAAiK,wCAA0C,EACxCO,iBAEA,MAAMC,EAA6D,CACjED,cAGFxK,KAAK4B,UAAUC,QJ/6CqC,2CIi7ClD4I,IAIJzK,KAAAgK,oCAAsC,EAAGQ,iBACvC,MAAMC,EAA6D,CACjED,cAGFxK,KAAK4B,UAAUC,QJ37CiC,uCI27Ca4I,IAG/DzK,KAAA8J,6BAA+B,EAAGY,MAAQF,aAAYvP,YACpD,MAAM0P,EAA+C,CACnDH,aACAvP,QAGF+E,KAAK4B,UAAUC,QJ/7CY,kBI+7Ca8I,IAG1C3K,KAAA+J,6BAA+B,EAAGW,MAAQF,aAAYvP,YACpD,MAAM0P,EAA+C,CACnDH,aACAvP,QAGF+E,KAAK4B,UAAUC,QJv8CY,kBIu8Ca8I,IAG1C3K,KAA4BqK,6BAAG,KAC7BrK,KAAK4B,UAAUC,QJ18CY,uBI08CanE,IAG1CsC,KAA4BsK,6BAAG,KAC7BtK,KAAK4B,UAAUC,QJ78CY,uBI68CanE,IAG1CsC,KAAAuK,yCAA2C,EACzCG,MAAQF,aAAYI,cAAaC,WAEjC,MAAMC,EAAuF,CAC3FN,aACAI,cACAC,OAGF7K,KAAK4B,UAAUC,QJx9CgC,sCI09C7CiJ,IAIJ9K,KAAA4J,uBAA0BD,IACxB,MAGMpJ,EAAkB,CACtB6I,cAJoBO,EAAaoB,MAKjCzB,eAJqBK,EAAaqB,QAOpChL,KAAK4B,UAAUC,QJx/CY,kBIw/CatB,IAG1CP,KAA0CkK,2CAAG,EAC3CQ,MAAQF,kBAER,MAAMjK,EAAkC,CACtCiK,cAGFxK,KAAK4B,UAAUC,QJx/CmC,yCIw/CatB,IAGjEP,KAAuCmK,wCAAG,EACxCO,MAAQF,kBAER,MAAMjK,EAAkC,CACtCiK,cAGFxK,KAAK4B,UAAUC,QJhgDgC,qCIggDatB,IAG9DP,KAAsCoK,uCAAG,EACvCM,MAAQF,kBAER,MAAMjK,EAAkC,CACtCiK,cAGFxK,KAAK4B,UAAUC,QJ3gD+B,qCI2gDatB,IAG7DP,KAAAiL,kBAAqBvK,IACnB,MAAMwK,EAAOxK,EAAQ2I,UE9iDgB,uBFgjDrCrJ,KAAKqH,eAAexF,QJjiDE,YIiiDkBqJ,IAG1ClL,KAAAmL,mBAAsBzK,IACpB,MAAMuE,EAAYvE,EAAQ2I,UE5hDY,wBF8hDtCrJ,KAAKqH,eAAexF,QJxiDG,aIwiDkBoD,IAG3CjF,KAAAoL,uBAA0B1K,IACxB,MAAM2K,EAAU3K,EAAQ2I,UE9iDG,oBFgjDrBiC,EAAY5K,EAAQ2I,UE9iDG,iBF+iDvBkC,EAAeD,IAAclM,EAAsBoM,kBAEzD,GAAIH,IAAYnM,EAAeuM,qBAC7BzL,KAAKqH,eAAexF,QJxiDU,uBIwiDoB,CAAE0J,sBAC/C,GAAIF,IAAYnM,EAAewM,oBACpC1L,KAAKqH,eAAexF,QJ3iDS,sBI2iDoB,CAAE0J,sBAC9C,GACJF,IAAYnM,EAAeyM,iBAAmBN,IAAYnM,EAAe0M,iBACxEN,EAGG,CACL,MAAMO,EAAoBnL,EAAQ2I,UE1jDE,+BF4jDpCrJ,KAAKqH,eAAexF,QJrjDM,mBIqjDoB,CAC5CwJ,UACAQ,2BANF7L,KAAKqH,eAAexF,QJ5iDkB,+BI4iDoB,CAAE0J,kBAWhEvL,KAAA8L,mBAAsBpL,IACpB,MAAMqL,EAAMrL,EAAQ2I,UEtkDE,gBFwkDhBkC,EADY7K,EAAQ2I,UEtkDG,mBFukDMjK,EAAsBoM,kBAErDO,IAAQ5M,EAAW6M,gBACrBhM,KAAKqH,eAAexF,QJ9jDK,kBI8jDoB,CAAE0J,iBACtCQ,IAAQ5M,EAAW8M,gBAC5BjM,KAAKqH,eAAexF,QJjkDI,iBIikDoB,CAAE0J,kBAIlDvL,KAAAkM,mBAAsBxL,IACpB,MAAMyL,EAAuBzL,EAAQ2I,UEtlDC,wBFwlDtCrJ,KAAKqH,eAAexF,QJjlDG,aIilDkBsK,IAG3CnM,KAAAoM,eAAkBC,IAChB,MAAM5M,WAAEA,GAAe4M,EAEvB,GAAmB,WAAf5M,EACF,OAGF,MAAMiB,EAAU2L,EAAK3L,QACf4L,EAAc5L,EAAQ2I,UE9mDQ,gBFgnDpC,GAAIiD,EACF,OAAQA,GACN,IE9mD+B,qCF+mD7BtM,KAAKiL,kBAAkBvK,GACvBV,KAAKmJ,sBAAsBzI,GAC3B,MACF,IE/lD2B,mCFgmDzBV,KAAKuM,mBAAmB7L,GACxB,MACF,IEtnDgC,yCFunD9BV,KAAKmL,mBAAmBzK,GACxB,MACF,IEpnD6B,oCFqnD3BV,KAAKoL,uBAAuB1K,GAC5B,MACF,IEtnDwB,gCFunDtBV,KAAK8L,mBAAmBpL,GACxB,MACF,IExnDgC,mCFynD9BV,KAAKkM,mBAAmBxL,KAShCV,KAAAwM,gBAAkB,EAAG9L,cACnBV,KAAKuM,mBAAmB7L,IAG1BV,KAAAuM,mBAAsB7L,IACpB,MAAM+L,EAAe/L,EAAQ2I,UEznDJ,mBF2nDzB,GAAIoD,EAAc,CAChB,MAAMC,EAAkCC,KAAKC,MAAMH,GAEnDzM,KAAKwJ,cAAckD,KAqFvB1M,KAAA6M,aAAgBtN,IACd,MAAME,WAAEA,GAAeF,EAxnDD,WA0nDlBE,GACFO,KAAKqH,eAAexF,QJxtDO,mBIwtDoBtC,GAGjDS,KAAKyI,mBA/2CLzI,KAAKD,MAAQA,EAEbC,KAAKqH,eAAiB,IAAIyF,EAAmC7Q,GAC7D+D,KAAK4B,UAAY,IAAIkL,EAA8B9Q,GAEnDgE,KAAKS,mBAAqB,IAAIsM,EAC5B/M,KAAKgD,SACL,CACEpD,aACAoN,mBAAoB,KAClBhN,KAAKY,oBAAoB4B,gBACzBxC,KAAKsG,sBAAsB9D,mBAKjCxC,KAAKY,oBAAsB,IAAImM,EAG7B/M,KAAKmD,UAAW,CAAEvD,eAEpBI,KAAKsG,sBAAwB,IAAIyG,EAC/B/M,KAAKuG,YACL,CAAE3G,eAGJI,KAAKc,eAAiB,IAAIiM,EAAyD/M,KAAKiG,KAAM,CAC5FrG,eAGFI,KAAKgB,gBAAkB,IAAI+L,EACzB/M,KAAK2G,MACL,CAAE/G,eAGJI,KAAKoB,kBAAoB,IAAI2L,EAG3B/M,KAAKyH,QAAS,CAAE7H,eAElBI,KAAKuB,oBAAsB,IAAIwL,EAG7B/M,KAAK2I,UAAW,CAAE/I,eAEpBI,KAAKsI,UJhakB,aIgaKtI,KAAKkJ,mBACjClJ,KAAKsI,UJ5Xe,UI4XKtI,KAAKoM,gBAC9BpM,KAAK+C,GJtagB,WIsaF/C,KAAKwM,iBAExBxM,KAAKsI,UJnYa,SImYKtI,KAAK6M,cAC5B7M,KAAKsI,UJ7YY,QI6YKtI,KAAK6M,cAyC7B7K,WACE,OAAO,IAAIhD,SAAQ,CAACC,EAASgD,KACvBjC,KAAK2B,kBACP3B,KAAK8E,GAAI/B,GJzdS,aIydM9D,GACxBe,KAAK8E,GAAI/B,GJxdkB,qBIwdMd,GACjCjC,KAAK8E,GAAI9C,YAETC,EAAO,IAAIzC,MAAM,gCAKvBsC,aACE,OAAO,IAAI9C,SAAQ,CAACC,EAASgD,KACvBjC,KAAKiN,cACPjN,KAAK8E,GAAI/B,GJpeW,eIoeM9D,GAC1Be,KAAK8E,GAAIhD,cAETG,EAAO,IAAIzC,MAAM,4BAqBvB0N,YAAYC,EAAsBzC,EAAejH,GAC/C,OAAKzD,KAAK8E,GAIH,IAAI9F,SAAQ,CAACC,EAASgD,KAC3B,IACEjC,KAAK8E,GAAGoI,YAAYC,EAAQzC,EAAM,CAChCjH,eACA2D,cAAe,CACbgG,UAAW,KACTnO,KAEFoO,OAAS9N,IACP0C,EAAO1C,OAIb,MAAOA,GACP0C,EAAO1C,OAjBFP,QAAQiD,OAAO,IAAIzC,MAAM,qBAsBpC8N,KAAK5C,EAAejH,GAClB,IAAKzD,KAAK8E,KAAO9E,KAAK8E,GAAGX,gBAAkBnE,KAAK8E,GAAGX,cAAcM,IAC/D,OAAOzF,QAAQiD,OAAO,IAAIzC,MAAM,qBAGlC,MAAM2N,EAASnN,KAAK8E,GAAGX,cAAcM,IAErC,OAAOzE,KAAKkN,YAAYC,EAAQzC,EAAMjH,GAGxC8J,mBACE1Q,EACA2Q,GAOA,IAAKxN,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,OAAOQ,KAAK8C,QAAQyK,mBAAmB1Q,EAAa2Q,GAiCtDC,yBACED,EAAkC,CAAEE,sBAAsB,IAE1D,IAAK1N,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,MAAMiE,EAAe,CExjBa,2DF0jBlC,OAAOzD,KAAK8C,QACT6K,SEvlB8B,yCFulBEjQ,iCAC5B8P,GAAO,CACV/J,kBAED4C,OAAO9G,IACN,GGlmBoC,CAACA,GAFf,2BAGrBA,EAAMqO,QHimBHC,CAA6BtO,GAC/B,MAAMA,KAOVuO,4BACF,QAAS9N,KAAK+N,mCAAqC/N,KAAKgO,+BAGlDC,kBACNnL,EACAoL,GACAtP,WACEA,EAAUmI,sBACVA,EAAqBoH,eACrBA,GAAiB,EAAIC,MACrBA,GAAQ,IAQV,MAAMC,EAA4BzR,EAAmBsR,GAErDlO,KAAK+I,2BAA6BsF,EAElC,MAAMC,EAAqBF,EACvB,CEpmBqC,8CFqmBrC,CE1mBiC,gDF4mB/BG,EAASzL,EACZ6K,SEroBiC,8CFqoBEjQ,EAAW,CAC7C+F,aAAc6K,IAEfxT,MAAK,IACGgI,EAAQ0L,kBACbH,EACAF,EACApH,KAIHjM,MAAK,KACJ,MAAM2T,WAAEA,GAAezO,KAEvB,IAAKyO,QAA6B/Q,IAAfkB,EACjB,OAKF,MIzpBwB,EAC9B8P,EACA7R,EACA+B,KAEA,MAAMhE,ECRmB,EACzB8T,EACAR,IAEOQ,EAAQlT,MAAMZ,GACZA,EAAOyN,OAAS6F,EAAO7Q,YAAYsR,SAAS/T,EAAOyN,SDG7CuG,CAAmBF,EAAS7R,GAE3C,OAAIjC,EACKiD,EAAqBjD,EAAQ,CAAEgE,eAGjCI,QAAQC,WJ8oBF4P,CAFSJ,EAAWK,aAEEZ,EAAQtP,MAEtC9D,MAAK,IACGoT,IAER7H,OAAO9G,IAGN,MAFAS,KAAKqH,eAAexF,QJ5lBO,sBI4lBsBtC,GAE3CA,KAKV,OAFAS,KAAK+N,gCAAkCQ,EAEhCA,EAAOxM,SAAQ,KACpB/B,KAAK+N,qCAAkCrQ,KAI3C8Q,kBACEN,GACAC,eACEA,GAAiB,EAAIC,MACrBA,GAAQ,EAAKxP,WACbA,EAAUmI,sBACVA,GAME,IAEJ,MAAMjE,EAAU9C,KAAK+O,mBAErB,OAAKjM,EAID9C,KAAK+I,2BACA/J,QAAQiD,OAAO,IAAIzC,MAAM,oCAG3BQ,KAAKiO,kBAAkBnL,EAASoL,EAAQ,CAC7CC,iBACAC,QACAxP,aACAmI,0BAXO/H,QAAQiD,OAAO,IAAIzC,MAAM,2BAepCwJ,kBAAiBoF,MACfA,GAAQ,GAGN,IACF,MAAMY,EAAyBhP,KAAK+I,2BACpC,IAAIwF,EACFvO,KAAK+N,iCAAmC/O,QAAQC,UAElD,MAAMqP,EAAqBF,EAAQ,CEtrBK,oCFsrB4B,CE3rBhC,0CF6rB9BtL,EAAU9C,KAAK+O,mBAyBrB,OAvBIjM,GAAWkM,IACbT,EAASA,EACNzT,MAAK,IACGgI,EAAQ6K,SE3tBe,8CF2tBoBjQ,EAAW,CAC3D+F,aAAc6K,MAGjBxT,MAAK,IACGgI,EAAQkG,iBAAiBgG,KAEjC3I,OAAO9G,IAGN,MAFAS,KAAKqH,eAAexF,QJhqBK,sBIgqBwBtC,GAE3CA,OAIPuD,GAAWkM,GACdhP,KAAKqH,eAAexF,QJxqBQ,qBIwqBoBmN,GAGlDhP,KAAKgO,+BAAiCO,EAE/BA,EAAOxM,SAAQ,KACpB/B,KAAK0I,wBAIHuG,mBACJf,GACAE,MACEA,GAAQ,EAAKxP,WACbA,EAAUmI,sBACVA,GAKE,6CAEJ,MAAMjE,EAAU9C,KAAK+O,mBAErB,OAAKjM,EAIA9C,KAAK+I,4BAIN/I,KAAK+N,wCACD/N,KAAK+N,iCAGN/N,KAAKiO,kBAAkBnL,EAASoL,EAAQ,CAC7CE,QACAxP,aACAmI,wBACAoH,gBAAgB,KAXTnP,QAAQiD,OAAO,IAAIzC,MAAM,qCAJzBR,QAAQiD,OAAO,IAAIzC,MAAM,8BAmBpCkJ,4BACS1I,KAAK+I,2BAEZ/I,KAAK+N,qCAAkCrQ,EACvCsC,KAAKgO,oCAAiCtQ,EAuBxCqF,GAAGkC,EAAqBiK,GACtB,OAAOlP,KAAK4B,UAAUmB,GAAGkC,EAAWiK,GAGtCzI,KAAKxB,EAAqBiK,GACxB,OAAOlP,KAAK4B,UAAU6E,KAAKxB,EAAWiK,GAGxCC,SAASC,EAAwBF,GAC/B,OAAOlP,KAAK4B,UAAUuN,SAASC,EAAYF,GAG7CG,KAAKpK,GACH,OAAOjF,KAAK4B,UAAUyN,KAAKpK,GAG7Ba,IAAIb,EAAqBiK,GACvBlP,KAAK4B,UAAUkE,IAAIb,EAAWiK,GAGhC5G,UAAUrD,EAA0BiK,GAClC,OAAOlP,KAAKqH,eAAetE,GAAGkC,EAAWiK,GAG3CtG,YAAY3D,EAA0BiK,GACpC,OAAOlP,KAAKqH,eAAeZ,KAAKxB,EAAWiK,GAG7CI,gBAAgBF,EAA6BF,GAC3C,OAAOlP,KAAKqH,eAAe8H,SAASC,EAAYF,GAGlDK,YAAYtK,GACV,OAAOjF,KAAKqH,eAAegI,KAAKpK,GAGlC6C,WAAW7C,EAA0BiK,GACnClP,KAAKqH,eAAevB,IAAIb,EAAWiK,GAGrCM,eACE,QAASxP,KAAK8E,GAGhB2K,6BACE,OAAYC,OAAAC,OAAA,GAAA3P,KAAKE,0BAGnB0P,mBACE,IAAK5P,KAAKyO,WACR,OAGF,MACMoB,EADY7P,KAAKyO,WAAWqB,eACH1U,KAAI,EAAGiN,WAC7BA,IAGT,MFp0B0B,CAACwH,GACDA,EAAaE,MAAMC,IAC7C,MAAMC,KAAEA,GAASD,EAEjB,MAAgB,UAATC,KEg0BHC,CAAeL,GACV7P,KAAKmQ,iBAAiBN,GAGxB7P,KAAKoQ,sBAAsBP,GAGhCpB,uBAGF,OAFkC,QAAf4B,EAAArQ,gBAAA,EAAAA,KAAM8C,eAAS,IAAAuN,OAAA,EAAAA,EAAA5B,WAKhClM,uCACF,MAAO,CAELpG,oBAAamU,EAAuB,QAAvBD,EAAArQ,gBAAA,EAAAA,KAAMqC,uBAAiB,IAAAgO,OAAA,EAAAA,EAAA1I,sCAAiBvD,aAErDmM,KAA8C,QAAxCC,EAAuB,QAAvBC,EAAAzQ,gBAAI,EAAJA,KAAMqC,uBAAiB,IAAAoO,OAAA,EAAAA,EAAA9I,uBAAiB,IAAA6I,OAAA,EAAAA,EAAA/L,IAAI8L,KAElDG,eAAwD,QAAxCC,EAAuB,QAAvBC,EAAA5Q,gBAAI,EAAJA,KAAMqC,uBAAiB,IAAAuO,OAAA,EAAAA,EAAAjJ,uBAAiB,IAAAgJ,OAAA,EAAAA,EAAAlM,IAAIrB,KAC5DN,QAAS9C,gBAAA,EAAAA,KAAMqC,iBAIfwO,gBACF,OACE7Q,KAAKS,mBAAmBoQ,WACxB7Q,KAAKY,oBAAoBiQ,WACzB7Q,KAAKgB,gBAAgB6P,WACrB7Q,KAAKoB,kBAAkByP,UAIvB9B,yBACF,OAAO/O,KAAK8C,SAAW9C,KAAK8C,QAAQgO,gBAAkB9Q,KAAK8C,aAAUpF,EAGnEuP,mBACF,QAASjN,KAAK8E,IAAM9E,KAAK8E,GAAGmI,eAG1BtL,uBACF,QAAS3B,KAAK8E,IAAM9E,KAAKC,kBAGvB8Q,mBACF,SAAU/Q,KAAK8E,KAAM9E,KAAK8C,SAGxBV,8BACF,QAASpC,KAAKqC,gBAmGhB6B,OAAMZ,aAAEA,EAAYC,sBAAEA,IFpgClB,IAAwByN,EEqgC1BhR,KAAKI,iBFrgCqB4Q,EEqgCW1N,EFpgC/BjD,GACC,OAAOA,KAAM2Q,KEogCpBhR,KAAKwE,OAAS,IAAIxE,KAAKD,MAAMkR,mBAAmB1N,GAuRlD2N,gBAAgBC,EAA8BC,GAC5C,MAAM/Q,EAAK8Q,EAAW9Q,GAEhBgR,EAA4BrR,KAAKG,eAAeE,IAAO,IAAIjD,YASjE,OAPIgU,GACFC,EAAaC,SAASF,GAGxBC,EAAaC,SAASH,GACtBnR,KAAKG,eAAeE,GAAMgR,EAEnBA,EAGTE,qBAAqBH,GACnB,MAAM/Q,EAAK+Q,EAAW/Q,GAEhBgR,EAAerR,KAAKG,eAAeE,IAAO,IAAIjD,YAMpD,OAJAiU,EAAaC,SAASF,GAEtBpR,KAAKG,eAAeE,GAAMgR,EAEnBA,EAGTlB,iBAAiBN,GACf,MAAM2B,EAA+B,GAoBrC,OAlBA3B,EAAa4B,SAAQ,CAACpJ,EAAOqJ,KAC3B,GAAmB,UAAfrJ,EAAM4H,KACR,OAGF,MAAMkB,EAAa9I,EACbsJ,EAAY9B,EAAa6B,EAAQ,GACvC,IAAIN,EAEAO,GAAgC,UAAnBA,EAAU1B,OACzBmB,EAAaO,GAGf,MAAMN,EAAerR,KAAKkR,gBAAgBC,EAAYC,GAEtDI,EAAclM,KAAK+L,KAClB,IAEIG,EAGTpB,sBAAsBP,GAKpB,OAJqCA,EAAazU,KAAK4U,GAC9ChQ,KAAKuR,qBAAqBvB,KAsBrCxP,kBACER,KAAK4R,yBACL5R,KAAK6R,sBACL7R,KAAK8R,yBAGPA,yBACE9R,KAAKS,mBAAmB+B,gBAG1BqP,sBACE7R,KAAKgB,gBAAgBwB,gBACrBxC,KAAKoB,kBAAkBoB,gBAGzBoP,yBACE5R,KAAKoB,kBAAkBoB,gBACvBxC,KAAKuB,oBAAoBiB,gBAiS3BuP,eACE,OAAO/R,KAAKuP,YJtoDQ,YIyoDtByC,qBACE,OAAOhS,KAAKuP,YJloD4B,gCIqoD1C0C,cAAa7I,cAAEA,EAAaE,eAAEA,IAC5B,IAAKtJ,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,MAEMiE,EAAqD,CAF/B,4BAA6B2F,IAC5B,6BAA8BE,KAM3D,OAAOtJ,KAAK8C,QAAQ6K,SEzqDa,0CFyqDmBjQ,EAAW,CAAE+F,iBAGnEyO,gBACEC,IAAEA,EAAGpG,IAAEA,GACPyB,EAAkC,CAAEE,sBAAsB,IAE1D,IAAK1N,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,MAGMiE,EAAqD,CAHlC,qCACP,6BAA8B0O,EAC9B,yBAAyBpG,GAO3C,OAAO/L,KAAK8C,QAAQ6K,SE5rDgB,4CF4rDmBjQ,EAAgBgS,OAAAC,OAAAD,OAAAC,OAAA,GAAAnC,GAAS,CAAA/J,kBAGlF2O,qBACEnX,EACAuS,EAAkC,CAAEE,sBAAsB,IAE1D,IAAK1N,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,MAKMiE,EAAqD,CADnC,wBAFG,OAARxI,EAFK,EACA,KAMxB,OAAO+E,KAAK8C,QAAQ6K,SE7sDY,yCF6sDmBjQ,EAAgBgS,OAAAC,OAAAD,OAAAC,OAAA,GAAAnC,GAAS,CAAA/J,kBAG9E4O,uBACE7E,EAAkC,CAAEE,sBAAsB,IAE1D,IAAK1N,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,OAAOQ,KAAKoS,qBAAqB,MAAO5E,GAG1C8E,uBACE9E,EAAkC,CAAEE,sBAAsB,IAE1D,IAAK1N,KAAK8C,QACR,MAAM,IAAItD,MAAM,0BAGlB,OAAOQ,KAAKoS,qBAAqB,MAAO5E,IMxuD5C,MCAM+E,EAAoB,CAACC,EAAiBrF,MACjCqF,KAAYrF,GAAUqF,EAAOC,cAAc9D,SAASxB,EAAOsF,eCChEC,EAAkBC,GAFI,IAGnBA,EAGIC,EAAkBF,EAAe,KACxCG,EAAkBH,EAAe,GCHjCI,EAAsB,CAACC,EAAiB/X,ICA1B,CAACA,GACZuX,EAAkBvX,EAHT,ODGZgY,CAAYhY,GAHO,GAId+X,EAGFA,EEFHE,EAA+B,CAACC,EAAkBlY,KACtD,MAAM4D,EHCqB,CAACsU,GACxBA,GAAY,GACPN,EAGLM,GAAY,IACPR,EAAe,KAGpBQ,GAAY,IACPR,EAAe,KAGpBQ,GAAY,IACPR,EAAe,KAGpBQ,GAAY,IACPR,EAAe,KAGpBQ,GAAY,IACPR,EAAe,IAGpBQ,GAAY,IACPR,EAAe,IAGpBQ,GAAY,KACPR,EAAe,GAGpBQ,GAAY,KACPR,EAAe,GAGjBG,EGtCYM,CAAqBD,GAExC,OAAOJ,EAAoBlU,EAAY5D,ICJnCoY,EAAgBC,IAUhBC,EAAOC,IACXH,EAAcI,IAAID,GAPXH,IAAgB/M,OAAO9G,IAE5BkU,QAAQC,MAAM,8BAA+BnU,OAU3CoU,EAAwC,EAC5C/Y,SACA0D,wBACAM,aACAb,qBAOOuV,GAAI,IACFzV,EAAqBjD,EAAQ,CAAE0D,wBAAuBM,cAAcb,KAIzE6V,EAA4B,EAC9BhZ,SAAQI,SACV+C,KAEA,MACMa,EDxCyB,CAAC5D,GACzB8X,EAAoBF,EAAiB5X,GCuCzB6Y,CAAkB7Y,GAErC,OAAO2Y,EAAsC,CAC3C/Y,SACAgE,aACAb,kBACAO,sBAPkC,OAWhCwV,EAA8B,EAChClZ,SAAQyN,QAAOrN,SACjB+C,KAEA,MAGMgW,EADW1L,EAAM2L,cACOC,MAExBrV,EAAaqU,EAA6Bc,EAAc/Y,GAE9D,OAAO2Y,EAAsC,CAC3C/Y,SACAgE,aACAb,kBACAO,sBAXkC,KAkDhC4V,EAAgB,EAElB7I,UACAQ,oBACAjR,SACAyN,QACArN,SAQF+C,KAEA,OAAQsN,GACN,KAAKnM,EAAe0M,eAClB,OAAOgI,EAA0B,CAAEhZ,SAAQI,SAAS+C,GACtD,KAAKmB,EAAeyM,gBAClB,OAAOmI,EAA4B,CAAElZ,SAAQyN,QAAOrN,SAAS+C,GAC/D,KAAKmB,EAAeiV,wBAClB,OAAItI,EAzDkB,GAExBjR,SACAyN,QACA+L,aACApZ,SAOF+C,KAEA,MAAMsW,EAAWhM,EAAM2L,cACjBD,EAAeM,EAASJ,MACxBK,EAAgBD,EAASE,QACxBC,EAAaC,GAAgBL,EAAWM,MAAM,KAE/CC,EAAeZ,GAAgBS,EAC/BI,EAAgBN,GAAiBG,EAGjClW,EAA8B9B,KAAKD,IAAImY,EAAcC,EAFzC,GAIZhW,EAAaqU,GAA8BuB,EAAaxZ,GAE9D,OAAO2Y,EAAsC,CAC3C/Y,SACAgE,aACAb,kBACAO,sBAAuBC,KA2BZsW,CACL,CAAEja,SAAQyN,QAAOrN,QAAOoZ,WAAYvI,GACpC9N,GAIG+V,EAA4B,CAAElZ,SAAQyN,QAAOrN,SAAS+C,GAC/D,QACE,OAAO+V,EAA4B,CAAElZ,SAAQyN,QAAOrN,SAAS+C,KCnI7D+W,EAA2B,CAC/BpW,WAAW,EACXV,WAAY,CACVE,UAAW,CAAC,IACZ6W,cAAe,IACfC,OAAQ,GACRC,iBAAkB,GAClBC,KAAM,KAIJC,EAAU,EACd9J,UACAQ,oBACA4C,aACA1Q,kBACAqX,oBAOGpR,OAAA,OAAA,OAAA,GAAA,YACH,MACMpJ,EPhCgB,CAAC8T,GAChBA,EAAQlT,MAAMZ,UACnB,MAA+B,WAAX,QAAbyV,EAAAzV,aAAM,EAANA,EAAQyN,aAAK,IAAAgI,OAAA,EAAAA,EAAEJ,SO8BToF,CADC5G,EAAWK,cAG3B,IAAKlU,IAAWA,EAAOyN,MACrB,OAAOyM,EAGT,MAAM9Z,QAAcL,EAAmBC,GAEvC,OAAI2X,EAAkBvX,EAAOoa,GACpBN,EAGFZ,EACL,CAAE7I,UAASQ,oBAAmBjR,SAAQI,QAAOqN,MAAOzN,EAAOyN,OAC3DtK,MCzCEuX,EAA8B,CAClCC,GAEEH,iBACArX,mBAIE,MAEJ,MAAMyX,EAAiB,KACrB,MAAM/G,WAAEA,GAAe8G,EAEvB,OAAK9G,EAIE0G,EAAQ,CACb1G,aACA1Q,kBACAqX,mBANOpW,QAAQiD,OAAO,IAAIzC,MAAM,6BAUpC,IAAIiW,EAAYD,EAEhB,MAAME,EAAwBrQ,IAI5BoQ,EAAY,KACV,MAAMpK,QAAEA,EAAOQ,kBAAEA,GAAsBxG,GACjCoJ,WAAEA,GAAe8G,EAEvB,OAAK9G,EAIE0G,EAAQ,CACb9J,UACAQ,oBACA4C,aACA1Q,kBACAqX,mBAROpW,QAAQiD,OAAO,IAAIzC,MAAM,6BAYpCiW,KAWF,MAAO,CACLE,UATgB,KAChBJ,EAAajN,UAAU,mBAAoBoN,IAS3CE,YANkB,KAClBL,EAAazN,WAAW,mBAAoB4N,IAM5CF,iBACAK,sBACEJ,EAAYD,GAEdC,UAAS,IACAA,MCpEPK,EAAgBvW,IACpB,MAAMwW,IAAEA,EAAGrW,MAAEA,GAAUH,EAEvB,IAAIyW,EAAOD,EAMX,MpBYmC,0BoBhB/BrW,GpBEmB,coBFuBA,IAC5CsW,EAAO,GAAGzW,EAAMqO,QAAQqI,GAAGxR,IAAIrB,QAAQ7D,EAAMqO,QAAQqI,GAAGxR,IAAI8L,QAGvDyF,GCRT,IAAYE,GAAZ,SAAYA,GACVA,EAAA,sBAAA,wBACAA,EAAA,uBAAA,yBACAA,EAAA,gBAAA,kBACAA,EAAA,gBAAA,kBACAA,EAAA,qBAAA,uBACAA,EAAA,8BAAA,gCANF,CAAYA,IAAAA,EAOX,yEAEwB,CAAC3W,EAAsB,IAAIC,eAClD,MAAME,MAAEA,EAAK8E,OAAEA,GAAWjF,EAE1B,IAAItE,EAAoBib,EAAYC,sBAcpC,MAZc,cAAVzW,EACFzE,EAAOib,EAAYE,uBrBKc,0BqBJxB1W,EACTzE,EAAOib,EAAYG,gBrBXE,cqBYZ3W,EACTzE,EAAOib,EAAYI,gBACV9R,GAAsC,KAAjB,QAAX6L,EAAA7L,aAAA,EAAAA,EAAQ+R,WAAG,IAAAlG,OAAA,EAAAA,EAAEmG,YAChCvb,EAAOib,EAAYO,qBACVX,EAAavW,KACtBtE,EAAOib,EAAYQ,+BAGdzb,sBCpBkB,CAACsE,EAAsB,IAAIC,SACpD,MAAMmX,KAAEA,EAAIjX,MAAEA,EAAKkO,QAAEA,GAAYrO,EAC3ByW,EAAOF,EAAavW,GACpBqX,EAAkB,GAkBxB,OAhBIhJ,IACFgJ,EAAOhJ,QAAUA,GAGfoI,IACFY,EAAOZ,KAAOA,GAGZW,IACFC,EAAOD,KAAOA,GAGZjX,IACFkX,EAAOlX,MAAQA,GAGVkX,KC7BT,MAAMC,GAAO,gBAEPC,GAASpD,EAAMmD,IAMRE,GAAc,KACzBrD,EAAMsD,OAAO,GAAGH,OAGLI,GAAe,KAC1BvD,EAAMsD,OAAO,IAAIH,OCbbK,GAAgBhM,GAFqB,cAGlCA,ECAHiM,GAA2B5B,GACN,KACvB6B,GAAI,oBAEG7B,EAAa3F,oBCHlByH,GAA6BC,GAC1B,EAAGjP,YALe,GAAG4H,OAAMuG,gBAClB,UAATvG,GAAmC,SAAfuG,EAKrBe,CAAmBlP,IACrBiP,KCJAE,GAA6B,EACjC5H,mBACA6H,sBAKOC,GAAS,KACd,MAAMlG,EAAgB5B,IAEtBwH,GAAI,gBAAiB5F,GAEjBA,GACFiG,EAAiBjG,KAElB,uECDwB,EAAG+D,mBAC9B,MAAMoC,EAA4B,CAACC,EAA4BC,IACtD,CAACtX,EAAkC,CAAEgL,cAAc,KACpDhL,EAAKgL,aACAqM,IAGFC,IAILC,ECzBsB,CAACvC,GAE3BrG,IAEAkI,GAAI,kBAEG7B,EAAajN,UAAU,uBAAwB4G,IDmB1B6I,CAAsBxC,GAC9CyC,EE1BqB,CAACzC,GAE1BrG,IAEAkI,GAAI,iBAEG7B,EAAajN,UAAU,sBAAuB4G,IFoB1B+I,CAAqB1C,GAC5C2C,EG3BkB,CAAC3C,GAEvBrG,IAEAkI,GAAI,cAEG7B,EAAajN,UAAU,kBAAmB4G,IHqBzBiJ,CAAkB5C,GACtC6C,EI5BiB,CAAC7C,GAEtBrG,IAEAkI,GAAI,aAEG7B,EAAajN,UAAU,iBAAkB4G,IJsBzBmJ,CAAiB9C,GAE1C,IAAI+C,EAA0B,OAC1BC,EAAyB,OACzBC,EAAsB,OACtBC,EAAqB,OAiDzB,MAAO,CACLzS,MATa0S,IAxCe,GAC5BC,uBACAC,0BACAC,sBACAC,yBACAC,mBACAC,sBACAC,kBACAC,yBAEA,MAAMC,EAAqBxB,EACzBgB,EACAC,GAGFN,EAA0BR,EAAsBqB,GAEhD,MAAMC,EAAoBzB,EACxBkB,EACAC,GAGFP,EAAyBP,EAAqBoB,GAE9C,MAAMC,EAAiB1B,EAA0BoB,EAAkBC,GAEnER,EAAsBN,EAAkBmB,GAExC,MAAMC,EAAgB3B,EAA0BsB,EAAiBC,GAEjET,EAAqBL,EAAiBkB,IAWtCC,CAAsBb,IAStBhS,KANW,KAVX4R,IACAC,IACAC,IACAC,iCKjE+BlD,GACLtS,IAc1B,MAAMpG,YACJA,EAAW4G,aACXA,EAAYqD,WACZA,EAAUC,sBACVA,EAAqB0Q,iBACrBA,EAAgB+B,qBAChBA,EAAoBC,sBACpBA,EAAqBC,iBACrBA,EAAgBC,kBAChBA,EAAiBC,mBACjBA,EAAkBC,qBAClBA,EAAoBC,YACpBA,GACE7W,EACEqU,EAAsBE,GAA2B,CACrDC,mBACA7H,iBAAkBuH,GAAwB5B,KAEtCwE,EAAqB1C,GAA0BC,GAErDF,GAAI,qBAAsBnU,GAkB1B,IACIiI,EADA8O,GAAwB,EAG5B,MAsBMC,GArBJ7C,GAAI,8CAA+CuC,GAE/CD,GAAoBC,EACfpE,EAAajN,UAAU,aAAc4R,IAC1C9C,GAAI,YAAa,CAAE8C,QAAOF,0BAE1B9O,EAAOgP,EAEHhD,GAAahM,GACXwO,GACFA,IAEOC,GACTA,EAAkB,CAAEK,6BAKnB,QAgDT,GAFA5C,GAAI,wBAEAoC,EAAsB,CAGxBA,EA/EwB,MACxB,MAAMjX,iBAAEA,GAAqBgT,GACvB7E,eAAEA,GAAmBnO,EAE3B,OAAOmO,GAyEYyJ,IAKrB,OA3FS5E,EAAapU,qBAAqB,CACvCtE,cACA4G,eACAqD,aACAC,wBACAF,QAASkT,IAsFGjf,MAjDGsf,IACjBhD,GAAI,aAEJ4C,GAAwB,EACxB1C,IAEImC,GACFA,EAAsB,CAAEY,YAAanD,GAAahM,KAGpDqK,EAAajG,gBAAgB,CAAC,QAAS,WAAW,KAChD2K,IAEIH,GACFA,OAIGM,KA+BuB/T,OA5BhB9G,IASd,MARA6X,GAAI,UAEAwC,GACFA,IAGFK,IAEM1a,KAmBsCwC,SAhB7B,KACfqV,GAAI,YAEAyC,GACFA,+BCrHqBtE,GACLtS,IAepB,MAAMuH,WACJA,EAAU3N,YACVA,EAAW4G,aACXA,EAAYqD,WACZA,EAAUC,sBACVA,EAAqB0Q,iBACrBA,EAAgB+B,qBAChBA,EAAoBC,sBACpBA,EAAqBC,iBACrBA,EAAgBC,kBAChBA,EAAiBC,mBACjBA,EAAkBC,qBAClBA,EAAoBC,YACpBA,GACE7W,EACEqU,EAAsBE,GAA2B,CACrDC,mBACA7H,iBAAkBuH,GAAwB5B,KAEtCwE,EAAqB1C,GAA0BC,GAErDF,GAAI,eAAgBnU,GAcpB,IACIiI,EADA8O,GAAwB,EAG5B,MAsBMC,GArBJ7C,GAAI,8CAA+CuC,GAE/CD,GAAoBC,EACfpE,EAAajN,UAAU,aAAc4R,IAC1C9C,GAAI,YAAa,CAAE8C,QAAOF,0BAE1B9O,EAAOgP,EAEHhD,GAAahM,GACXwO,GACFA,IAEOC,GACTA,EAAkB,CAAEK,6BAKnB,QAoDT,OANA5C,GAAI,wBAEAoC,GACFA,EAAqBhP,IAlFrB4M,GAAI,aAEG7B,EAAaxU,KAAK,CACvBlE,cACA4G,eACAqD,aACAC,wBACAH,OAAQ4D,EACR3D,QAASkT,KA6EMjf,MA/CAsf,IACjBhD,GAAI,aAEJ4C,GAAwB,EACxB1C,IAEImC,GACFA,EAAsB,CAAEY,YAAanD,GAAahM,KAGpDqK,EAAajG,gBAAgB,CAAC,QAAS,WAAW,KAChD2K,IAEIH,GACFA,OAIGM,KA6B0B/T,OA1BnB9G,IASd,MARA6X,GAAI,UAEAwC,GACFA,IAGFK,IAEM1a,KAiByCwC,SAdhC,KACfqV,GAAI,YAEAyC,GACFA,oCCzH6BtE,GAC5B,KACL6B,GAAI,wBAEG7B,EACJtU,aACAnG,MAAK,KACJsc,GAAI,+BAEG,KAER/Q,OAAO9G,IACN6X,GAAI,8BAA+B7X,IAE5B,sDCd0BgW,GACN,IAC1BA,EAAaxE,cAIlBqG,GAAI,4BAEG7B,EAAa9H,4BALXzO,QAAQC,uCCHgB,EAAGsW,kBACR,EAAGnH,SAAQ,GAA8B,CAAEA,OAAO,MAC9EgJ,GAAI,yBAEG7B,EACJvM,iBAAiB,CAChBoF,UAED/H,MAAM+Q,mCCR0B7B,GACLrG,IAC9BkI,GAAI,0BAEG7B,EAAajN,UAAU,uBAAwB4G,wBCH7BqG,GACLrG,IACpBkI,GAAI,gBAEG7B,EAAajN,UAAU,aAAc4G,0BCLjBqG,GACN,EAAG+E,eAAcC,kBACjChF,EAAaxE,cAIlBqG,GAAI,kBAEG7B,EAAarD,eAAe,CAAEC,IAAKmI,EAAcvO,IAAKwO,KALpDvb,QAAQC,wCCHkBsW,GACN,IACxBA,EAAaxE,cAIlBqG,GAAI,0BAEG7B,EAAajD,yBAAyBjM,OAAO9G,IAClD6X,GAAI,gCAAiC7X,OAN9BP,QAAQC,wCCHkBsW,GACN,IACxBA,EAAaxE,cAIlBqG,GAAI,0BAEG7B,EAAalD,yBAAyBhM,OAAO9G,IAClD6X,GAAI,gCAAiC7X,OAN9BP,QAAQC,mCCDY,EAC/BL,aAH0B,IAI1B2W,kBAK0B,EACxB1Y,cACAuR,SAAQ,MAKRgJ,GAAI,qBAEG7B,EAAa/G,kBAAkB3R,EAAa,CACjDuR,QACAxP,0CClB4B,EAChC2W,eACA3W,aAJ0B,OASC,EACzB/B,cACAuR,SAAQ,MAKRgJ,GAAI,sBAEG7B,EAAatG,mBAAmBpS,EAAa,CAClDuR,QACAxP,6FCHsB,EAC1B4b,kBACAC,UACAC,iBAQA,MAAMC,EAzBe,CAACF,GACfG,GACJzf,GACQuZ,EAAMvZ,EAAM,MAEpB0f,GACQA,EAASzf,KAAKC,GACZ,IACEof,EAAQpf,OAiBCyf,CAAeL,GACjCM,EAAQJ,EAAgBH,GAE9B,OAAOQ,EAAsBD,EAAOL"}
|