sip-connector 19.8.2 → 19.9.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.
@@ -0,0 +1 @@
1
+ "use strict";const O=require("events-constructor"),G=require("debug"),k=require("@krivega/cancelable-promise"),y=require("@krivega/timeout-requester"),Q=require("repeated-calls"),ie=require("xstate"),Y=require("stack-promises");require("ua-parser-js");require("sequent-promises");const z="sip-connector",h=G(z),De=()=>{G.enable(z)},be=()=>{G.enable(`-${z}`)},ye="Error decline with 603",we=1006,Ue=n=>typeof n=="object"&&n!==null&&"code"in n&&n.code===we,Le=n=>n.message===ye;var u=(n=>(n.CONTENT_TYPE="content-type",n.CONTENT_ENTER_ROOM="x-webrtc-enter-room",n.CONTENT_USE_LICENSE="X-WEBRTC-USE-LICENSE",n.PARTICIPANT_NAME="X-WEBRTC-PARTICIPANT-NAME",n.INPUT_CHANNELS="X-WEBRTC-INPUT-CHANNELS",n.OUTPUT_CHANNELS="X-WEBRTC-OUTPUT-CHANNELS",n.MAIN_CAM="X-WEBRTC-MAINCAM",n.MIC="X-WEBRTC-MIC",n.MEDIA_SYNC="X-WEBRTC-SYNC",n.MAIN_CAM_RESOLUTION="X-WEBRTC-MAINCAM-RESOLUTION",n.MEDIA_STATE="X-WEBRTC-MEDIA-STATE",n.MEDIA_TYPE="X-Vinteo-Media-Type",n.MAIN_CAM_STATE="X-Vinteo-MainCam-State",n.MIC_STATE="X-Vinteo-Mic-State",n.CONTENT_PARTICIPANT_STATE="X-WEBRTC-PARTSTATE",n.NOTIFY="X-VINTEO-NOTIFY",n.CONTENT_ENABLE_MEDIA_DEVICE="X-WEBRTC-REQUEST-ENABLE-MEDIA-DEVICE",n.CONTENT_SHARE_STATE="x-webrtc-share-state",n.MUST_STOP_PRESENTATION_P2P="x-webrtc-share-state: YOUMUSTSTOPSENDCONTENT",n.START_PRESENTATION_P2P="x-webrtc-share-state: YOUCANRECEIVECONTENT",n.STOP_PRESENTATION_P2P="x-webrtc-share-state: CONTENTEND",n.STOP_PRESENTATION="x-webrtc-share-state: STOPPRESENTATION",n.START_PRESENTATION="x-webrtc-share-state: LETMESTARTPRESENTATION",n.ENABLE_MAIN_CAM="X-WEBRTC-REQUEST-ENABLE-MEDIA-DEVICE: LETMESTARTMAINCAM",n.AVAILABLE_INCOMING_BITRATE="X-WEBRTC-AVAILABLE-INCOMING-BITRATE",n.AUDIO_TRACK_COUNT="X-WEBRTC-AUDIO-TRACK-COUNT",n.VIDEO_TRACK_COUNT="X-WEBRTC-VIDEO-TRACK-COUNT",n.TRACKS_DIRECTION="X-WEBRTC-TRACKS-DIRECTION",n.AUDIO_ID="X-WEBRTC-AUDIOID",n))(u||{}),F=(n=>(n.AVAILABLE_SECOND_REMOTE_STREAM="YOUCANRECEIVECONTENT",n.NOT_AVAILABLE_SECOND_REMOTE_STREAM="CONTENTEND",n.MUST_STOP_PRESENTATION="YOUMUSTSTOPSENDCONTENT",n))(F||{}),V=(n=>(n.SPECTATOR="SPECTATOR",n.PARTICIPANT="PARTICIPANT",n))(V||{}),D=(n=>(n.ENTER_ROOM="application/vinteo.webrtc.roomname",n.MIC="application/vinteo.webrtc.mic",n.USE_LICENSE="application/vinteo.webrtc.uselic",n.PARTICIPANT_STATE="application/vinteo.webrtc.partstate",n.NOTIFY="application/vinteo.webrtc.notify",n.SHARE_STATE="application/vinteo.webrtc.sharedesktop",n.MAIN_CAM="application/vinteo.webrtc.maincam",n))(D||{}),m=(n=>(n.CHANNELS="application/vinteo.webrtc.channels",n.MEDIA_STATE="application/vinteo.webrtc.mediastate",n.REFUSAL="application/vinteo.webrtc.refusal",n.SHARE_STATE="application/vinteo.webrtc.sharedesktop",n.MAIN_CAM="application/vinteo.webrtc.maincam",n.STATS="application/vinteo.webrtc.stats",n))(m||{}),P=(n=>(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))(P||{}),H=(n=>(n.ADMIN_STOP_MIC="ADMINSTOPMIC",n.ADMIN_START_MIC="ADMINSTARTMIC",n))(H||{}),x=(n=>(n.ADMIN_SYNC_FORCED="1",n.ADMIN_SYNC_NOT_FORCED="0",n))(x||{}),re=(n=>(n.AUDIO="AUDIO",n.VIDEO="VIDEO",n.AUDIOPLUSPRESENTATION="AUDIOPLUSPRESENTATION",n))(re||{}),g=(n=>(n.CHANNELS_NOTIFY="channels:notify",n.PARTICIPANT_ADDED_TO_LIST_MODERATORS="participant:added-to-list-moderators",n.PARTICIPANT_REMOVED_FROM_LIST_MODERATORS="participant:removed-from-list-moderators",n.PARTICIPANT_MOVE_REQUEST_TO_STREAM="participant:move-request-to-stream",n.PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS="participant:move-request-to-spectators",n.PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS_WITH_AUDIO_ID="participant:move-request-to-spectators-with-audio-id",n.PARTICIPANT_MOVE_REQUEST_TO_PARTICIPANTS="participant:move-request-to-participants",n.PARTICIPATION_ACCEPTING_WORD_REQUEST="participation:accepting-word-request",n.PARTICIPATION_CANCELLING_WORD_REQUEST="participation:cancelling-word-request",n.WEBCAST_STARTED="webcast:started",n.WEBCAST_STOPPED="webcast:stopped",n.ACCOUNT_CHANGED="account:changed",n.ACCOUNT_DELETED="account:deleted",n.CONFERENCE_PARTICIPANT_TOKEN_ISSUED="conference:participant-token-issued",n.CHANNELS="channels",n.ENTER_ROOM="enterRoom",n.SHARE_STATE="shareState",n.MAIN_CAM_CONTROL="main-cam-control",n.USE_LICENSE="useLicense",n.ADMIN_START_MAIN_CAM="admin-start-main-cam",n.ADMIN_STOP_MAIN_CAM="admin-stop-main-cam",n.ADMIN_START_MIC="admin-start-mic",n.ADMIN_STOP_MIC="admin-stop-mic",n.ADMIN_FORCE_SYNC_MEDIA_STATE="admin-force-sync-media-state",n.AVAILABLE_SECOND_REMOTE_STREAM="availableSecondRemoteStream",n.NOT_AVAILABLE_SECOND_REMOTE_STREAM="notAvailableSecondRemoteStream",n.MUST_STOP_PRESENTATION="mustStopPresentation",n.NEW_DTMF="newDTMF",n))(g||{});const ae=["participation:accepting-word-request","participation:cancelling-word-request","participant:move-request-to-stream","channels:notify","conference:participant-token-issued","account:changed","account:deleted","webcast:started","webcast:stopped","participant:added-to-list-moderators","participant:removed-from-list-moderators","participant:move-request-to-spectators","participant:move-request-to-spectators-with-audio-id","participant:move-request-to-participants","channels","enterRoom","shareState","main-cam-control","useLicense","admin-start-main-cam","admin-stop-main-cam","admin-start-mic","admin-stop-mic","admin-force-sync-media-state","availableSecondRemoteStream","notAvailableSecondRemoteStream","mustStopPresentation","newDTMF"];var I=(n=>(n.CHANNELS="channels",n.WEBCAST_STARTED="WebcastStarted",n.WEBCAST_STOPPED="WebcastStopped",n.ACCOUNT_CHANGED="accountChanged",n.ACCOUNT_DELETED="accountDeleted",n.ADDED_TO_LIST_MODERATORS="addedToListModerators",n.REMOVED_FROM_LIST_MODERATORS="removedFromListModerators",n.ACCEPTING_WORD_REQUEST="ParticipationRequestAccepted",n.CANCELLING_WORD_REQUEST="ParticipationRequestRejected",n.MOVE_REQUEST_TO_STREAM="ParticipantMovedToWebcast",n.CONFERENCE_PARTICIPANT_TOKEN_ISSUED="ConferenceParticipantTokenIssued",n))(I||{});class Be{events;connectionManager;callManager;constructor({connectionManager:e,callManager:t}){this.connectionManager=e,this.callManager=t,this.events=new O.TypedEvents(ae),this.subscribe()}async waitChannels(){return this.wait(g.CHANNELS)}async waitSyncMediaState(){return this.wait(g.ADMIN_FORCE_SYNC_MEDIA_STATE)}async sendDTMF(e){return new Promise((t,s)=>{let i;try{i=this.getEstablishedRTCSessionProtected()}catch(r){s(r)}i&&(this.callManager.once("newDTMF",({originator:r})=>{r==="local"&&t()}),i.sendDTMF(e,{duration:120,interToneGap:600}))})}async sendChannels({inputChannels:e,outputChannels:t}){const s=this.getEstablishedRTCSessionProtected(),i=`${u.INPUT_CHANNELS}: ${e}`,r=`${u.OUTPUT_CHANNELS}: ${t}`,a=[i,r];return s.sendInfo(m.CHANNELS,void 0,{extraHeaders:a})}async sendMediaState({cam:e,mic:t},s={}){const i=this.getEstablishedRTCSessionProtected(),r=`${u.MEDIA_STATE}: currentstate`,a=`${u.MAIN_CAM_STATE}: ${Number(e)}`,o=`${u.MIC_STATE}: ${Number(t)}`,c=[r,a,o];return i.sendInfo(m.MEDIA_STATE,void 0,{noTerminateWhenError:!0,...s,extraHeaders:c})}async sendStats({availableIncomingBitrate:e}){const t=this.getEstablishedRTCSessionProtected(),i=[`${u.AVAILABLE_INCOMING_BITRATE}: ${e}`];return t.sendInfo(m.STATS,void 0,{noTerminateWhenError:!0,extraHeaders:i})}async sendRefusalToTurnOn(e,t={}){const s=this.getEstablishedRTCSessionProtected(),a=e==="mic"?0:1,c=[`${u.MEDIA_TYPE}: ${a}`];return s.sendInfo(m.REFUSAL,void 0,{noTerminateWhenError:!0,...t,extraHeaders:c})}async sendRefusalToTurnOnMic(e={}){return this.sendRefusalToTurnOn("mic",{noTerminateWhenError:!0,...e})}async sendRefusalToTurnOnCam(e={}){return this.sendRefusalToTurnOn("cam",{noTerminateWhenError:!0,...e})}async sendMustStopPresentationP2P(){await this.getEstablishedRTCSessionProtected().sendInfo(m.SHARE_STATE,void 0,{extraHeaders:[u.MUST_STOP_PRESENTATION_P2P]})}async sendStoppedPresentationP2P(){await this.getEstablishedRTCSessionProtected().sendInfo(m.SHARE_STATE,void 0,{extraHeaders:[u.STOP_PRESENTATION_P2P]})}async sendStoppedPresentation(){await this.getEstablishedRTCSessionProtected().sendInfo(m.SHARE_STATE,void 0,{extraHeaders:[u.STOP_PRESENTATION]})}async askPermissionToStartPresentationP2P(){await this.getEstablishedRTCSessionProtected().sendInfo(m.SHARE_STATE,void 0,{extraHeaders:[u.START_PRESENTATION_P2P]})}async askPermissionToStartPresentation(){await this.getEstablishedRTCSessionProtected().sendInfo(m.SHARE_STATE,void 0,{extraHeaders:[u.START_PRESENTATION]})}async askPermissionToEnableCam(e={}){const t=this.getEstablishedRTCSessionProtected(),s=[u.ENABLE_MAIN_CAM];return t.sendInfo(m.MAIN_CAM,void 0,{noTerminateWhenError:!0,...e,extraHeaders:s}).catch(i=>{if(Le(i))throw i})}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}getEstablishedRTCSessionProtected=()=>{const e=this.callManager.getEstablishedRTCSession();if(!e)throw new Error("No rtcSession established");return e};subscribe(){this.connectionManager.on("sipEvent",this.handleSipEvent),this.callManager.on("newInfo",this.handleNewInfo),this.callManager.on("newDTMF",e=>{this.events.trigger("newDTMF",e)})}handleSipEvent=({request:e})=>{this.maybeHandleNotify(e)};maybeHandleNotify=e=>{try{const t=e.getHeader(u.NOTIFY);if(t){const s=JSON.parse(t);this.handleNotify(s)}}catch(t){h("error parse notify",t)}};handleNotify=e=>{switch(e.cmd){case I.CHANNELS:{const t=e;this.triggerChannelsNotify(t);break}case I.WEBCAST_STARTED:{const t=e;this.triggerWebcastStartedNotify(t);break}case I.WEBCAST_STOPPED:{const t=e;this.triggerWebcastStoppedNotify(t);break}case I.ADDED_TO_LIST_MODERATORS:{const t=e;this.triggerAddedToListModeratorsNotify(t);break}case I.REMOVED_FROM_LIST_MODERATORS:{const t=e;this.triggerRemovedFromListModeratorsNotify(t);break}case I.ACCEPTING_WORD_REQUEST:{const t=e;this.triggerParticipationAcceptingWordRequest(t);break}case I.CANCELLING_WORD_REQUEST:{const t=e;this.triggerParticipationCancellingWordRequest(t);break}case I.MOVE_REQUEST_TO_STREAM:{const t=e;this.triggerParticipantMoveRequestToStream(t);break}case I.ACCOUNT_CHANGED:{this.triggerAccountChangedNotify();break}case I.ACCOUNT_DELETED:{this.triggerAccountDeletedNotify();break}case I.CONFERENCE_PARTICIPANT_TOKEN_ISSUED:{const t=e;this.triggerConferenceParticipantTokenIssued(t);break}default:h("unknown cmd",e)}};handleNewInfo=e=>{const{originator:t}=e;if(t!=="remote")return;const{request:s}=e,i=s,r=i.getHeader(u.CONTENT_TYPE);if(r!==void 0)switch(r){case D.ENTER_ROOM:{this.triggerEnterRoom(i),this.maybeTriggerChannels(i);break}case D.NOTIFY:{this.maybeHandleNotify(i);break}case D.SHARE_STATE:{this.triggerShareState(i);break}case D.MAIN_CAM:{this.triggerMainCamControl(i);break}case D.MIC:{this.triggerMicControl(i);break}case D.USE_LICENSE:{this.triggerUseLicense(i);break}case D.PARTICIPANT_STATE:{this.maybeTriggerParticipantMoveRequest(i);break}}};triggerChannelsNotify=e=>{const t=e.input,s=e.output,i={inputChannels:t,outputChannels:s};this.events.trigger(g.CHANNELS_NOTIFY,i)};triggerWebcastStartedNotify=({body:{conference:e,type:t}})=>{const s={conference:e,type:t};this.events.trigger(g.WEBCAST_STARTED,s)};triggerWebcastStoppedNotify=({body:{conference:e,type:t}})=>{const s={conference:e,type:t};this.events.trigger(g.WEBCAST_STOPPED,s)};triggerAddedToListModeratorsNotify=({conference:e})=>{const t={conference:e};this.events.trigger(g.PARTICIPANT_ADDED_TO_LIST_MODERATORS,t)};triggerRemovedFromListModeratorsNotify=({conference:e})=>{const t={conference:e};this.events.trigger(g.PARTICIPANT_REMOVED_FROM_LIST_MODERATORS,t)};triggerParticipationAcceptingWordRequest=({body:{conference:e}})=>{const t={conference:e};this.events.trigger(g.PARTICIPATION_ACCEPTING_WORD_REQUEST,t)};triggerParticipationCancellingWordRequest=({body:{conference:e}})=>{const t={conference:e};this.events.trigger(g.PARTICIPATION_CANCELLING_WORD_REQUEST,t)};triggerParticipantMoveRequestToStream=({body:{conference:e}})=>{const t={conference:e};this.events.trigger(g.PARTICIPANT_MOVE_REQUEST_TO_STREAM,t)};triggerAccountChangedNotify=()=>{this.events.trigger(g.ACCOUNT_CHANGED,{})};triggerAccountDeletedNotify=()=>{this.events.trigger(g.ACCOUNT_DELETED,{})};triggerConferenceParticipantTokenIssued=({body:{conference:e,participant:t,jwt:s}})=>{const i={conference:e,participant:t,jwt:s};this.events.trigger(g.CONFERENCE_PARTICIPANT_TOKEN_ISSUED,i)};maybeTriggerChannels=e=>{const t=e.getHeader(u.INPUT_CHANNELS),s=e.getHeader(u.OUTPUT_CHANNELS);if(t&&s){const i={inputChannels:t,outputChannels:s};this.events.trigger(g.CHANNELS,i)}};triggerEnterRoom=e=>{const t=e.getHeader(u.CONTENT_ENTER_ROOM),s=e.getHeader(u.PARTICIPANT_NAME);this.events.trigger(g.ENTER_ROOM,{room:t,participantName:s})};triggerShareState=e=>{const t=e.getHeader(u.CONTENT_SHARE_STATE);if(t!==void 0)switch(t){case F.AVAILABLE_SECOND_REMOTE_STREAM:{this.events.trigger(g.AVAILABLE_SECOND_REMOTE_STREAM,{});break}case F.NOT_AVAILABLE_SECOND_REMOTE_STREAM:{this.events.trigger(g.NOT_AVAILABLE_SECOND_REMOTE_STREAM,{});break}case F.MUST_STOP_PRESENTATION:{this.events.trigger(g.MUST_STOP_PRESENTATION,{});break}}};maybeTriggerParticipantMoveRequest=e=>{const t=e.getHeader(u.CONTENT_PARTICIPANT_STATE),s=e.getHeader(u.AUDIO_ID);t===V.SPECTATOR&&(s?this.events.trigger(g.PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS_WITH_AUDIO_ID,{audioId:s}):this.events.trigger(g.PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS,{})),t===V.PARTICIPANT&&this.events.trigger(g.PARTICIPANT_MOVE_REQUEST_TO_PARTICIPANTS,{})};triggerMainCamControl=e=>{const t=e.getHeader(u.MAIN_CAM),s=e.getHeader(u.MEDIA_SYNC),i=s===x.ADMIN_SYNC_FORCED;if(t===P.ADMIN_START_MAIN_CAM){this.events.trigger(g.ADMIN_START_MAIN_CAM,{isSyncForced:i});return}if(t===P.ADMIN_STOP_MAIN_CAM){this.events.trigger(g.ADMIN_STOP_MAIN_CAM,{isSyncForced:i});return}(t===P.RESUME_MAIN_CAM||t===P.PAUSE_MAIN_CAM)&&s!==void 0&&this.events.trigger(g.ADMIN_FORCE_SYNC_MEDIA_STATE,{isSyncForced:i});const r=e.getHeader(u.MAIN_CAM_RESOLUTION);this.events.trigger(g.MAIN_CAM_CONTROL,{mainCam:t,resolutionMainCam:r})};triggerMicControl=e=>{const t=e.getHeader(u.MIC),i=e.getHeader(u.MEDIA_SYNC)===x.ADMIN_SYNC_FORCED;t===H.ADMIN_START_MIC?this.events.trigger(g.ADMIN_START_MIC,{isSyncForced:i}):t===H.ADMIN_STOP_MIC&&this.events.trigger(g.ADMIN_STOP_MIC,{isSyncForced:i})};triggerUseLicense=e=>{const t=e.getHeader(u.CONTENT_USE_LICENSE);this.events.trigger(g.USE_LICENSE,t)}}function Fe(n){return e=>`sip:${e}@${n}`}const ke=(n,e)=>()=>Math.floor(Math.random()*(e-n))+n,oe=n=>n.trim().replaceAll(" ","_"),$e=ke(1e5,99999999),qe=n=>n.some(t=>{const{kind:s}=t;return s==="video"});var N=(n=>(n.PEER_CONNECTION="peerconnection",n.CONNECTING="connecting",n.SENDING="sending",n.PROGRESS="progress",n.ACCEPTED="accepted",n.CONFIRMED="confirmed",n.ENDED="ended",n.FAILED="failed",n.NEW_DTMF="newDTMF",n.NEW_INFO="newInfo",n.HOLD="hold",n.UNHOLD="unhold",n.MUTED="muted",n.UNMUTED="unmuted",n.REINVITE="reinvite",n.UPDATE="update",n.REFER="refer",n.REPLACES="replaces",n.SDP="sdp",n.ICE_CANDIDATE="icecandidate",n.GET_USER_MEDIA_FAILED="getusermediafailed",n.PEER_CONNECTION_CREATE_OFFER_FAILED="peerconnection:createofferfailed",n.PEER_CONNECTION_CREATE_ANSWER_FAILED="peerconnection:createanswerfailed",n.PEER_CONNECTION_SET_LOCAL_DESCRIPTION_FAILED="peerconnection:setlocaldescriptionfailed",n.PEER_CONNECTION_SET_REMOTE_DESCRIPTION_FAILED="peerconnection:setremotedescriptionfailed",n.START_PRESENTATION="presentation:start",n.STARTED_PRESENTATION="presentation:started",n.END_PRESENTATION="presentation:end",n.ENDED_PRESENTATION="presentation:ended",n.FAILED_PRESENTATION="presentation:failed",n.PEER_CONNECTION_CONFIRMED="peerconnection:confirmed",n.PEER_CONNECTION_ONTRACK="peerconnection:ontrack",n.ENDED_FROM_SERVER="ended:fromserver",n.CALL_STATUS_CHANGED="call-status-changed",n))(N||{}),ce=(n=>(n.LOCAL="local",n.REMOTE="remote",n.SYSTEM="system",n))(ce||{});const he=["peerconnection","connecting","sending","progress","accepted","confirmed","ended","failed","newInfo","newDTMF","presentation:start","presentation:started","presentation:end","presentation:ended","presentation:failed","reinvite","update","refer","replaces","sdp","icecandidate","getusermediafailed","peerconnection:createofferfailed","peerconnection:createanswerfailed","peerconnection:setlocaldescriptionfailed","peerconnection:setremotedescriptionfailed"],We=["peerconnection:confirmed","peerconnection:ontrack","ended:fromserver","call-status-changed"],de=[...he,...We],Ve=(n,e)=>{n.getVideoTracks().forEach(s=>{"contentHint"in s&&s.contentHint!==e&&(s.contentHint=e)})},L=(n,{directionVideo:e,directionAudio:t,contentHint:s}={})=>{if(!n||e==="recvonly"&&t==="recvonly")return;const i=t==="recvonly"?[]:n.getAudioTracks(),r=e==="recvonly"?[]:n.getVideoTracks(),a=[...i,...r],o=new MediaStream(a);return o.getTracks=()=>[...o.getAudioTracks(),...o.getVideoTracks()],s&&s!=="none"&&Ve(o,s),o};var X=(n=>(n.BYE="Terminated",n.WEBRTC_ERROR="WebRTC Error",n.CANCELED="Canceled",n.REQUEST_TIMEOUT="Request Timeout",n.REJECTED="Rejected",n.REDIRECTED="Redirected",n.UNAVAILABLE="Unavailable",n.NOT_FOUND="Not Found",n.ADDRESS_INCOMPLETE="Address Incomplete",n.INCOMPATIBLE_SDP="Incompatible SDP",n.BAD_MEDIA_DESCRIPTION="Bad Media Description",n))(X||{});class He{events;rtcSession;disposers=new Set;onReset;constructor(e,{onReset:t}){this.events=e,this.onReset=t,e.on(N.FAILED,this.handleEnded),e.on(N.ENDED,this.handleEnded)}get connection(){return this.rtcSession?.connection}get isCallActive(){return this.rtcSession?.isEstablished()===!0}getEstablishedRTCSession=()=>this.rtcSession?.isEstablished()===!0?this.rtcSession:void 0;startCall=async(e,t,{number:s,mediaStream:i,extraHeaders:r=[],ontrack:a,iceServers:o,directionVideo:c,directionAudio:d,contentHint:T,offerToReceiveAudio:S=!0,offerToReceiveVideo:l=!0,degradationPreference:A,sendEncodings:p,onAddedTransceiver:R})=>new Promise((M,$)=>{this.handleCall({ontrack:a}).then(M).catch(q=>{$(q)}),this.rtcSession=e.call(t(s),{mediaStream:L(i,{directionVideo:c,directionAudio:d,contentHint:T}),pcConfig:{iceServers:o},rtcOfferConstraints:{offerToReceiveAudio:S,offerToReceiveVideo:l},eventHandlers:this.events.triggers,extraHeaders:r,directionVideo:c,directionAudio:d,degradationPreference:A,sendEncodings:p,onAddedTransceiver:R})});async endCall(){const{rtcSession:e}=this;if(e&&!e.isEnded())return e.terminateAsync({cause:X.CANCELED}).finally(()=>{this.reset()});this.reset()}answerToIncomingCall=async(e,{mediaStream:t,ontrack:s,extraHeaders:i=[],iceServers:r,directionVideo:a,directionAudio:o,offerToReceiveAudio:c,offerToReceiveVideo:d,contentHint:T,degradationPreference:S,sendEncodings:l,onAddedTransceiver:A})=>new Promise((p,R)=>{try{this.rtcSession=e,this.subscribeToSessionEvents(e),this.handleCall({ontrack:s}).then(p).catch(M=>{R(M)}),e.answer({pcConfig:{iceServers:r},rtcOfferConstraints:{offerToReceiveAudio:c,offerToReceiveVideo:d},mediaStream:L(t,{directionVideo:a,directionAudio:o,contentHint:T}),extraHeaders:i,directionVideo:a,directionAudio:o,degradationPreference:S,sendEncodings:l,onAddedTransceiver:A})}catch(M){R(M)}});getRemoteTracks(){return this.connection?this.connection.getReceivers().map(({track:s})=>s):void 0}async replaceMediaStream(e,t){if(!this.rtcSession)throw new Error("No rtcSession established");const{contentHint:s}=t??{},i=L(e,{contentHint:s});if(i===void 0)throw new Error("No preparedMediaStream");return this.rtcSession.replaceMediaStream(i,t)}async restartIce(e){if(!this.rtcSession)throw new Error("No rtcSession established");return this.rtcSession.restartIce(e)}handleCall=async({ontrack:e})=>new Promise((t,s)=>{const i=()=>{this.events.on(N.PEER_CONNECTION,T),this.events.on(N.CONFIRMED,S)},r=()=>{this.events.off(N.PEER_CONNECTION,T),this.events.off(N.CONFIRMED,S)},a=()=>{this.events.on(N.FAILED,c),this.events.on(N.ENDED,c)},o=()=>{this.events.off(N.FAILED,c),this.events.off(N.ENDED,c)},c=l=>{r(),o(),s(l)};let d;const T=({peerconnection:l})=>{d=l;const A=p=>{this.events.trigger(N.PEER_CONNECTION_ONTRACK,p),e&&e(p)};l.addEventListener("track",A),this.disposers.add(()=>{l.removeEventListener("track",A)})},S=()=>{d!==void 0&&this.events.trigger(N.PEER_CONNECTION_CONFIRMED,d),r(),o(),t(d)};i(),a()});subscribeToSessionEvents(e){this.events.eachTriggers((t,s)=>{const i=he.find(r=>r===s);i&&(e.on(i,t),this.disposers.add(()=>{e.off(i,t)}))})}unsubscribeFromSessionEvents(){this.disposers.forEach(e=>{e()}),this.disposers.clear()}handleEnded=e=>{const{originator:t}=e;t==="remote"&&this.events.trigger(N.ENDED_FROM_SERVER,e),this.reset()};reset=()=>{delete this.rtcSession,this.unsubscribeFromSessionEvents(),this.onReset()}}class xe{remoteStreams={};reset(){this.remoteStreams={}}generateStream(e,t){const{id:s}=e,i=this.remoteStreams[s]??new MediaStream;return t&&i.addTrack(t),i.addTrack(e),this.remoteStreams[s]=i,i}generateAudioStream(e){const{id:t}=e,s=this.remoteStreams[t]??new MediaStream;return s.addTrack(e),this.remoteStreams[t]=s,s}generateStreams(e){const t=[];return e.forEach((s,i)=>{if(s.kind==="audio")return;const r=s,a=e[i-1];let o;a?.kind==="audio"&&(o=a);const c=this.generateStream(r,o);t.push(c)}),t}generateAudioStreams(e){return e.map(t=>this.generateAudioStream(t))}}class Ge{events;isPendingCall=!1;isPendingAnswer=!1;rtcSession;remoteStreams={};callConfiguration={};remoteStreamsManager=new xe;mcuSession;constructor(){this.events=new O.TypedEvents(de),this.mcuSession=new He(this.events,{onReset:this.reset}),this.subscribeCallStatusChange()}get requested(){return this.isPendingCall||this.isPendingAnswer}get connection(){return this.mcuSession.connection}get isCallActive(){return this.mcuSession.isCallActive}getEstablishedRTCSession=()=>this.mcuSession.getEstablishedRTCSession();on(e,t){return this.events.on(e,t)}onRace(e,t){return this.events.onRace(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}startCall=async(e,t,s)=>(this.isPendingCall=!0,this.callConfiguration.number=s.number,this.callConfiguration.answer=!1,this.mcuSession.startCall(e,t,s).finally(()=>{this.isPendingCall=!1}));async endCall(){return this.mcuSession.endCall()}answerToIncomingCall=async(e,t)=>{this.isPendingAnswer=!0;const s=e();return this.callConfiguration.answer=!0,this.callConfiguration.number=s.remote_identity.uri.user,this.mcuSession.answerToIncomingCall(s,t).finally(()=>{this.isPendingAnswer=!1})};getCallConfiguration(){return{...this.callConfiguration}}getRemoteStreams(){const e=this.mcuSession.getRemoteTracks();if(e)return qe(e)?this.remoteStreamsManager.generateStreams(e):this.remoteStreamsManager.generateAudioStreams(e)}async replaceMediaStream(e,t){return this.mcuSession.replaceMediaStream(e,t)}async restartIce(e){return this.mcuSession.restartIce(e)}reset=()=>{this.remoteStreamsManager.reset(),this.callConfiguration.number=void 0,this.callConfiguration.answer=!1};subscribeCallStatusChange(){let{isCallActive:e}=this;const{ACCEPTED:t,CONFIRMED:s,ENDED:i,FAILED:r}=N;this.onRace([t,s,i,r],()=>{e=this.maybeTriggerCallStatus(e)})}maybeTriggerCallStatus(e){const t=this.isCallActive;return t!==e&&this.events.trigger(N.CALL_STATUS_CHANGED,{isCallActive:t}),t}}const Qe=(n,e)=>(n.degradationPreference=e.degradationPreference,n),Ye=(n,e)=>{n.encodings??=[];for(let t=n.encodings.length;t<e;t+=1)n.encodings.push({});return n},le=n=>(e,t)=>t!==void 0&&e!==t||t===void 0&&e!==n,ze=le(),Xe=(n,e)=>{if(ze(n,e))return n},Je=(n,e)=>{const t=n.maxBitrate,s=Xe(e,t);return s!==void 0&&(n.maxBitrate=s),n},ue=1,Ke=le(ue),je=(n,e)=>{const t=n===void 0?void 0:Math.max(n,ue);if(t!==void 0&&Ke(t,e))return t},Ze=(n,e)=>{const t=n.scaleResolutionDownBy,s=je(e,t);return s!==void 0&&(n.scaleResolutionDownBy=s),n},et=(n,e)=>{const t=e.encodings?.length??0;return Ye(n,t),n.encodings.forEach((s,i)=>{const r=(e?.encodings??[])[i],a=r?.maxBitrate,o=r?.scaleResolutionDownBy;Je(s,a),Ze(s,o)}),n},tt=(n,e)=>{if(n.codecs?.length!==e.codecs?.length)return!0;for(let t=0;t<(n.codecs?.length??0);t++)if(JSON.stringify(n.codecs[t])!==JSON.stringify(e.codecs[t]))return!0;if(n.headerExtensions?.length!==e.headerExtensions?.length)return!0;for(let t=0;t<(n.headerExtensions?.length??0);t++)if(JSON.stringify(n.headerExtensions[t])!==JSON.stringify(e.headerExtensions[t]))return!0;if(n.encodings?.length!==e.encodings?.length)return!0;for(let t=0;t<(n.encodings?.length??0);t++)if(JSON.stringify(n.encodings[t])!==JSON.stringify(e.encodings[t]))return!0;return n.rtcp?.cname!==e.rtcp?.cname||n.rtcp?.reducedSize!==e.rtcp?.reducedSize||n.degradationPreference!==e.degradationPreference},ge=async(n,e)=>{const t=n.getParameters(),s=JSON.parse(JSON.stringify(t));et(t,e),Qe(t,e);const i=tt(s,t);return i&&await n.setParameters(t),{parameters:t,isChanged:i}},J=async(n,e,t)=>{const{isChanged:s,parameters:i}=await ge(n,{encodings:[{scaleResolutionDownBy:e.scaleResolutionDownBy,maxBitrate:e.maxBitrate}]});return s&&t&&t(i),{isChanged:s,parameters:i}},nt=(n,e)=>n.find(t=>t.track!==null&&e.getTracks().includes(t.track)),st=async(n,e,t)=>{const s=nt(n,e);if(s)return J(s,{maxBitrate:t})};var v=(n=>(n.START_PRESENTATION="presentation:start",n.STARTED_PRESENTATION="presentation:started",n.END_PRESENTATION="presentation:end",n.ENDED_PRESENTATION="presentation:ended",n.FAILED_PRESENTATION="presentation:failed",n))(v||{});const Te=["presentation:start","presentation:started","presentation:end","presentation:ended","presentation:failed"],it=1,rt=n=>Q.hasCanceledError(n);class at{events;promisePendingStartPresentation;promisePendingStopPresentation;streamPresentationCurrent;maxBitrate;cancelableSendPresentationWithRepeatedCalls;callManager;constructor({callManager:e,maxBitrate:t}){this.callManager=e,this.maxBitrate=t,this.events=new O.TypedEvents(Te),this.subscribe()}get isPendingPresentation(){return!!this.promisePendingStartPresentation||!!this.promisePendingStopPresentation}async startPresentation(e,t,{isNeedReinvite:s,contentHint:i,sendEncodings:r,onAddedTransceiver:a}={},o){const c=this.getRtcSessionProtected();if(this.streamPresentationCurrent)throw new Error("Presentation is already started");return this.sendPresentationWithDuplicatedCalls(e,{rtcSession:c,stream:t,presentationOptions:{isNeedReinvite:s,contentHint:i,sendEncodings:r,onAddedTransceiver:a},options:o})}async stopPresentation(e){this.cancelSendPresentationWithRepeatedCalls();const t=this.streamPresentationCurrent;let s=this.promisePendingStartPresentation??Promise.resolve(void 0);this.promisePendingStartPresentation&&await this.promisePendingStartPresentation.catch(()=>{});const i=this.callManager.getEstablishedRTCSession();return i&&t?s=e().then(async()=>i.stopPresentation(t)).catch(r=>{const a=r instanceof Error?r:new Error(String(r));throw this.events.trigger(v.FAILED_PRESENTATION,a),r}):t&&this.events.trigger(v.ENDED_PRESENTATION,t),this.promisePendingStopPresentation=s,s.finally(()=>{this.resetPresentation()})}async updatePresentation(e,t,{contentHint:s,sendEncodings:i,onAddedTransceiver:r}={}){const a=this.getRtcSessionProtected();if(!this.streamPresentationCurrent)throw new Error("Presentation has not started yet");return this.promisePendingStartPresentation&&await this.promisePendingStartPresentation,this.sendPresentation(e,a,t,{contentHint:s,isNeedReinvite:!1,sendEncodings:i,onAddedTransceiver:r}).then(async o=>(await this.setMaxBitrate(),o))}cancelSendPresentationWithRepeatedCalls(){this.cancelableSendPresentationWithRepeatedCalls?.stopRepeatedCalls()}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}subscribe(){this.callManager.on("presentation:start",e=>{this.events.trigger(v.START_PRESENTATION,e)}),this.callManager.on("presentation:started",e=>{this.events.trigger(v.STARTED_PRESENTATION,e)}),this.callManager.on("presentation:end",e=>{this.events.trigger(v.END_PRESENTATION,e)}),this.callManager.on("presentation:ended",e=>{this.events.trigger(v.ENDED_PRESENTATION,e)}),this.callManager.on("presentation:failed",e=>{this.events.trigger(v.FAILED_PRESENTATION,e)}),this.callManager.on("failed",this.handleEnded),this.callManager.on("ended",this.handleEnded)}async sendPresentationWithDuplicatedCalls(e,{rtcSession:t,stream:s,presentationOptions:i,options:r={callLimit:it}}){const a=async()=>this.sendPresentation(e,t,s,i),o=()=>!!this.streamPresentationCurrent;return this.cancelableSendPresentationWithRepeatedCalls=Q.repeatedCallsAsync({targetFunction:a,isComplete:o,isRejectAsValid:!0,...r}),this.cancelableSendPresentationWithRepeatedCalls.then(c=>c)}async sendPresentation(e,t,s,{isNeedReinvite:i=!0,contentHint:r="detail",degradationPreference:a,sendEncodings:o,onAddedTransceiver:c}){const d=L(s,{contentHint:r});if(d===void 0)throw new Error("No streamPresentationTarget");this.streamPresentationCurrent=d;const T=e().then(async()=>t.startPresentation(d,i,{degradationPreference:a,sendEncodings:o,onAddedTransceiver:c})).then(this.setMaxBitrate).then(()=>s).catch(S=>{this.removeStreamPresentationCurrent();const l=S instanceof Error?S:new Error(String(S));throw this.events.trigger(v.FAILED_PRESENTATION,l),S});return this.promisePendingStartPresentation=T,T.finally(()=>{this.promisePendingStartPresentation=void 0})}setMaxBitrate=async()=>{const{connection:e}=this.callManager,{streamPresentationCurrent:t}=this,{maxBitrate:s}=this;if(!e||!t||s===void 0)return;const i=e.getSenders();await st(i,t,s)};getRtcSessionProtected=()=>{const e=this.callManager.getEstablishedRTCSession();if(!e)throw new Error("No rtcSession established");return e};handleEnded=()=>{this.reset()};reset(){this.cancelSendPresentationWithRepeatedCalls(),this.resetPresentation()}resetPresentation(){this.removeStreamPresentationCurrent(),this.promisePendingStartPresentation=void 0,this.promisePendingStopPresentation=void 0}removeStreamPresentationCurrent(){delete this.streamPresentationCurrent}}class ot{data;getUa;constructor(e){this.getUa=e.getUa}isConfigured(){return this.getUa()!==void 0}get(){if(this.data!==void 0)return{...this.data}}set(e){if(e===void 0){this.data=void 0;return}this.data={...e}}update(e,t){if(this.data===void 0)throw new Error("data is not exist");this.data[e]=t}clear(){this.data=void 0}isRegister(){return this.data?.register===!0}getSipServerUrl(){return this.data?.sipServerUrl}getDisplayName(){return this.data?.displayName}getUser(){return this.data?.user}getPassword(){return this.data?.password}isRegisterEnabled(){return this.data?.register===!0}}var C=(n=>(n.CONNECTING="connecting",n.CONNECTED="connected",n.DISCONNECTED="disconnected",n.DISCONNECTING="disconnecting",n.NEW_RTC_SESSION="newRTCSession",n.REGISTERED="registered",n.UNREGISTERED="unregistered",n.REGISTRATION_FAILED="registrationFailed",n.NEW_MESSAGE="newMessage",n.SIP_EVENT="sipEvent",n.CONNECT_STARTED="connect-started",n.CONNECT_SUCCEEDED="connect-succeeded",n.CONNECT_FAILED="connect-failed",n.CONNECT_PARAMETERS_RESOLVE_SUCCESS="connect-parameters-resolve-success",n.CONNECT_PARAMETERS_RESOLVE_FAILED="connect-parameters-resolve-failed",n.CONNECTED_WITH_CONFIGURATION="connected-with-configuration",n))(C||{});const Se=["connecting","connected","disconnected","newRTCSession","registered","unregistered","registrationFailed","newMessage","sipEvent"],ct=["disconnecting","connect-started","connect-succeeded","connect-failed","connect-parameters-resolve-success","connect-parameters-resolve-failed","connected-with-configuration"],Ce=[...Se,...ct],ht=3;class dt{cancelableConnectWithRepeatedCalls;JsSIP;events;uaFactory;stateMachine;registrationManager;getUa;setUa;getConnectionConfiguration;setConnectionConfiguration;updateConnectionConfiguration;setSipServerUrl;setSocket;constructor(e){this.JsSIP=e.JsSIP,this.events=e.events,this.uaFactory=e.uaFactory,this.stateMachine=e.stateMachine,this.registrationManager=e.registrationManager,this.getUa=e.getUa,this.setUa=e.setUa,this.getConnectionConfiguration=e.getConnectionConfiguration,this.setConnectionConfiguration=e.setConnectionConfiguration,this.updateConnectionConfiguration=e.updateConnectionConfiguration,this.setSipServerUrl=e.setSipServerUrl,this.setSocket=e.setSocket,this.proxyEvents()}connect=async(e,t)=>(this.cancelRequests(),this.connectWithDuplicatedCalls(e,t));set=async({displayName:e})=>new Promise((t,s)=>{const i=this.getUa();if(!i){s(new Error("this.ua is not initialized"));return}let r=!1;const a=this.getConnectionConfiguration();e!==void 0&&e!==a?.displayName&&(r=i.set("display_name",oe(e)),this.updateConnectionConfiguration("displayName",e));const o=r;o?t(o):s(new Error("nothing changed"))});disconnect=async()=>{this.events.trigger(C.DISCONNECTING,{});const e=new Promise(s=>{this.events.once(C.DISCONNECTED,()=>{s()})}),t=this.getUa();return t?t.stop():this.events.trigger(C.DISCONNECTED,{socket:{},error:!1}),e.finally(()=>{t?.removeAllListeners(),this.setUa(void 0),this.stateMachine.reset()})};cancelRequests(){this.cancelConnectWithRepeatedCalls()}connectWithDuplicatedCalls=async(e,{callLimit:t=ht}={})=>{const s=async()=>this.connectInner(e),i=r=>{const c=this.getUa()?.isConnected()===!0&&this.hasEqualConnectionConfiguration(e),d=r!=null&&!Ue(r);return c||d};return this.stateMachine.startConnect(),this.cancelableConnectWithRepeatedCalls=Q.repeatedCallsAsync({targetFunction:s,isComplete:i,callLimit:t,isRejectAsValid:!0,isCheckBeforeCall:!1}),this.cancelableConnectWithRepeatedCalls.then(r=>{if("ua"in r&&r.ua instanceof this.JsSIP.UA)return r;throw r})};hasEqualConnectionConfiguration(e){const{configuration:t}=this.uaFactory.createConfiguration(e),i=this.getUa()?.configuration;return i?i.password===t.password&&i.register===t.register&&i.uri.toString()===t.uri&&i.display_name===t.display_name&&i.user_agent===t.user_agent&&i.sockets===t.sockets&&i.session_timers===t.session_timers&&i.register_expires===t.register_expires&&i.connection_recovery_min_interval===t.connection_recovery_min_interval&&i.connection_recovery_max_interval===t.connection_recovery_max_interval:!1}connectInner=async e=>this.initUa(e).then(async()=>this.start()).then(t=>{const s=this.getConnectionConfiguration();if(s===void 0)throw new Error("connectionConfiguration has not defined");return{...s,ua:t}});initUa=async({user:e,password:t,sipServerUrl:s,sipWebSocketServerURL:i,remoteAddress:r,sessionTimers:a,registerExpires:o,connectionRecoveryMinInterval:c,connectionRecoveryMaxInterval:d,userAgent:T,displayName:S="",register:l=!1,extraHeaders:A=[]})=>{this.stateMachine.startInitUa(),this.setConnectionConfiguration({sipServerUrl:s,displayName:S,register:l,user:e,password:t}),this.getUa()&&await this.disconnect();const{ua:R,helpers:M}=this.uaFactory.createUAWithConfiguration({user:e,password:t,sipServerUrl:s,sipWebSocketServerURL:i,displayName:S,register:l,sessionTimers:a,registerExpires:o,connectionRecoveryMinInterval:c,connectionRecoveryMaxInterval:d,userAgent:T,remoteAddress:r,extraHeaders:A},this.events);return this.setUa(R),this.setSipServerUrl(M.getSipServerUrl),this.setSocket(M.socket),R};start=async()=>new Promise((e,t)=>{const s=this.getUa();if(!s){t(new Error("this.ua is not initialized"));return}let i;i=((c,d)=>{if(this.getConnectionConfiguration()?.register===!0)return this.registrationManager.subscribeToStartEvents(c,d);const S=C.CONNECTED,l=[C.DISCONNECTED];return this.events.on(S,c),l.forEach(A=>{this.events.on(A,d)}),()=>{this.events.off(S,c),l.forEach(A=>{this.events.off(A,d)})}})(()=>{i?.(),e(s)},c=>{i?.(),t(c)}),s.start()});cancelConnectWithRepeatedCalls(){this.cancelableConnectWithRepeatedCalls?.cancel()}proxyEvents(){this.events.on(C.CONNECTED,()=>{const e=this.getConnectionConfiguration(),t=this.getUa();e!==void 0&&t!==void 0&&this.events.trigger(C.CONNECTED_WITH_CONFIGURATION,{...e,ua:t})})}}var Ee=(n=>(n.START_CONNECT="START_CONNECT",n.START_INIT_UA="START_INIT_UA",n.UA_CONNECTED="UA_CONNECTED",n.UA_REGISTERED="UA_REGISTERED",n.UA_UNREGISTERED="UA_UNREGISTERED",n.UA_DISCONNECTED="UA_DISCONNECTED",n.CONNECTION_FAILED="CONNECTION_FAILED",n.RESET="RESET",n))(Ee||{});const lt=ie.setup({types:{context:{},events:{}},actions:{logTransition:(n,e)=>{h(`State transition: ${e.from} -> ${e.to} (${e.event})`)},logStateChange:(n,e)=>{h("ConnectionStateMachine state changed",e.state)}}}).createMachine({id:"connection",initial:"idle",context:{},states:{idle:{entry:{type:"logStateChange",params:{state:"idle"}},on:{START_CONNECT:{target:"connecting",actions:{type:"logTransition",params:{from:"idle",to:"connecting",event:"START_CONNECT"}}}}},connecting:{entry:{type:"logStateChange",params:{state:"connecting"}},on:{START_INIT_UA:{target:"initializing",actions:{type:"logTransition",params:{from:"connecting",to:"initializing",event:"START_INIT_UA"}}},UA_DISCONNECTED:{target:"disconnected",actions:{type:"logTransition",params:{from:"connecting",to:"disconnected",event:"UA_DISCONNECTED"}}},CONNECTION_FAILED:{target:"failed",actions:{type:"logTransition",params:{from:"connecting",to:"failed",event:"CONNECTION_FAILED"}}}}},initializing:{entry:{type:"logStateChange",params:{state:"initializing"}},on:{UA_CONNECTED:{target:"connected",actions:{type:"logTransition",params:{from:"initializing",to:"connected",event:"UA_CONNECTED"}}},UA_REGISTERED:{target:"registered",actions:{type:"logTransition",params:{from:"initializing",to:"registered",event:"UA_REGISTERED"}}},UA_DISCONNECTED:{target:"disconnected",actions:{type:"logTransition",params:{from:"initializing",to:"disconnected",event:"UA_DISCONNECTED"}}},CONNECTION_FAILED:{target:"failed",actions:{type:"logTransition",params:{from:"initializing",to:"failed",event:"CONNECTION_FAILED"}}}}},connected:{entry:{type:"logStateChange",params:{state:"connected"}},on:{UA_REGISTERED:{target:"registered",actions:{type:"logTransition",params:{from:"connected",to:"registered",event:"UA_REGISTERED"}}},UA_DISCONNECTED:{target:"disconnected",actions:{type:"logTransition",params:{from:"connected",to:"disconnected",event:"UA_DISCONNECTED"}}},CONNECTION_FAILED:{target:"failed",actions:{type:"logTransition",params:{from:"connected",to:"failed",event:"CONNECTION_FAILED"}}}}},registered:{entry:{type:"logStateChange",params:{state:"registered"}},on:{UA_UNREGISTERED:{target:"connected",actions:{type:"logTransition",params:{from:"registered",to:"connected",event:"UA_UNREGISTERED"}}},UA_DISCONNECTED:{target:"disconnected",actions:{type:"logTransition",params:{from:"registered",to:"disconnected",event:"UA_DISCONNECTED"}}},CONNECTION_FAILED:{target:"failed",actions:{type:"logTransition",params:{from:"registered",to:"failed",event:"CONNECTION_FAILED"}}}}},disconnected:{entry:{type:"logStateChange",params:{state:"disconnected"}},on:{RESET:{target:"idle",actions:{type:"logTransition",params:{from:"disconnected",to:"idle",event:"RESET"}}},START_CONNECT:{target:"connecting",actions:{type:"logTransition",params:{from:"disconnected",to:"connecting",event:"START_CONNECT"}}}}},failed:{entry:{type:"logStateChange",params:{state:"failed"}},on:{RESET:{target:"idle",actions:{type:"logTransition",params:{from:"failed",to:"idle",event:"RESET"}}},START_CONNECT:{target:"connecting",actions:{type:"logTransition",params:{from:"failed",to:"connecting",event:"START_CONNECT"}}}}}}});class ut{actor;stateChangeListeners=new Set;events;unsubscribeFromEvents;actorSubscription;constructor(e){this.events=e,this.actor=ie.createActor(lt),this.actorSubscription=this.actor.subscribe(t=>{const s=t.value;this.stateChangeListeners.forEach(i=>{i(s)})}),this.actor.start(),this.subscribeToEvents()}get state(){return this.actor.getSnapshot().value}get isIdle(){return this.hasState("idle")}get isConnecting(){return this.hasState("connecting")}get isInitializing(){return this.hasState("initializing")}get isConnected(){return this.hasState("connected")}get isRegistered(){return this.hasState("registered")}get isDisconnected(){return this.hasState("disconnected")}get isFailed(){return this.hasState("failed")}get isPending(){return this.isConnecting||this.isInitializing}get isPendingConnect(){return this.isConnecting}get isPendingInitUa(){return this.isInitializing}get isActiveConnection(){return this.isConnected||this.isRegistered}startConnect(){this.toStartConnect()}startInitUa(){this.toStartInitUa()}reset(){this.toIdle()}destroy(){this.unsubscribeFromEvents?.(),this.actorSubscription?.unsubscribe(),this.actor.stop()}onStateChange(e){return this.stateChangeListeners.add(e),()=>{this.stateChangeListeners.delete(e)}}canTransition(e){return this.actor.getSnapshot().can({type:e})}getValidEvents(){return Object.values(Ee).filter(e=>this.canTransition(e))}hasState(e){return this.actor.getSnapshot().matches(e)}sendEvent(e){const t=this.actor.getSnapshot(),s={type:e};if(!t.can(s)){h(`Invalid transition: ${s.type} from ${this.state}. Event cannot be processed in current state.`);return}this.actor.send(s)}toStartConnect=()=>{this.sendEvent("START_CONNECT")};toStartInitUa=()=>{this.sendEvent("START_INIT_UA")};toConnected=()=>{this.sendEvent("UA_CONNECTED")};toRegistered=()=>{this.sendEvent("UA_REGISTERED")};toUnregistered=()=>{this.sendEvent("UA_UNREGISTERED")};toDisconnected=()=>{this.sendEvent("UA_DISCONNECTED")};toFailed=()=>{this.sendEvent("CONNECTION_FAILED")};toIdle=()=>{this.sendEvent("RESET")};subscribeToEvents(){this.events.on("connected",this.toConnected),this.events.on("registered",this.toRegistered),this.events.on("unregistered",this.toUnregistered),this.events.on("disconnected",this.toDisconnected),this.events.on("registrationFailed",this.toFailed),this.unsubscribeFromEvents=()=>{this.events.off("connected",this.toConnected),this.events.off("registered",this.toRegistered),this.events.off("unregistered",this.toUnregistered),this.events.off("disconnected",this.toDisconnected),this.events.off("registrationFailed",this.toFailed)}}}class gt{events;getUaProtected;constructor(e){this.events=e.events,this.getUaProtected=e.getUaProtected}async register(){const e=this.getUaProtected();return new Promise((t,s)=>{e.on(C.REGISTERED,t),e.on(C.REGISTRATION_FAILED,s),e.register()})}async unregister(){const e=this.getUaProtected();return new Promise(t=>{e.on(C.UNREGISTERED,t),e.unregister()})}async tryRegister(){try{await this.unregister()}catch(e){h("tryRegister",e)}return this.register()}subscribeToStartEvents(e,t){const s=C.REGISTERED,i=[C.REGISTRATION_FAILED,C.DISCONNECTED];return this.events.on(s,e),i.forEach(r=>{this.events.on(r,t)}),()=>{this.events.off(s,e),i.forEach(r=>{this.events.off(r,t)})}}}class Tt{uaFactory;getUaProtected;constructor(e){this.uaFactory=e.uaFactory,this.getUaProtected=e.getUaProtected}async sendOptions(e,t,s){const i=this.getUaProtected();return new Promise((r,a)=>{try{i.sendOptions(e,t,{extraHeaders:s,eventHandlers:{succeeded:()=>{r()},failed:a}})}catch(o){a(o)}})}async ping(e,t){const i=this.getUaProtected().configuration.uri;return this.sendOptions(i,e,t)}async checkTelephony({userAgent:e,displayName:t,sipServerUrl:s,sipWebSocketServerURL:i,remoteAddress:r,extraHeaders:a}){return new Promise((o,c)=>{const{configuration:d}=this.uaFactory.createConfiguration({sipWebSocketServerURL:i,displayName:t,userAgent:e,sipServerUrl:s}),T=this.uaFactory.createUA({...d,remoteAddress:r,extraHeaders:a}),S=()=>{const A=new Error("Telephony is not available");c(A)};T.once(C.DISCONNECTED,S);const l=()=>{T.removeAllListeners(),T.once(C.DISCONNECTED,()=>{o()}),T.stop()};T.once(C.CONNECTED,l),T.start()})}}const St=n=>{const e=[];return n!==void 0&&n!==""&&e.push(`X-Vinteo-Remote: ${n}`),e};class b{JsSIP;constructor(e){this.JsSIP=e}static isRegisteredUA(e){return!!e&&e.isRegistered()}static validateParametersConnection({register:e,password:t,user:s,sipServerUrl:i,sipWebSocketServerURL:r}){if(!i)throw new Error("sipServerUrl is required");if(!r)throw new Error("sipWebSocketServerURL is required");if(e&&(t===void 0||t===""))throw new Error("password is required for authorized connection");if(e&&(s===void 0||s===""))throw new Error("user is required for authorized connection")}static resolveAuthorizationUser(e,t){return e&&t!==void 0&&t.trim()!==""?t.trim():`${$e()}`}static buildExtraHeaders(e,t){const s=e!==void 0&&e!==""?St(e):[];return t===void 0?s:[...s,...t]}createConfiguration({user:e,password:t,sipWebSocketServerURL:s,displayName:i="",sipServerUrl:r,register:a=!1,sessionTimers:o=!1,registerExpires:c=300,connectionRecoveryMinInterval:d=2,connectionRecoveryMaxInterval:T=6,userAgent:S}){b.validateParametersConnection({register:a,password:t,user:e,sipServerUrl:r,sipWebSocketServerURL:s});const l=b.resolveAuthorizationUser(a,e),A=Fe(r),p=A(l),R=new this.JsSIP.WebSocketInterface(s);return{configuration:{password:t,register:a,uri:p,display_name:oe(i),user_agent:S,sdpSemantics:"unified-plan",sockets:[R],session_timers:o,register_expires:c,connection_recovery_min_interval:d,connection_recovery_max_interval:T},helpers:{socket:R,getSipServerUrl:A}}}createUA({remoteAddress:e,extraHeaders:t,...s}){const i=new this.JsSIP.UA(s),r=b.buildExtraHeaders(e,t);return r.length>0&&i.registrator().setExtraHeaders(r),i}createUAWithConfiguration(e,t){const{configuration:s,helpers:i}=this.createConfiguration(e),r=this.createUA({...s,remoteAddress:e.remoteAddress,extraHeaders:e.extraHeaders});return t.eachTriggers((a,o)=>{const c=Se.find(d=>d===o);c&&r.on(c,a)}),{ua:r,helpers:i}}}const Ae="Not ready for connection",Ne=n=>n instanceof Error&&n.message===Ae,Ct=()=>new Error(Ae),Et=async n=>typeof n=="function"?n():n;class At{events;ua;socket;uaFactory;registrationManager;stateMachine;connectionFlow;sipOperations;configurationManager;JsSIP;constructor({JsSIP:e}){this.JsSIP=e,this.events=new O.TypedEvents(Ce),this.uaFactory=new b(e),this.registrationManager=new gt({events:this.events,getUaProtected:this.getUaProtected}),this.stateMachine=new ut(this.events),this.configurationManager=new ot({getUa:this.getUa}),this.sipOperations=new Tt({uaFactory:this.uaFactory,getUaProtected:this.getUaProtected}),this.connectionFlow=new dt({JsSIP:this.JsSIP,events:this.events,uaFactory:this.uaFactory,stateMachine:this.stateMachine,registrationManager:this.registrationManager,getUa:this.getUa,getConnectionConfiguration:this.getConnectionConfiguration,setConnectionConfiguration:t=>{this.configurationManager.set(t)},updateConnectionConfiguration:(t,s)=>{this.configurationManager.update(t,s)},setUa:t=>{this.ua=t},setSipServerUrl:t=>{this.getSipServerUrl=t},setSocket:t=>{this.socket=t}})}get requested(){return this.stateMachine.isPending}get isPendingConnect(){return this.stateMachine.isPendingConnect}get isPendingInitUa(){return this.stateMachine.isPendingInitUa}get isIdle(){return this.stateMachine.isIdle}get isDisconnected(){return this.stateMachine.isDisconnected}get isFailed(){return this.stateMachine.isFailed}get connectionState(){return this.stateMachine.state}get isRegistered(){return b.isRegisteredUA(this.ua)}get isRegisterConfig(){return this.configurationManager.isRegister()}connect=async(e,t)=>this.disconnect().catch(s=>{h("connect: disconnect error",s)}).then(async()=>this.connectWithProcessError(e,t));set=async({displayName:e})=>this.connectionFlow.set({displayName:e});disconnect=async()=>{if(this.isConfigured())return this.connectionFlow.disconnect()};async register(){return this.registrationManager.register()}async unregister(){return this.registrationManager.unregister()}tryRegister=async()=>this.registrationManager.tryRegister();sendOptions=async(e,t,s)=>this.sipOperations.sendOptions(e,t,s);ping=async(e,t)=>this.sipOperations.ping(e,t);checkTelephony=async e=>this.sipOperations.checkTelephony(e);on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}isConfigured(){return this.configurationManager.isConfigured()}getConnectionConfiguration=()=>this.configurationManager.get();destroy(){this.stateMachine.destroy()}getSipServerUrl=e=>e;getUaProtected=()=>{if(!this.ua)throw new Error("UA not initialized");return this.ua};getUa=()=>this.ua;connectWithProcessError=async(e,t)=>{if(!(t?.hasReadyForConnection?.()??!0))throw Ct();return this.processConnect(e,t).catch(async i=>{const r=i;return this.disconnect().then(()=>{throw r}).catch(()=>{throw r})})};processConnect=async(e,t)=>(this.events.trigger(C.CONNECT_STARTED,{}),Et(e).then(s=>(this.events.trigger(C.CONNECT_PARAMETERS_RESOLVE_SUCCESS,s),s)).catch(s=>{throw this.events.trigger(C.CONNECT_PARAMETERS_RESOLVE_FAILED,s),s}).then(async s=>this.connectionFlow.connect(s,t)).then(s=>(this.events.trigger(C.CONNECT_SUCCEEDED,{...s}),s)).catch(s=>{const i=s??new Error("Failed to connect to server");throw this.events.trigger(C.CONNECT_FAILED,i),i}))}class Nt{connectionManager;stackPromises=Y.createStackPromises({noRunIsNotActual:!0});constructor({connectionManager:e}){this.connectionManager=e}connect=async(...e)=>this.stackPromises.run(async()=>this.connectionManager.connect(...e));disconnect=async()=>this.stackPromises.run(async()=>this.connectionManager.disconnect());stop(){this.stackPromises.stop()}}const j=0,Rt=30;class It{countInner=j;initialCount=j;limitInner=Rt;isInProgress=!1;onStatusChange;constructor({onStatusChange:e}){this.onStatusChange=e}get count(){return this.countInner}get limit(){return this.limitInner}get isAttemptInProgress(){return this.isInProgress}hasLimitReached(){return this.countInner>=this.limitInner}startAttempt(){this.isInProgress||(this.isInProgress=!0,this.onStatusChange({isInProgress:this.isInProgress}))}finishAttempt(){this.isInProgress&&(this.isInProgress=!1,this.onStatusChange({isInProgress:this.isInProgress}))}increment(){this.count<this.limit&&(this.countInner+=1)}reset(){this.countInner=this.initialCount,this.finishAttempt()}}class pt{connectionManager;interval;checkTelephonyByTimeout=void 0;cancelableBeforeRequest=void 0;constructor({connectionManager:e,interval:t}){this.connectionManager=e,this.interval=t}start({onBeforeRequest:e,onSuccessRequest:t,onFailRequest:s}){this.stop(),this.cancelableBeforeRequest=new k.CancelableRequest(e),this.checkTelephonyByTimeout=y.resolveRequesterByTimeout({isDontStopOnFail:!0,requestInterval:this.interval,request:async()=>{if(!this.cancelableBeforeRequest)throw new Error("cancelableBeforeRequest is not defined");const i=await this.cancelableBeforeRequest.request();return this.connectionManager.checkTelephony(i)}}),this.checkTelephonyByTimeout.start(void 0,{onFailRequest:s,onSuccessRequest:()=>{this.stop(),t()}})}stop(){this.checkTelephonyByTimeout?.stop(),this.checkTelephonyByTimeout=void 0,this.cancelableBeforeRequest?.cancelRequest(),this.cancelableBeforeRequest=void 0}}var _=(n=>(n.BEFORE_ATTEMPT="before-attempt",n.SUCCESS="success",n.FAILED_ALL_ATTEMPTS="failed-all-attempts",n.CANCELLED_ATTEMPTS="cancelled-attempts",n.CHANGED_ATTEMPT_STATUS="changed-attempt-status",n.STOP_ATTEMPTS_BY_ERROR="stop-attempts-by-error",n.LIMIT_REACHED_ATTEMPTS="limit-reached-attempts",n))(_||{});const Re=["before-attempt","success","failed-all-attempts","cancelled-attempts","changed-attempt-status","stop-attempts-by-error","limit-reached-attempts"],mt=15e3,_t=2;class Mt{connectionManager;pingServerByTimeoutWithFailCalls;constructor({connectionManager:e}){this.connectionManager=e,this.pingServerByTimeoutWithFailCalls=y.requesterByTimeoutsWithFailCalls(_t,{whenPossibleRequest:async()=>{},requestInterval:mt,request:async()=>(h("ping"),this.connectionManager.ping().then(()=>{h("ping success")}))})}start({onFailRequest:e}){this.pingServerByTimeoutWithFailCalls.start(void 0,{onFailRequest:e}).catch(h)}stop(){this.pingServerByTimeoutWithFailCalls.stop()}}class ft{callManager;pingServerRequester;disposeCallStatusChange;constructor({connectionManager:e,callManager:t}){this.callManager=t,this.pingServerRequester=new Mt({connectionManager:e})}start({onFailRequest:e}){h("start"),this.disposeCallStatusChange=this.callManager.on("call-status-changed",()=>{this.handleCallStatusChange({onFailRequest:e})}),this.handleCallStatusChange({onFailRequest:e})}stop(){h("stop"),this.pingServerRequester.stop(),this.unsubscribeCallStatusChange()}unsubscribeCallStatusChange(){this.disposeCallStatusChange?.(),this.disposeCallStatusChange=void 0}handleCallStatusChange({onFailRequest:e}){this.callManager.isCallActive?this.pingServerRequester.stop():this.pingServerRequester.start({onFailRequest:e})}}class Pt{connectionManager;callManager;isRegistrationFailed=!1;disposers=[];constructor({connectionManager:e,callManager:t}){this.connectionManager=e,this.callManager=t}subscribe(e){this.unsubscribe(),this.disposers.push(this.connectionManager.on("registrationFailed",()=>{this.setIsRegistrationFailed()})),this.disposers.push(this.callManager.on("call-status-changed",({isCallActive:t})=>{!t&&this.isRegistrationFailed&&e()}))}unsubscribe(){this.disposers.forEach(e=>{e()}),this.disposers=[],this.resetIsRegistrationFailed()}setIsRegistrationFailed(){this.isRegistrationFailed=!0}resetIsRegistrationFailed(){this.isRegistrationFailed=!1}}const vt=3e3,Ot=15e3,Z={LIMIT_REACHED:"Limit reached",FAILED_TO_RECONNECT:"Failed to reconnect"},Dt=async()=>{},bt=n=>!0;class yt{events;connectionManager;connectionQueueManager;checkTelephonyRequester;pingServerIfNotActiveCallRequester;registrationFailedOutOfCallSubscriber;attemptsState;delayBetweenAttempts;cancelableRequestBeforeRetry;onBeforeRetry;canRetryOnError;networkInterfacesSubscriber;resumeFromSleepModeSubscriber;constructor({connectionQueueManager:e,connectionManager:t,callManager:s},i){const r=i?.onBeforeRetry??Dt,a=i?.canRetryOnError??bt;this.connectionQueueManager=e,this.connectionManager=t,this.onBeforeRetry=r,this.canRetryOnError=a,this.networkInterfacesSubscriber=i?.networkInterfacesSubscriber,this.resumeFromSleepModeSubscriber=i?.resumeFromSleepModeSubscriber,this.events=new O.TypedEvents(Re),this.checkTelephonyRequester=new pt({connectionManager:t,interval:i?.checkTelephonyRequestInterval??Ot}),this.pingServerIfNotActiveCallRequester=new ft({connectionManager:t,callManager:s}),this.registrationFailedOutOfCallSubscriber=new Pt({connectionManager:t,callManager:s}),this.attemptsState=new It({onStatusChange:this.emitStatusChange}),this.cancelableRequestBeforeRetry=new k.CancelableRequest(r),this.delayBetweenAttempts=new y.DelayRequester(i?.timeoutBetweenAttempts??vt)}start(e){h("auto connector start"),this.restartConnectionAttempts(e),this.subscribeToHardwareTriggers(e)}stop(){h("auto connector stop"),this.unsubscribeFromHardwareTriggers(),this.stopConnectionFlow().catch(e=>{h("auto connector stop from stop method: error",e)})}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}restartConnectionAttempts(e){h("auto connector restart connection attempts"),this.stopConnectionFlow().then(async()=>this.attemptConnection(e)).catch(t=>{h("auto connector failed to restart connection attempts:",t)})}async stopConnectionFlow(){h("stopConnectionFlow"),this.stopAttempts(),this.stopConnectTriggers(),await this.connectionQueueManager.disconnect()}stopAttempts(){this.attemptsState.isAttemptInProgress&&this.connectionQueueManager.stop(),this.delayBetweenAttempts.cancelRequest(),this.cancelableRequestBeforeRetry.cancelRequest(),this.attemptsState.reset()}stopConnectTriggers(){h("stopConnectTriggers"),this.stopPingRequester(),this.checkTelephonyRequester.stop(),this.registrationFailedOutOfCallSubscriber.unsubscribe()}startCheckTelephony(e){h("startCheckTelephony"),this.checkTelephonyRequester.start({onBeforeRequest:async()=>(await this.onBeforeRetry(),e.getParameters()),onSuccessRequest:()=>{h("startCheckTelephony: onSuccessRequest"),this.connectIfDisconnected(e)},onFailRequest:t=>{h("startCheckTelephony: onFailRequest",t.message)}})}async attemptConnection(e){if(h("attemptConnection: attempts.count",this.attemptsState.count),this.events.trigger(_.BEFORE_ATTEMPT,{}),this.stopConnectTriggers(),this.attemptsState.hasLimitReached()){h("attemptConnection: limit reached"),this.handleLimitReached(e);return}return this.attemptsState.startAttempt(),this.attemptsState.increment(),this.executeConnectionAttempt(e)}async executeConnectionAttempt(e){try{await this.connectionQueueManager.connect(e.getParameters,e.options),h("executeConnectionAttempt: success"),this.handleSucceededAttempt(e)}catch(t){this.handleConnectionError(t,e)}}handleConnectionError(e,t){if(Ne(e)){this.attemptsState.finishAttempt(),this.events.trigger(_.STOP_ATTEMPTS_BY_ERROR,e);return}if(!this.canRetryOnError(e)){h("executeConnectionAttempt: error does not allow retry",e),this.attemptsState.finishAttempt(),this.events.trigger(_.STOP_ATTEMPTS_BY_ERROR,e);return}if(Y.isPromiseIsNotActualError(e)){h("executeConnectionAttempt: not actual error",e),this.attemptsState.finishAttempt(),this.events.trigger(_.CANCELLED_ATTEMPTS,e);return}h("executeConnectionAttempt: error",e),this.scheduleReconnect(t)}handleLimitReached(e){this.attemptsState.finishAttempt(),this.events.trigger(_.LIMIT_REACHED_ATTEMPTS,new Error(Z.LIMIT_REACHED)),this.startCheckTelephony(e)}handleSucceededAttempt(e){h("handleSucceededAttempt"),this.subscribeToConnectTriggers(e),this.events.trigger(_.SUCCESS)}subscribeToConnectTriggers(e){this.startPingRequester(e),this.registrationFailedOutOfCallSubscriber.subscribe(()=>{h("registrationFailedOutOfCallListener callback"),this.restartConnectionAttempts(e)})}subscribeToHardwareTriggers(e){this.unsubscribeFromHardwareTriggers(),h("subscribeToHardwareTriggers"),this.networkInterfacesSubscriber?.subscribe({onChange:()=>{h("networkInterfacesSubscriber onChange"),this.restartConnectionAttempts(e)},onUnavailable:()=>{h("networkInterfacesSubscriber onUnavailable"),this.stopConnectionFlow().catch(t=>{h("auto connector stop from networkInterfacesSubscriber onUnavailable: error",t)})}}),this.resumeFromSleepModeSubscriber?.subscribe({onResume:()=>{h("resumeFromSleepModeSubscriber onResume"),this.restartConnectionAttempts(e)}})}unsubscribeFromHardwareTriggers(){h("unsubscribeFromHardwareTriggers"),this.networkInterfacesSubscriber?.unsubscribe(),this.resumeFromSleepModeSubscriber?.unsubscribe()}stopPingRequester(){this.pingServerIfNotActiveCallRequester.stop()}startPingRequester(e){this.pingServerIfNotActiveCallRequester.start({onFailRequest:()=>{h("pingRequester: onFailRequest"),this.restartConnectionAttempts(e)}})}connectIfDisconnected(e){const t=this.isConnectionUnavailable();h("connectIfDisconnected: isUnavailable",t),t?this.restartConnectionAttempts(e):(this.stopConnectTriggers(),this.events.trigger(_.SUCCESS))}scheduleReconnect(e){h("scheduleReconnect"),this.delayBetweenAttempts.request().then(async()=>(h("scheduleReconnect: delayBetweenAttempts success"),this.cancelableRequestBeforeRetry.request())).then(async()=>(h("scheduleReconnect: onBeforeRetry success"),this.attemptConnection(e))).catch(t=>{const s=t instanceof Error?t:new Error(Z.FAILED_TO_RECONNECT);this.attemptsState.finishAttempt(),k.isCanceledError(t)||y.hasCanceledError(t)?this.events.trigger(_.CANCELLED_ATTEMPTS,s):this.events.trigger(_.FAILED_ALL_ATTEMPTS,s),h("scheduleReconnect: error",t)})}isConnectionUnavailable(){const{isFailed:e,isDisconnected:t,isIdle:s}=this.connectionManager;return e||t||s}emitStatusChange=({isInProgress:e})=>{this.events.trigger(_.CHANGED_ATTEMPT_STATUS,{isInProgress:e})}}var U=(n=>(n.INCOMING_CALL="incomingCall",n.DECLINED_INCOMING_CALL="declinedIncomingCall",n.TERMINATED_INCOMING_CALL="terminatedIncomingCall",n.FAILED_INCOMING_CALL="failedIncomingCall",n))(U||{});const Ie=["incomingCall","declinedIncomingCall","terminatedIncomingCall","failedIncomingCall"],wt=486,Ut=487;class Lt{events;incomingRTCSession;connectionManager;constructor(e){this.connectionManager=e,this.events=new O.TypedEvents(Ie),this.start()}get remoteCallerData(){return{displayName:this.incomingRTCSession?.remote_identity.display_name,host:this.incomingRTCSession?.remote_identity.uri.host,incomingNumber:this.incomingRTCSession?.remote_identity.uri.user,rtcSession:this.incomingRTCSession}}get isAvailableIncomingCall(){return!!this.incomingRTCSession}start(){this.subscribe()}stop(){this.unsubscribe(),this.removeIncomingSession()}getIncomingRTCSession=()=>{const{incomingRTCSession:e}=this;if(!e)throw new Error("No incomingRTCSession");return e};extractIncomingRTCSession=()=>{const e=this.getIncomingRTCSession();return this.removeIncomingSession(),e};async declineToIncomingCall({statusCode:e=Ut}={}){return new Promise((t,s)=>{try{const i=this.getIncomingRTCSession(),r=this.remoteCallerData;this.removeIncomingSession(),this.events.trigger(U.DECLINED_INCOMING_CALL,r),i.terminate({status_code:e}),t()}catch(i){s(i)}})}async busyIncomingCall(){return this.declineToIncomingCall({statusCode:wt})}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}subscribe(){this.connectionManager.on("newRTCSession",this.handleNewRTCSession)}unsubscribe(){this.connectionManager.off("newRTCSession",this.handleNewRTCSession)}handleNewRTCSession=({originator:e,session:t})=>{e==="remote"&&this.setIncomingSession(t)};setIncomingSession(e){this.incomingRTCSession=e;const t=this.remoteCallerData;e.on("failed",s=>{this.removeIncomingSession(),s.originator==="local"?this.events.trigger(U.TERMINATED_INCOMING_CALL,t):this.events.trigger(U.FAILED_INCOMING_CALL,t)}),this.events.trigger(U.INCOMING_CALL,t)}removeIncomingSession(){delete this.incomingRTCSession}}const w=1e3;var E=(n=>(n.INBOUND_RTP="inbound-rtp",n.REMOTE_OUTBOUND_RTP="remote-outbound-rtp",n.MEDIA_SOURCE="media-source",n.OUTBOUND_RTP="outbound-rtp",n.REMOTE_INBOUND_RTP="remote-inbound-rtp",n.CODEC="codec",n.CANDIDATE_PAIR="candidate-pair",n.CERTIFICATE="certificate",n.TRANSPORT="transport",n.LOCAL_CANDIDATE="local-candidate",n.REMOTE_CANDIDATE="remote-candidate",n))(E||{});const pe=["collected"],ee=()=>"performance"in window?performance.now():Date.now(),B=n=>[...n.keys()].reduce((e,t)=>{const s=n.get(t);return s===void 0?e:{...e,[s.type]:s}},{}),Bt=n=>{if(!n)return{outboundRtp:void 0,codec:void 0,mediaSource:void 0,remoteInboundRtp:void 0};const e=B(n);return{outboundRtp:e[E.OUTBOUND_RTP],codec:e[E.CODEC],mediaSource:e[E.MEDIA_SOURCE],remoteInboundRtp:e[E.REMOTE_INBOUND_RTP]}},te=n=>{if(!n)return{outboundRtp:void 0,codec:void 0,mediaSource:void 0,remoteInboundRtp:void 0};const e=B(n);return{outboundRtp:e[E.OUTBOUND_RTP],codec:e[E.CODEC],mediaSource:e[E.MEDIA_SOURCE],remoteInboundRtp:e[E.REMOTE_INBOUND_RTP]}},ne=({videoReceiversStats:n,synchronizationSourcesVideo:e})=>{if(!n)return{inboundRtp:void 0,codec:void 0,synchronizationSources:e};const t=B(n);return{inboundRtp:t[E.INBOUND_RTP],codec:t[E.CODEC],synchronizationSources:e}},Ft=({audioReceiverStats:n,synchronizationSourcesAudio:e})=>{if(!n)return{inboundRtp:void 0,codec:void 0,remoteOutboundRtp:void 0,synchronizationSources:e};const t=B(n);return{inboundRtp:t[E.INBOUND_RTP],codec:t[E.CODEC],remoteOutboundRtp:t[E.REMOTE_OUTBOUND_RTP],synchronizationSources:e}},me=n=>{if(!n)return{candidatePair:void 0,certificate:void 0,localCandidate:void 0,remoteCandidate:void 0,transport:void 0};const e=B(n);return{candidatePair:e[E.CANDIDATE_PAIR],certificate:e[E.CERTIFICATE],localCandidate:e[E.LOCAL_CANDIDATE],remoteCandidate:e[E.REMOTE_CANDIDATE],transport:e[E.TRANSPORT]}},kt=({audioSenderStats:n,videoSenderFirstStats:e,videoSenderSecondStats:t})=>({video:te(e),secondVideo:te(t),audio:Bt(n),additional:me(n??e??t)}),$t=({audioReceiverStats:n,videoReceiverFirstStats:e,videoReceiverSecondStats:t,synchronizationSources:s})=>({video:ne({videoReceiversStats:e,synchronizationSourcesVideo:s.video}),secondVideo:ne({videoReceiversStats:t,synchronizationSourcesVideo:s.video}),audio:Ft({audioReceiverStats:n,synchronizationSourcesAudio:s.audio}),additional:me(n??e??t)}),qt=({audioSenderStats:n,videoSenderFirstStats:e,videoSenderSecondStats:t,audioReceiverStats:s,videoReceiverFirstStats:i,videoReceiverSecondStats:r,synchronizationSources:a})=>{const o=kt({audioSenderStats:n,videoSenderFirstStats:e,videoSenderSecondStats:t}),c=$t({audioReceiverStats:s,videoReceiverFirstStats:i,videoReceiverSecondStats:r,synchronizationSources:a});return{outbound:o,inbound:c}},Wt=async n=>{const e="audio",t="video",s=n.getSenders(),i=s.find(l=>l.track?.kind===e),r=s.filter(l=>l.track?.kind===t),a=n.getReceivers(),o=a.find(l=>l.track.kind===e),c=a.filter(l=>l.track.kind===t),d={trackIdentifier:o?.track.id,item:o?.getSynchronizationSources()[0]},T={trackIdentifier:c[0]?.track.id,item:c[0]?.getSynchronizationSources()[0]},S={audio:d,video:T};return Promise.all([i?.getStats()??Promise.resolve(void 0),r[0]?.getStats()??Promise.resolve(void 0),r[1]?.getStats()??Promise.resolve(void 0),o?.getStats()??Promise.resolve(void 0),c[0]?.getStats()??Promise.resolve(void 0),c[1]?.getStats()??Promise.resolve(void 0)]).then(l=>{const[A,p,R,M,$,q]=l;return{synchronizationSources:S,audioSenderStats:A,videoSenderFirstStats:p,videoSenderSecondStats:R,audioReceiverStats:M,videoReceiverFirstStats:$,videoReceiverSecondStats:q}})},Vt=n=>{h(String(n))};class _e{events;setTimeoutRequest;requesterAllStatistics=new k.CancelableRequest(Wt);constructor(){this.events=new O.TypedEvents(pe),this.setTimeoutRequest=new y.SetTimeoutRequest}get requested(){return this.setTimeoutRequest.requested}start(e,{interval:t=w,onError:s=Vt}={}){this.stop(),this.setTimeoutRequest.request(()=>{this.collectStatistics(e,{onError:s})},t)}stop(){this.setTimeoutRequest.cancelRequest(),this.requesterAllStatistics.cancelRequest()}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}collectStatistics=(e,{onError:t})=>{const s=ee();this.requesterAllStatistics.request(e).then(i=>{this.events.trigger("collected",qt(i));const a=ee()-s;let o=w;a>48?o=w*4:a>32?o=w*3:a>16&&(o=w*2),this.start(e,{onError:t,interval:o})}).catch(i=>{t&&t(i)})}}class Ht{availableIncomingBitrate;statsPeerConnection;callManager;apiManager;previousAvailableIncomingBitrate;constructor({callManager:e,apiManager:t}){this.callManager=e,this.apiManager=t,this.statsPeerConnection=new _e,this.subscribe()}get events(){return this.statsPeerConnection.events}on(e,t){return this.statsPeerConnection.on(e,t)}once(e,t){return this.statsPeerConnection.once(e,t)}onceRace(e,t){return this.statsPeerConnection.onceRace(e,t)}async wait(e){return this.statsPeerConnection.wait(e)}off(e,t){this.statsPeerConnection.off(e,t)}hasAvailableIncomingBitrateChangedQuarter(){const e=this.previousAvailableIncomingBitrate,t=this.availableIncomingBitrate;return e===void 0||t===void 0?!1:e===0?t>0:Math.abs(t-e)/e>=.25}subscribe(){this.callManager.on("peerconnection:confirmed",this.handleStarted),this.callManager.on("failed",this.handleEnded),this.callManager.on("ended",this.handleEnded),this.statsPeerConnection.on("collected",this.handleStatsCollected)}handleStatsCollected=e=>{this.previousAvailableIncomingBitrate=this.availableIncomingBitrate,this.availableIncomingBitrate=e.inbound.additional.candidatePair?.availableIncomingBitrate,this.maybeSendStats()};handleStarted=e=>{this.statsPeerConnection.start(e)};handleEnded=()=>{this.statsPeerConnection.stop(),this.availableIncomingBitrate=void 0,this.previousAvailableIncomingBitrate=void 0};maybeSendStats(){this.availableIncomingBitrate!==void 0&&this.hasAvailableIncomingBitrateChangedQuarter()&&this.apiManager.sendStats({availableIncomingBitrate:this.availableIncomingBitrate}).catch(e=>{h("Failed to send stats",e)})}}const xt=(n,e)=>n.filter(s=>e.some(i=>i.clockRate===s.clockRate&&i.mimeType===s.mimeType&&i.channels===s.channels&&i.sdpFmtpLine===s.sdpFmtpLine)),Gt=n=>{const e=RTCRtpSender.getCapabilities(n),t=RTCRtpReceiver.getCapabilities(n),s=e===null?[]:e.codecs,i=t===null?[]:t.codecs;return xt(s,i)},Qt=(n,e)=>e===void 0||e.length===0?n:n.sort((t,s)=>{const i=e.indexOf(t.mimeType),r=e.indexOf(s.mimeType),a=i===-1?Number.MAX_VALUE:i,o=r===-1?Number.MAX_VALUE:r;return a-o}),Yt=(n,e)=>e===void 0||e.length===0?n:n.filter(t=>!e.includes(t.mimeType)),zt=(n,{preferredMimeTypesVideoCodecs:e,excludeMimeTypesVideoCodecs:t})=>{try{if(typeof n.setCodecPreferences=="function"&&n.sender.track?.kind==="video"&&(e!==void 0&&e.length>0||t!==void 0&&t.length>0)){const s=Gt("video"),i=Yt(s,t),r=Qt(i,e);n.setCodecPreferences(r)}}catch(s){h("setCodecPreferences error",s)}},Xt=n=>[...n.keys()].map(e=>n.get(e)),Jt=(n,e)=>Xt(n).find(t=>t?.type===e),Me=async n=>n.getStats().then(e=>Jt(e,"codec")?.mimeType);class Kt{async getCodecFromSender(e){return await Me(e)??""}}class jt{stackPromises=Y.createStackPromises({noRunIsNotActual:!0});async add(e){return this.stackPromises.add(e),this.run()}stop(){this.stackPromises.stop()}async run(){return this.stackPromises().catch(e=>{h("TaskQueue: error",e)})}}class Zt{taskQueue;onSetParameters;constructor(e){this.onSetParameters=e,this.taskQueue=new jt}async setEncodingsToSender(e,t){return this.taskQueue.add(async()=>J(e,t,this.onSetParameters))}stop(){this.taskQueue.stop()}}const fe=(n,e)=>n!==void 0&&e!==void 0&&n.toLowerCase().includes(e.toLowerCase()),en=1e6,f=n=>n*en,Pe=f(.06),ve=f(4),tn=n=>n<=64?Pe:n<=128?f(.12):n<=256?f(.25):n<=384?f(.32):n<=426?f(.38):n<=640?f(.5):n<=848?f(.7):n<=1280?f(1):n<=1920?f(2):ve,nn="av1",sn=n=>fe(n,nn),rn=.6,K=(n,e)=>sn(e)?n*rn:n,an=n=>K(Pe,n),on=n=>K(ve,n),se=(n,e)=>{const t=tn(n);return K(t,e)},W=1,cn=({videoTrack:n,targetSize:e})=>{const t=n.getSettings(),s=t.width,i=t.height,r=s===void 0?W:s/e.width,a=i===void 0?W:i/e.height;return Math.max(r,a,W)};class hn{ignoreForCodec;senderFinder;codecProvider;parametersSetter;resultNoChanged={isChanged:!1,parameters:{encodings:[{}],transactionId:"0",codecs:[],headerExtensions:[],rtcp:{}}};constructor({senderFinder:e,codecProvider:t,parametersSetter:s},i){this.senderFinder=e,this.codecProvider=t,this.parametersSetter=s,this.ignoreForCodec=i.ignoreForCodec}async balance(e,t){const s=e.getSenders(),i=this.senderFinder.findVideoSender(s);if(!i?.track)return{...this.resultNoChanged,sender:i};const r=await this.codecProvider.getCodecFromSender(i);if(fe(r,this.ignoreForCodec))return{...this.resultNoChanged,sender:i};const{mainCam:a,resolutionMainCam:o}=t??{};return this.processSender({mainCam:a,resolutionMainCam:o},{sender:i,codec:r,videoTrack:i.track}).then(c=>({...c,sender:i}))}async processSender(e,t){const{mainCam:s,resolutionMainCam:i}=e;switch(s){case P.PAUSE_MAIN_CAM:return this.downgradeResolutionSender(t);case P.RESUME_MAIN_CAM:return this.setBitrateByTrackResolution(t);case P.MAX_MAIN_CAM_RESOLUTION:return i!==void 0?this.setResolutionSender(i,t):this.setBitrateByTrackResolution(t);case P.ADMIN_STOP_MAIN_CAM:case P.ADMIN_START_MAIN_CAM:case void 0:return this.setBitrateByTrackResolution(t);default:return this.setBitrateByTrackResolution(t)}}async downgradeResolutionSender(e){const{sender:t,codec:s}=e,i={scaleResolutionDownBy:200,maxBitrate:an(s)};return this.parametersSetter.setEncodingsToSender(t,i)}async setBitrateByTrackResolution(e){const{sender:t,videoTrack:s,codec:i}=e,a=s.getSettings().width,o=a===void 0?on(i):se(a,i);return this.parametersSetter.setEncodingsToSender(t,{scaleResolutionDownBy:1,maxBitrate:o})}async setResolutionSender(e,t){const[s,i]=e.split("x"),{sender:r,videoTrack:a,codec:o}=t,c={width:Number(s),height:Number(i)},d=cn({videoTrack:a,targetSize:c}),T=se(c.width,o),S={scaleResolutionDownBy:d,maxBitrate:T};return this.parametersSetter.setEncodingsToSender(r,S)}}const dn=n=>n.find(e=>e.track?.kind==="video");class ln{findVideoSender(e){return dn(e)}}class un{currentSender;originalReplaceTrack;lastWidth;lastHeight;maxPollIntervalMs;currentPollIntervalMs;pollIntervalMs;setTimeoutRequest;constructor({pollIntervalMs:e=1e3,maxPollIntervalMs:t}){this.pollIntervalMs=e,this.maxPollIntervalMs=t??e*16,this.currentPollIntervalMs=this.pollIntervalMs,this.setTimeoutRequest=new y.SetTimeoutRequest}subscribe(e,t){if(!e){this.detachSender();return}this.currentSender!==e&&(this.detachSender(),this.attachSender(e,t))}unsubscribe(){this.detachSender()}attachSender(e,t){this.currentSender=e;const s=e.replaceTrack.bind(e);this.originalReplaceTrack=s,e.replaceTrack=async i=>{await s(i),this.attachTrack(t,i??void 0),t()},this.attachTrack(t,e.track)}detachSender(){this.currentSender&&this.originalReplaceTrack&&(this.currentSender.replaceTrack=this.originalReplaceTrack),this.originalReplaceTrack=void 0,this.currentSender=void 0,this.detachTrack()}attachTrack(e,t){if(this.detachTrack(),!t)return;const{width:s,height:i}=t.getSettings();this.lastWidth=s,this.lastHeight=i,this.currentPollIntervalMs=this.pollIntervalMs,this.schedulePoll(t,e)}schedulePoll(e,t){const s=()=>{const{width:i,height:r}=e.getSettings();i!==this.lastWidth||r!==this.lastHeight?(this.lastWidth=i,this.lastHeight=r,this.currentPollIntervalMs=this.pollIntervalMs,t()):this.currentPollIntervalMs=Math.min(this.currentPollIntervalMs*2,this.maxPollIntervalMs),this.setTimeoutRequest.request(s,this.currentPollIntervalMs)};this.setTimeoutRequest.request(s,this.currentPollIntervalMs)}detachTrack(){this.setTimeoutRequest.cancelRequest(),this.lastWidth=void 0,this.lastHeight=void 0}}class gn{apiManager;currentHandler;constructor(e){this.apiManager=e}subscribe(e){this.currentHandler=e,this.apiManager.on("main-cam-control",e)}unsubscribe(){this.currentHandler&&(this.apiManager.off("main-cam-control",this.currentHandler),this.currentHandler=void 0)}}class Tn{eventHandler;senderBalancer;parametersSetterWithQueue;getConnection;serverHeaders;trackMonitor;constructor(e,t,{ignoreForCodec:s,onSetParameters:i,pollIntervalMs:r}={}){this.getConnection=t,this.eventHandler=new gn(e),this.parametersSetterWithQueue=new Zt(i),this.senderBalancer=new hn({senderFinder:new ln,codecProvider:new Kt,parametersSetter:this.parametersSetterWithQueue},{ignoreForCodec:s}),this.trackMonitor=new un({pollIntervalMs:r})}subscribe(){this.eventHandler.subscribe(this.handleMainCamControl)}unsubscribe(){this.eventHandler.unsubscribe(),this.parametersSetterWithQueue.stop(),this.reset()}reset(){delete this.serverHeaders,this.trackMonitor.unsubscribe()}async balance(){const e=this.getConnection();if(!e)throw new Error("connection is not exist");const t=await this.senderBalancer.balance(e,this.serverHeaders);return this.trackMonitor.subscribe(t.sender,()=>{this.balance().catch(s=>{h("balance on track change: error",s)})}),t}handleMainCamControl=e=>{this.serverHeaders=e,this.balance().catch(t=>{h("handleMainCamControl: error",t)})}}const Oe=["balancing-scheduled","balancing-started","balancing-stopped","parameters-updated"];class Sn{isBalancingActive=!1;events;callManager;balancingStartDelay;videoSendingBalancer;startBalancingTimer;constructor(e,t,s={}){this.events=new O.TypedEvents(Oe),this.callManager=e,this.balancingStartDelay=s.balancingStartDelay??1e4,this.videoSendingBalancer=new Tn(t,()=>e.connection,{...s,onSetParameters:i=>{this.events.trigger("parameters-updated",i),s.onSetParameters?.(i)}}),this.subscribe()}get isBalancingScheduled(){return this.startBalancingTimer!==void 0}async startBalancing(){this.isBalancingActive||(this.clearStartTimer(),await this.videoSendingBalancer.balance(),this.videoSendingBalancer.subscribe(),this.isBalancingActive=!0,this.events.trigger("balancing-started",{delay:this.balancingStartDelay}))}stopBalancing(){this.clearStartTimer(),this.videoSendingBalancer.unsubscribe(),this.isBalancingActive=!1,this.events.trigger("balancing-stopped",{})}async balance(){return this.videoSendingBalancer.balance()}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}subscribe(){this.callManager.on("peerconnection:confirmed",this.handleCallStarted),this.callManager.on("ended",this.handleCallEnded),this.callManager.on("failed",this.handleCallEnded)}handleCallStarted=()=>{this.scheduleBalancingStart()};handleCallEnded=()=>{this.stopBalancing()};scheduleBalancingStart(){this.clearStartTimer(),this.startBalancingTimer=setTimeout(()=>{this.startBalancingTimer=void 0,this.startBalancing().catch(e=>{h("startBalancing: error",e)})},this.balancingStartDelay),this.events.trigger("balancing-scheduled",{delay:this.balancingStartDelay})}clearStartTimer(){this.startBalancingTimer&&(clearTimeout(this.startBalancingTimer),this.startBalancingTimer=void 0)}}const Cn=1e6,En=Re.map(n=>`auto-connect:${n}`),An=Ce.map(n=>`connection:${n}`),Nn=de.map(n=>`call:${n}`),Rn=ae.map(n=>`api:${n}`),In=Ie.map(n=>`incoming-call:${n}`),pn=Te.map(n=>`presentation:${n}`),mn=pe.map(n=>`stats:${n}`),_n=Oe.map(n=>`video-balancer:${n}`),Mn=[...En,...An,...Nn,...Rn,...In,...pn,...mn,..._n];class fn{events;connectionManager;connectionQueueManager;callManager;autoConnectorManager;apiManager;incomingCallManager;presentationManager;statsManager;videoSendingBalancerManager;preferredMimeTypesVideoCodecs;excludeMimeTypesVideoCodecs;constructor({JsSIP:e},{preferredMimeTypesVideoCodecs:t,excludeMimeTypesVideoCodecs:s,videoBalancerOptions:i,autoConnectorOptions:r}={}){this.preferredMimeTypesVideoCodecs=t,this.excludeMimeTypesVideoCodecs=s,this.events=new O.TypedEvents(Mn),this.connectionManager=new At({JsSIP:e}),this.connectionQueueManager=new Nt({connectionManager:this.connectionManager}),this.callManager=new Ge,this.apiManager=new Be({connectionManager:this.connectionManager,callManager:this.callManager}),this.incomingCallManager=new Lt(this.connectionManager),this.presentationManager=new at({callManager:this.callManager,maxBitrate:Cn}),this.statsManager=new Ht({callManager:this.callManager,apiManager:this.apiManager}),this.autoConnectorManager=new yt({connectionQueueManager:this.connectionQueueManager,connectionManager:this.connectionManager,callManager:this.callManager},r),this.videoSendingBalancerManager=new Sn(this.callManager,this.apiManager,i),this.subscribe()}get requestedConnection(){return this.connectionManager.requested}get isPendingConnect(){return this.connectionManager.isPendingConnect}get isPendingInitUa(){return this.connectionManager.isPendingInitUa}get connectionState(){return this.connectionManager.connectionState}get isRegistered(){return this.connectionManager.isRegistered}get isRegisterConfig(){return this.connectionManager.isRegisterConfig}get socket(){return this.connectionManager.socket}get requestedCall(){return this.callManager.requested}get connection(){return this.callManager.connection}get isCallActive(){return this.callManager.isCallActive}get remoteCallerData(){return this.incomingCallManager.remoteCallerData}get isAvailableIncomingCall(){return this.incomingCallManager.isAvailableIncomingCall}on(e,t){return this.events.on(e,t)}once(e,t){return this.events.once(e,t)}onceRace(e,t){return this.events.onceRace(e,t)}async wait(e){return this.events.wait(e)}off(e,t){this.events.off(e,t)}connect=async(...e)=>this.connectionQueueManager.connect(...e);disconnect=async()=>this.connectionQueueManager.disconnect();register=async()=>this.connectionManager.register();unregister=async()=>this.connectionManager.unregister();tryRegister=async()=>this.connectionManager.tryRegister();set=async(...e)=>this.connectionManager.set(...e);sendOptions=async(e,t,s)=>this.connectionManager.sendOptions(e,t,s);ping=async(e,t)=>this.connectionManager.ping(e,t);checkTelephony=async e=>this.connectionManager.checkTelephony(e);isConfigured=()=>this.connectionManager.isConfigured();getConnectionConfiguration=()=>this.connectionManager.getConnectionConfiguration();getSipServerUrl=e=>this.connectionManager.getSipServerUrl(e);startAutoConnect=(...e)=>{this.autoConnectorManager.start(...e)};stopAutoConnect=()=>{this.autoConnectorManager.stop()};call=async e=>{const{onAddedTransceiver:t,...s}=e;return this.callManager.startCall(this.connectionManager.getUaProtected(),this.getSipServerUrl,{...s,onAddedTransceiver:this.resolveHandleAddTransceiver(t)})};hangUp=async()=>this.callManager.endCall();answerToIncomingCall=async e=>{const{onAddedTransceiver:t,...s}=e;return this.callManager.answerToIncomingCall(this.incomingCallManager.extractIncomingRTCSession,{...s,onAddedTransceiver:this.resolveHandleAddTransceiver(t)})};declineToIncomingCall=async(...e)=>this.incomingCallManager.declineToIncomingCall(...e);getEstablishedRTCSession=()=>this.callManager.getEstablishedRTCSession();getCallConfiguration=()=>this.callManager.getCallConfiguration();getRemoteStreams=()=>this.callManager.getRemoteStreams();replaceMediaStream=async(...e)=>this.callManager.replaceMediaStream(...e);async startPresentation(e,t={}){const{isP2P:s,callLimit:i,onAddedTransceiver:r,...a}=t;return this.presentationManager.startPresentation(async()=>{s===!0?(await this.apiManager.sendMustStopPresentationP2P(),await this.apiManager.askPermissionToStartPresentationP2P()):await this.apiManager.askPermissionToStartPresentation()},e,{...a,onAddedTransceiver:this.resolveHandleAddTransceiver(r)},i===void 0?void 0:{callLimit:i})}async stopPresentation(e={}){const{isP2P:t}=e;return this.presentationManager.stopPresentation(async()=>{await(t===!0?this.apiManager.sendMustStopPresentationP2P():this.apiManager.sendStoppedPresentation())})}async updatePresentation(e,t={}){const{isP2P:s,onAddedTransceiver:i,...r}=t;return this.presentationManager.updatePresentation(async()=>{s===!0?(await this.apiManager.sendMustStopPresentationP2P(),await this.apiManager.askPermissionToStartPresentationP2P()):await this.apiManager.askPermissionToStartPresentation()},e,{...r,onAddedTransceiver:this.resolveHandleAddTransceiver(i)})}async waitChannels(...e){return this.apiManager.waitChannels(...e)}async waitSyncMediaState(...e){return this.apiManager.waitSyncMediaState(...e)}async sendDTMF(...e){return this.apiManager.sendDTMF(...e)}async sendChannels(...e){return this.apiManager.sendChannels(...e)}async sendMediaState(...e){return this.apiManager.sendMediaState(...e)}async sendRefusalToTurnOn(...e){return this.apiManager.sendRefusalToTurnOn(...e)}async sendRefusalToTurnOnMic(...e){return this.apiManager.sendRefusalToTurnOnMic(...e)}async sendRefusalToTurnOnCam(...e){return this.apiManager.sendRefusalToTurnOnCam(...e)}async sendMustStopPresentationP2P(...e){return this.apiManager.sendMustStopPresentationP2P(...e)}async sendStoppedPresentationP2P(...e){return this.apiManager.sendStoppedPresentationP2P(...e)}async sendStoppedPresentation(...e){return this.apiManager.sendStoppedPresentation(...e)}async askPermissionToStartPresentationP2P(...e){return this.apiManager.askPermissionToStartPresentationP2P(...e)}async askPermissionToStartPresentation(...e){return this.apiManager.askPermissionToStartPresentation(...e)}async askPermissionToEnableCam(...e){return this.apiManager.askPermissionToEnableCam(...e)}setCodecPreferences(e){zt(e,{preferredMimeTypesVideoCodecs:this.preferredMimeTypesVideoCodecs,excludeMimeTypesVideoCodecs:this.excludeMimeTypesVideoCodecs})}subscribe(){this.bridgeEvents("auto-connect",this.autoConnectorManager),this.bridgeEvents("connection",this.connectionManager),this.bridgeEvents("call",this.callManager),this.bridgeEvents("api",this.apiManager),this.bridgeEvents("incoming-call",this.incomingCallManager),this.bridgeEvents("presentation",this.presentationManager),this.bridgeEvents("stats",this.statsManager),this.bridgeEvents("video-balancer",this.videoSendingBalancerManager)}bridgeEvents=(e,t)=>{t.events.eachTriggers((s,i)=>{t.on(i,r=>{this.events.trigger(`${e}:${i}`,r)})})};resolveHandleAddTransceiver=e=>async(t,s,i)=>{this.setCodecPreferences(t),await e?.(t,s,i)}}exports.ECallCause=X;exports.EStatsTypes=E;exports.EUseLicense=re;exports.Originator=ce;exports.SipConnector=fn;exports.StatsPeerConnection=_e;exports.disableDebug=be;exports.enableDebug=De;exports.getCodecFromSender=Me;exports.hasCanceledStartPresentationError=rt;exports.hasNotReadyForConnectionError=Ne;exports.logger=h;exports.prepareMediaStream=L;exports.setEncodingsToSender=J;exports.setParametersToSender=ge;
@@ -58,6 +58,5 @@ declare class ApiManager {
58
58
  private readonly triggerMainCamControl;
59
59
  private readonly triggerMicControl;
60
60
  private readonly triggerUseLicense;
61
- private readonly triggerRestart;
62
61
  }
63
62
  export default ApiManager;
@@ -26,7 +26,8 @@ export declare enum EHeader {
26
26
  AVAILABLE_INCOMING_BITRATE = "X-WEBRTC-AVAILABLE-INCOMING-BITRATE",
27
27
  AUDIO_TRACK_COUNT = "X-WEBRTC-AUDIO-TRACK-COUNT",
28
28
  VIDEO_TRACK_COUNT = "X-WEBRTC-VIDEO-TRACK-COUNT",
29
- TRACKS_DIRECTION = "X-WEBRTC-TRACKS-DIRECTION"
29
+ TRACKS_DIRECTION = "X-WEBRTC-TRACKS-DIRECTION",
30
+ AUDIO_ID = "X-WEBRTC-AUDIOID"
30
31
  }
31
32
  export declare enum EShareState {
32
33
  AVAILABLE_SECOND_REMOTE_STREAM = "YOUCANRECEIVECONTENT",
@@ -44,8 +45,7 @@ export declare enum EContentTypeReceived {
44
45
  PARTICIPANT_STATE = "application/vinteo.webrtc.partstate",
45
46
  NOTIFY = "application/vinteo.webrtc.notify",
46
47
  SHARE_STATE = "application/vinteo.webrtc.sharedesktop",
47
- MAIN_CAM = "application/vinteo.webrtc.maincam",
48
- RESTART = "application/vinteo.webrtc.restart"
48
+ MAIN_CAM = "application/vinteo.webrtc.maincam"
49
49
  }
50
50
  export declare enum EContentTypeSent {
51
51
  CHANNELS = "application/vinteo.webrtc.channels",
@@ -75,8 +75,3 @@ export declare enum EUseLicense {
75
75
  VIDEO = "VIDEO",
76
76
  AUDIOPLUSPRESENTATION = "AUDIOPLUSPRESENTATION"
77
77
  }
78
- export declare enum ETracksDirection {
79
- SENDRECV = "SENDRECV",
80
- SENDONLY = "SENDONLY",
81
- RECVONLY = "RECVONLY"
82
- }
@@ -1,12 +1,13 @@
1
1
  import { TypedEvents } from 'events-constructor';
2
2
  import { EUseLicense, EEventsMainCAM } from './constants';
3
- import { TChannels, TParametersModeratorsList, TParametersWebcast, TParametersConferenceParticipantTokenIssued, TRestartData } from './types';
3
+ import { TChannels, TParametersModeratorsList, TParametersWebcast, TParametersConferenceParticipantTokenIssued } from './types';
4
4
  export declare enum EEvent {
5
5
  CHANNELS_NOTIFY = "channels:notify",
6
6
  PARTICIPANT_ADDED_TO_LIST_MODERATORS = "participant:added-to-list-moderators",
7
7
  PARTICIPANT_REMOVED_FROM_LIST_MODERATORS = "participant:removed-from-list-moderators",
8
8
  PARTICIPANT_MOVE_REQUEST_TO_STREAM = "participant:move-request-to-stream",
9
9
  PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS = "participant:move-request-to-spectators",
10
+ PARTICIPANT_MOVE_REQUEST_TO_SPECTATORS_WITH_AUDIO_ID = "participant:move-request-to-spectators-with-audio-id",
10
11
  PARTICIPANT_MOVE_REQUEST_TO_PARTICIPANTS = "participant:move-request-to-participants",
11
12
  PARTICIPATION_ACCEPTING_WORD_REQUEST = "participation:accepting-word-request",
12
13
  PARTICIPATION_CANCELLING_WORD_REQUEST = "participation:cancelling-word-request",
@@ -28,10 +29,9 @@ export declare enum EEvent {
28
29
  AVAILABLE_SECOND_REMOTE_STREAM = "availableSecondRemoteStream",
29
30
  NOT_AVAILABLE_SECOND_REMOTE_STREAM = "notAvailableSecondRemoteStream",
30
31
  MUST_STOP_PRESENTATION = "mustStopPresentation",
31
- NEW_DTMF = "newDTMF",
32
- RESTART = "restart"
32
+ NEW_DTMF = "newDTMF"
33
33
  }
34
- export declare const EVENT_NAMES: readonly ["participation:accepting-word-request", "participation:cancelling-word-request", "participant:move-request-to-stream", "channels:notify", "conference:participant-token-issued", "account:changed", "account:deleted", "webcast:started", "webcast:stopped", "participant:added-to-list-moderators", "participant:removed-from-list-moderators", "participant:move-request-to-spectators", "participant:move-request-to-participants", "channels", "enterRoom", "shareState", "main-cam-control", "useLicense", "admin-start-main-cam", "admin-stop-main-cam", "admin-start-mic", "admin-stop-mic", "admin-force-sync-media-state", "availableSecondRemoteStream", "notAvailableSecondRemoteStream", "mustStopPresentation", "newDTMF", "restart"];
34
+ export declare const EVENT_NAMES: readonly ["participation:accepting-word-request", "participation:cancelling-word-request", "participant:move-request-to-stream", "channels:notify", "conference:participant-token-issued", "account:changed", "account:deleted", "webcast:started", "webcast:stopped", "participant:added-to-list-moderators", "participant:removed-from-list-moderators", "participant:move-request-to-spectators", "participant:move-request-to-spectators-with-audio-id", "participant:move-request-to-participants", "channels", "enterRoom", "shareState", "main-cam-control", "useLicense", "admin-start-main-cam", "admin-stop-main-cam", "admin-start-mic", "admin-stop-mic", "admin-force-sync-media-state", "availableSecondRemoteStream", "notAvailableSecondRemoteStream", "mustStopPresentation", "newDTMF"];
35
35
  export type TEvent = (typeof EVENT_NAMES)[number];
36
36
  export type TEventMap = {
37
37
  'channels:notify': TChannels;
@@ -39,6 +39,9 @@ export type TEventMap = {
39
39
  'participant:removed-from-list-moderators': TParametersModeratorsList;
40
40
  'participant:move-request-to-stream': TParametersModeratorsList;
41
41
  'participant:move-request-to-spectators': Record<string, never>;
42
+ 'participant:move-request-to-spectators-with-audio-id': {
43
+ audioId: string;
44
+ };
42
45
  'participant:move-request-to-participants': Record<string, never>;
43
46
  'participation:accepting-word-request': TParametersModeratorsList;
44
47
  'participation:cancelling-word-request': TParametersModeratorsList;
@@ -79,6 +82,5 @@ export type TEventMap = {
79
82
  newDTMF: {
80
83
  originator: string;
81
84
  };
82
- restart: TRestartData;
83
85
  };
84
86
  export type TEvents = TypedEvents<TEventMap>;
@@ -1,4 +1,3 @@
1
1
  export { default as ApiManager } from './@ApiManager';
2
2
  export { EContentTypeReceived, EContentTypeSent, EEventsMainCAM, EEventsMic, EEventsSyncMediaState, EHeader, EShareState, EUseLicense, } from './constants';
3
3
  export type { TEvent as TApiEvent } from './eventNames';
4
- export type { TRestartData } from './types';
@@ -1,4 +1,3 @@
1
- import { ETracksDirection } from './constants';
2
1
  export declare enum ECMDNotify {
3
2
  CHANNELS = "channels",
4
3
  WEBCAST_STARTED = "WebcastStarted",
@@ -98,8 +97,3 @@ export type TOptionsInfoMediaState = {
98
97
  export type TOptionsExtraHeaders = {
99
98
  extraHeaders?: string[];
100
99
  };
101
- export type TRestartData = {
102
- tracksDirection: ETracksDirection;
103
- audioTrackCount: number;
104
- videoTrackCount: number;
105
- };
@@ -1,28 +1,43 @@
1
+ import { RTCSession } from '@krivega/jssip';
1
2
  import { TEvents, TEventMap } from './eventNames';
2
- import { ICallStrategy } from './types';
3
+ import { TStartCall, TCallConfiguration, TReplaceMediaStream, TAnswerToIncomingCall } from './types';
3
4
  declare class CallManager {
4
5
  readonly events: TEvents;
5
- private strategy;
6
- constructor(strategy?: ICallStrategy);
6
+ protected isPendingCall: boolean;
7
+ protected isPendingAnswer: boolean;
8
+ protected rtcSession?: RTCSession;
9
+ protected remoteStreams: Record<string, MediaStream>;
10
+ protected readonly callConfiguration: TCallConfiguration;
11
+ private readonly remoteStreamsManager;
12
+ private readonly mcuSession;
13
+ constructor();
7
14
  get requested(): boolean;
8
- get connection(): ICallStrategy['connection'];
9
- get isCallActive(): ICallStrategy['isCallActive'];
10
- getEstablishedRTCSession: ICallStrategy['getEstablishedRTCSession'];
15
+ get connection(): RTCPeerConnection | undefined;
16
+ get isCallActive(): boolean;
17
+ getEstablishedRTCSession: () => RTCSession | undefined;
11
18
  on<T extends keyof TEventMap>(eventName: T, handler: (data: TEventMap[T]) => void): () => void;
12
19
  onRace<T extends keyof TEventMap>(eventNames: T[], handler: (data: TEventMap[T], eventName: string) => void): () => void;
13
20
  once<T extends keyof TEventMap>(eventName: T, handler: (data: TEventMap[T]) => void): () => void;
14
21
  onceRace<T extends keyof TEventMap>(eventNames: T[], handler: (data: TEventMap[T], eventName: string) => void): () => void;
15
22
  wait<T extends keyof TEventMap>(eventName: T): Promise<TEventMap[T]>;
16
23
  off<T extends keyof TEventMap>(eventName: T, handler: (data: TEventMap[T]) => void): void;
17
- setStrategy(strategy: ICallStrategy): void;
18
- startCall: ICallStrategy['startCall'];
19
- endCall: ICallStrategy['endCall'];
20
- answerToIncomingCall: ICallStrategy['answerToIncomingCall'];
21
- getCallConfiguration: ICallStrategy['getCallConfiguration'];
22
- getRemoteStreams: ICallStrategy['getRemoteStreams'];
23
- addTransceiver: ICallStrategy['addTransceiver'];
24
- replaceMediaStream: ICallStrategy['replaceMediaStream'];
25
- restartIce: ICallStrategy['restartIce'];
24
+ startCall: TStartCall;
25
+ endCall(): Promise<void>;
26
+ answerToIncomingCall: TAnswerToIncomingCall;
27
+ getCallConfiguration(): {
28
+ answer?: boolean;
29
+ number?: string;
30
+ };
31
+ getRemoteStreams(): MediaStream[] | undefined;
32
+ replaceMediaStream(mediaStream: Parameters<TReplaceMediaStream>[0], options?: Parameters<TReplaceMediaStream>[1]): Promise<void>;
33
+ restartIce(options?: {
34
+ useUpdate?: boolean;
35
+ extraHeaders?: string[];
36
+ rtcOfferConstraints?: RTCOfferOptions;
37
+ sendEncodings?: RTCRtpEncodingParameters[];
38
+ degradationPreference?: RTCDegradationPreference;
39
+ }): Promise<boolean>;
40
+ private readonly reset;
26
41
  private subscribeCallStatusChange;
27
42
  private maybeTriggerCallStatus;
28
43
  }
@@ -24,7 +24,6 @@ export declare class MCUSession implements IMCUSession {
24
24
  sendEncodings?: RTCRtpEncodingParameters[];
25
25
  degradationPreference?: RTCDegradationPreference;
26
26
  }): Promise<boolean>;
27
- addTransceiver(kind: 'audio' | 'video', options?: RTCRtpTransceiverInit): Promise<RTCRtpTransceiver>;
28
27
  private readonly handleCall;
29
28
  private subscribeToSessionEvents;
30
29
  private unsubscribeFromSessionEvents;
@@ -0,0 +1,29 @@
1
+ type TConferenceNumber = string;
2
+ type TSendOfferParams = {
3
+ quality: 'low' | 'medium' | 'high';
4
+ audioChannel: string;
5
+ };
6
+ type TConfig = Pick<TSendOfferParams, 'quality' | 'audioChannel'> & {
7
+ pcConfig?: RTCConfiguration;
8
+ };
9
+ type TTools = {
10
+ sendOffer: (params: TSendOfferParams & {
11
+ conferenceNumber: TConferenceNumber;
12
+ }, offer: RTCSessionDescriptionInit) => Promise<RTCSessionDescription>;
13
+ };
14
+ declare class RecvSession {
15
+ private readonly config;
16
+ private readonly tools;
17
+ private readonly connection;
18
+ constructor(config: TConfig, tools: TTools);
19
+ get settings(): TConfig;
20
+ get peerConnection(): RTCPeerConnection;
21
+ close(): void;
22
+ call(conferenceNumber: TConferenceNumber): Promise<void>;
23
+ private createOffer;
24
+ private setRemoteDescription;
25
+ private waitForTracks;
26
+ private addTransceivers;
27
+ private addRecvOnlyTransceiver;
28
+ }
29
+ export default RecvSession;
@@ -4,5 +4,4 @@ export type { TEventMap } from './eventNames';
4
4
  export { EEvent as ECallEvent } from './eventNames';
5
5
  export type { TEvent as TCallEvent, TEvents as TCallEvents } from './eventNames';
6
6
  export { default as hasCanceledCallError } from './hasCanceledCallError';
7
- export { MCUCallStrategy } from './MCUCallStrategy';
8
7
  export type { TCustomError, TGetServerUrl } from './types';
@@ -37,43 +37,26 @@ export type TCallConfiguration = {
37
37
  answer?: boolean;
38
38
  number?: string;
39
39
  };
40
- export interface ICallStrategy {
41
- readonly requested: boolean;
42
- readonly connection: RTCPeerConnection | undefined;
43
- readonly isCallActive: boolean;
44
- getEstablishedRTCSession: () => RTCSession | undefined;
45
- startCall: (ua: UA, getSipServerUrl: TGetServerUrl, params: TParamsCall) => Promise<RTCPeerConnection>;
46
- endCall: () => Promise<void>;
47
- answerToIncomingCall: (extractIncomingRTCSession: () => RTCSession, params: TParamsAnswerToIncomingCall) => Promise<RTCPeerConnection>;
48
- getCallConfiguration: () => TCallConfiguration;
49
- getRemoteStreams: () => MediaStream[] | undefined;
50
- addTransceiver: (kind: 'audio' | 'video', options?: RTCRtpTransceiverInit) => Promise<RTCRtpTransceiver>;
51
- replaceMediaStream: (mediaStream: MediaStream, options?: {
52
- deleteExisting?: boolean;
53
- addMissing?: boolean;
54
- forceRenegotiation?: boolean;
55
- contentHint?: TContentHint;
56
- degradationPreference?: RTCDegradationPreference;
57
- sendEncodings?: RTCRtpEncodingParameters[];
58
- onAddedTransceiver?: TOnAddedTransceiver;
59
- }) => Promise<void>;
60
- restartIce: (options?: {
61
- extraHeaders?: string[];
62
- useUpdate?: boolean;
63
- rtcOfferConstraints?: RTCOfferOptions;
64
- sendEncodings?: RTCRtpEncodingParameters[];
65
- degradationPreference?: RTCDegradationPreference;
66
- }) => Promise<boolean>;
67
- }
40
+ export type TStartCall = (ua: UA, getSipServerUrl: TGetServerUrl, params: TParamsCall) => Promise<RTCPeerConnection>;
41
+ export type TReplaceMediaStream = (mediaStream: MediaStream, options?: {
42
+ deleteExisting?: boolean;
43
+ addMissing?: boolean;
44
+ forceRenegotiation?: boolean;
45
+ contentHint?: TContentHint;
46
+ degradationPreference?: RTCDegradationPreference;
47
+ sendEncodings?: RTCRtpEncodingParameters[];
48
+ onAddedTransceiver?: TOnAddedTransceiver;
49
+ }) => Promise<void>;
50
+ export type TAnswerToIncomingCall = (extractIncomingRTCSession: () => RTCSession, params: TParamsAnswerToIncomingCall) => Promise<RTCPeerConnection>;
68
51
  export interface IMCUSession {
69
52
  readonly connection: RTCPeerConnection | undefined;
70
53
  readonly isCallActive: boolean;
71
54
  getEstablishedRTCSession: () => RTCSession | undefined;
72
- startCall: ICallStrategy['startCall'];
55
+ startCall: TStartCall;
73
56
  endCall: () => Promise<void>;
74
57
  answerToIncomingCall: (incomingRTCSession: RTCSession, params: TParamsAnswerToIncomingCall) => Promise<RTCPeerConnection>;
75
58
  getRemoteTracks: () => MediaStreamTrack[] | undefined;
76
- replaceMediaStream: ICallStrategy['replaceMediaStream'];
59
+ replaceMediaStream: TReplaceMediaStream;
77
60
  restartIce: (options?: {
78
61
  useUpdate?: boolean;
79
62
  extraHeaders?: string[];
@@ -81,6 +64,5 @@ export interface IMCUSession {
81
64
  sendEncodings?: RTCRtpEncodingParameters[];
82
65
  degradationPreference?: RTCDegradationPreference;
83
66
  }) => Promise<boolean>;
84
- addTransceiver: (kind: 'audio' | 'video', options?: RTCRtpTransceiverInit) => Promise<RTCRtpTransceiver>;
85
67
  }
86
68
  export {};
@@ -6,7 +6,6 @@ import { ConnectionQueueManager } from '../ConnectionQueueManager';
6
6
  import { IncomingCallManager } from '../IncomingCallManager';
7
7
  import { PresentationManager, TContentHint, TOnAddedTransceiver } from '../PresentationManager';
8
8
  import { StatsManager } from '../StatsManager';
9
- import { TransceiverManager } from '../TransceiverManager';
10
9
  import { VideoSendingBalancerManager } from '../VideoSendingBalancerManager';
11
10
  import { TJsSIP } from '../types';
12
11
  import { IBalancerOptions } from '../VideoSendingBalancer';
@@ -22,7 +21,6 @@ declare class SipConnector {
22
21
  readonly presentationManager: PresentationManager;
23
22
  readonly statsManager: StatsManager;
24
23
  readonly videoSendingBalancerManager: VideoSendingBalancerManager;
25
- readonly transceiverManager: TransceiverManager;
26
24
  private readonly preferredMimeTypesVideoCodecs?;
27
25
  private readonly excludeMimeTypesVideoCodecs?;
28
26
  constructor({ JsSIP }: {
@@ -7,7 +7,7 @@ import { TEventMap as TIncomingCallManagerEventMap } from '../IncomingCallManage
7
7
  import { TEventMap as TPresentationManagerEventMap } from '../PresentationManager/eventNames';
8
8
  import { TEventMap as TStatsManagerEventMap } from '../StatsPeerConnection/eventNames';
9
9
  import { TEventMap as TVideoBalancerManagerEventMap } from '../VideoSendingBalancerManager/eventNames';
10
- export declare const EVENT_NAMES: readonly ("auto-connect:before-attempt" | "auto-connect:success" | "auto-connect:failed-all-attempts" | "auto-connect:cancelled-attempts" | "auto-connect:changed-attempt-status" | "auto-connect:stop-attempts-by-error" | "auto-connect:limit-reached-attempts" | "connection:connecting" | "connection:connected" | "connection:disconnected" | "connection:disconnecting" | "connection:newRTCSession" | "connection:registered" | "connection:unregistered" | "connection:registrationFailed" | "connection:newMessage" | "connection:sipEvent" | "connection:connect-started" | "connection:connect-succeeded" | "connection:connected-with-configuration" | "connection:connect-failed" | "connection:connect-parameters-resolve-success" | "connection:connect-parameters-resolve-failed" | "call:peerconnection" | "call:connecting" | "call:sending" | "call:progress" | "call:accepted" | "call:confirmed" | "call:ended" | "call:failed" | "call:newDTMF" | "call:newInfo" | "call:reinvite" | "call:update" | "call:refer" | "call:replaces" | "call:sdp" | "call:icecandidate" | "call:getusermediafailed" | "call:peerconnection:createofferfailed" | "call:peerconnection:createanswerfailed" | "call:peerconnection:setlocaldescriptionfailed" | "call:peerconnection:setremotedescriptionfailed" | "call:presentation:start" | "call:presentation:started" | "call:presentation:end" | "call:presentation:ended" | "call:presentation:failed" | "call:peerconnection:confirmed" | "call:peerconnection:ontrack" | "call:ended:fromserver" | "call:call-status-changed" | "api:channels:notify" | "api:participant:added-to-list-moderators" | "api:participant:removed-from-list-moderators" | "api:participant:move-request-to-stream" | "api:participant:move-request-to-spectators" | "api:participant:move-request-to-participants" | "api:participation:accepting-word-request" | "api:participation:cancelling-word-request" | "api:webcast:started" | "api:webcast:stopped" | "api:account:changed" | "api:account:deleted" | "api:conference:participant-token-issued" | "api:channels" | "api:enterRoom" | "api:shareState" | "api:main-cam-control" | "api:useLicense" | "api:admin-start-main-cam" | "api:admin-stop-main-cam" | "api:admin-start-mic" | "api:admin-stop-mic" | "api:admin-force-sync-media-state" | "api:availableSecondRemoteStream" | "api:notAvailableSecondRemoteStream" | "api:mustStopPresentation" | "api:newDTMF" | "api:restart" | "incoming-call:incomingCall" | "incoming-call:declinedIncomingCall" | "incoming-call:terminatedIncomingCall" | "incoming-call:failedIncomingCall" | "presentation:presentation:start" | "presentation:presentation:started" | "presentation:presentation:end" | "presentation:presentation:ended" | "presentation:presentation:failed" | "stats:collected" | "video-balancer:balancing-scheduled" | "video-balancer:balancing-started" | "video-balancer:balancing-stopped" | "video-balancer:parameters-updated")[];
10
+ export declare const EVENT_NAMES: readonly ("auto-connect:before-attempt" | "auto-connect:success" | "auto-connect:failed-all-attempts" | "auto-connect:cancelled-attempts" | "auto-connect:changed-attempt-status" | "auto-connect:stop-attempts-by-error" | "auto-connect:limit-reached-attempts" | "connection:connecting" | "connection:connected" | "connection:disconnected" | "connection:disconnecting" | "connection:newRTCSession" | "connection:registered" | "connection:unregistered" | "connection:registrationFailed" | "connection:newMessage" | "connection:sipEvent" | "connection:connect-started" | "connection:connect-succeeded" | "connection:connected-with-configuration" | "connection:connect-failed" | "connection:connect-parameters-resolve-success" | "connection:connect-parameters-resolve-failed" | "call:peerconnection" | "call:connecting" | "call:sending" | "call:progress" | "call:accepted" | "call:confirmed" | "call:ended" | "call:failed" | "call:newDTMF" | "call:newInfo" | "call:reinvite" | "call:update" | "call:refer" | "call:replaces" | "call:sdp" | "call:icecandidate" | "call:getusermediafailed" | "call:peerconnection:createofferfailed" | "call:peerconnection:createanswerfailed" | "call:peerconnection:setlocaldescriptionfailed" | "call:peerconnection:setremotedescriptionfailed" | "call:presentation:start" | "call:presentation:started" | "call:presentation:end" | "call:presentation:ended" | "call:presentation:failed" | "call:peerconnection:confirmed" | "call:peerconnection:ontrack" | "call:ended:fromserver" | "call:call-status-changed" | "api:channels:notify" | "api:participant:added-to-list-moderators" | "api:participant:removed-from-list-moderators" | "api:participant:move-request-to-stream" | "api:participant:move-request-to-spectators" | "api:participant:move-request-to-spectators-with-audio-id" | "api:participant:move-request-to-participants" | "api:participation:accepting-word-request" | "api:participation:cancelling-word-request" | "api:webcast:started" | "api:webcast:stopped" | "api:account:changed" | "api:account:deleted" | "api:conference:participant-token-issued" | "api:channels" | "api:enterRoom" | "api:shareState" | "api:main-cam-control" | "api:useLicense" | "api:admin-start-main-cam" | "api:admin-stop-main-cam" | "api:admin-start-mic" | "api:admin-stop-mic" | "api:admin-force-sync-media-state" | "api:availableSecondRemoteStream" | "api:notAvailableSecondRemoteStream" | "api:mustStopPresentation" | "api:newDTMF" | "incoming-call:incomingCall" | "incoming-call:declinedIncomingCall" | "incoming-call:terminatedIncomingCall" | "incoming-call:failedIncomingCall" | "presentation:presentation:start" | "presentation:presentation:started" | "presentation:presentation:end" | "presentation:presentation:ended" | "presentation:presentation:failed" | "stats:collected" | "video-balancer:balancing-scheduled" | "video-balancer:balancing-started" | "video-balancer:balancing-stopped" | "video-balancer:parameters-updated")[];
11
11
  export type TEvent = (typeof EVENT_NAMES)[number];
12
12
  type PrefixedEventMap<T extends Record<string, unknown>, Prefix extends string> = {
13
13
  [K in keyof T as `${Prefix}:${string & K}`]: T[K];
@@ -1,12 +1,10 @@
1
- import { Events } from 'events-constructor';
1
+ import { MediaStreamTrackMock } from 'webrtc-mock';
2
2
  import { default as RTCRtpSenderMock } from './RTCRtpSenderMock';
3
3
  import { RTCPeerConnectionDeprecated } from '@krivega/jssip';
4
- import { MediaStreamTrackMock } from 'webrtc-mock';
5
4
  export declare enum EEvent {
6
5
  TRACK = "track"
7
6
  }
8
- declare const EVENT_NAMES: readonly ["track"];
9
- declare class RTCPeerConnectionMock implements RTCPeerConnectionDeprecated {
7
+ declare class RTCPeerConnectionMock extends EventTarget implements RTCPeerConnectionDeprecated {
10
8
  senders: RTCRtpSender[];
11
9
  receivers: RTCRtpReceiver[];
12
10
  canTrickleIceCandidates: boolean | null;
@@ -33,34 +31,32 @@ declare class RTCPeerConnectionMock implements RTCPeerConnectionDeprecated {
33
31
  remoteDescription: RTCSessionDescription | null;
34
32
  sctp: null;
35
33
  signalingState: RTCSignalingState;
36
- events: Events<typeof EVENT_NAMES>;
37
- constructor(_configuration?: RTCConfiguration, tracks: MediaStreamTrackMock[]);
34
+ close: jest.Mock<any, any, any>;
35
+ setLocalDescription: jest.Mock<Promise<void>, [_description: RTCSessionDescriptionInit], any>;
36
+ setRemoteDescription: jest.Mock<Promise<void>, [_description: RTCSessionDescriptionInit], any>;
37
+ addTransceiver: jest.Mock<RTCRtpTransceiver, [_trackOrKind: string | MediaStreamTrack, _init?: RTCRtpTransceiverInit | undefined], any>;
38
+ createOffer: {
39
+ (options?: RTCOfferOptions): Promise<RTCSessionDescriptionInit>;
40
+ (successCallback: RTCSessionDescriptionCallback, failureCallback: RTCPeerConnectionErrorCallback, options?: RTCOfferOptions): Promise<void>;
41
+ };
42
+ constructor(_configuration?: RTCConfiguration, tracks?: MediaStreamTrackMock[]);
38
43
  getRemoteStreams(): MediaStream[];
39
44
  addIceCandidate(_candidate: RTCIceCandidate | RTCIceCandidateInit): Promise<void>;
40
- addTransceiver(_trackOrKind: MediaStreamTrack | string, _init?: RTCRtpTransceiverInit): RTCRtpTransceiver;
41
- close(): void;
42
45
  restartIce(): void;
43
46
  createAnswer(options?: RTCAnswerOptions): Promise<RTCSessionDescriptionInit>;
44
47
  createAnswer(successCallback: RTCSessionDescriptionCallback, failureCallback: RTCPeerConnectionErrorCallback): Promise<void>;
45
48
  createDataChannel(_label: string, _dataChannelDict?: RTCDataChannelInit): RTCDataChannel;
46
- createOffer(options?: RTCOfferOptions): Promise<RTCSessionDescriptionInit>;
47
- createOffer(successCallback: RTCSessionDescriptionCallback, failureCallback: RTCPeerConnectionErrorCallback, options?: RTCOfferOptions): Promise<void>;
48
49
  getConfiguration(): RTCConfiguration;
49
50
  getIdentityAssertion(): Promise<string>;
50
51
  getStats(_selector?: MediaStreamTrack | null): Promise<RTCStatsReport>;
51
52
  getTransceivers(): RTCRtpTransceiver[];
52
53
  removeTrack(_sender: RTCRtpSender): void;
53
54
  setConfiguration(_configuration: RTCConfiguration): void;
54
- setLocalDescription(_description: RTCSessionDescriptionInit): Promise<void>;
55
- setRemoteDescription(_description: RTCSessionDescriptionInit): Promise<void>;
56
- addEventListener<K extends keyof RTCPeerConnectionEventMap>(type: K, listener: (this: RTCPeerConnection, event_: RTCPeerConnectionEventMap[K]) => unknown, options?: AddEventListenerOptions | boolean): void;
57
- addEventListener(type: string, listener: EventListenerOrEventListenerObject, options?: AddEventListenerOptions | boolean): void;
58
- removeEventListener<K extends keyof RTCPeerConnectionEventMap>(type: K, listener: (this: RTCPeerConnection, event_: RTCPeerConnectionEventMap[K]) => unknown, options?: EventListenerOptions | boolean): void;
59
- removeEventListener(type: string, listener: EventListenerOrEventListenerObject, options?: EventListenerOptions | boolean): void;
60
- dispatchEvent(_event: Event): boolean;
61
55
  getReceivers: () => RTCRtpReceiver[];
62
56
  getSenders: () => RTCRtpSender[];
63
57
  addTrack: (track: MediaStreamTrack, ..._streams: MediaStream[]) => RTCRtpSenderMock;
64
58
  addTrackWithMid: (track: MediaStreamTrack, mid?: string) => RTCRtpSenderMock;
59
+ dispatchTrack(kind: 'audio' | 'video'): void;
60
+ private dispatchTrackInternal;
65
61
  }
66
62
  export default RTCPeerConnectionMock;
@@ -0,0 +1,2 @@
1
+ declare const flushPromises: () => Promise<void>;
2
+ export default flushPromises;