diff --git a/.changeset/yellow-pugs-call.md b/.changeset/yellow-pugs-call.md new file mode 100644 index 000000000..e5ae839d1 --- /dev/null +++ b/.changeset/yellow-pugs-call.md @@ -0,0 +1,7 @@ +--- +'@sw-internal/playground-js': patch +'@signalwire/webrtc': patch +'@signalwire/js': patch +--- + +Expose `destroy` event for inbound calls in Call Fabric to handle cases where the caller cancel the dial before the callee answers. diff --git a/internal/playground-js/src/fabric-callee/index.js b/internal/playground-js/src/fabric-callee/index.js index f7d1971be..67da4392b 100644 --- a/internal/playground-js/src/fabric-callee/index.js +++ b/internal/playground-js/src/fabric-callee/index.js @@ -205,6 +205,9 @@ window.tapPushNotification = async () => { switch (resultType) { case 'inboundCall': window.__call = resultObject + window.__call.on('destroy', () => { + console.warn('Inbound Call got cancelled!!') + }) enableCallButtons() connectStatus.innerHTML = 'Ringing...' break diff --git a/internal/playground-js/src/fabric/index.js b/internal/playground-js/src/fabric/index.js index 8cf7571e1..882560f86 100644 --- a/internal/playground-js/src/fabric/index.js +++ b/internal/playground-js/src/fabric/index.js @@ -245,13 +245,13 @@ window.connect = async () => { nodeId: steeringId, }) + window.__call = call + roomObj = call + await call.start() console.debug('Call Obj', call) - window.__call = call - roomObj = call - const joinHandler = (params) => { console.debug('>> room.joined', params) diff --git a/internal/playground-js/vite.config.ts b/internal/playground-js/vite.config.ts index 8565a2923..96caa63f1 100644 --- a/internal/playground-js/vite.config.ts +++ b/internal/playground-js/vite.config.ts @@ -87,6 +87,14 @@ export default defineConfig({ videoManager: path.resolve(__dirname, 'src/videoManager/index.html'), fabricHttp: path.resolve(__dirname, 'src/fabric-http/index.html'), fabricCallee: path.resolve(__dirname, 'src/fabric-callee/index.html'), + sw: path.resolve(__dirname, 'src/fabric-callee/sw.js'), + }, + output: { + entryFileNames: (assetInfo) => { + return ['sw'].includes(assetInfo.name) + ? 'src/fabric-callee/[name].js' // put service worker in the correct folder + : 'assets/[name]-[hash].js' // others in `assets/` as default + }, }, }, }, diff --git a/packages/js/src/fabric/WSClient.ts b/packages/js/src/fabric/WSClient.ts index aa9689fdb..33b5be390 100644 --- a/packages/js/src/fabric/WSClient.ts +++ b/packages/js/src/fabric/WSClient.ts @@ -104,7 +104,7 @@ export class WSClient { return new Promise(async (resolve, reject) => { try { // @ts-expect-error - call.emitter.once('verto.display', () => resolve(call)) + call.once('verto.display', () => resolve(call)) call.once('room.subscribed', () => resolve(call)) await call.join() diff --git a/packages/webrtc/src/BaseConnection.ts b/packages/webrtc/src/BaseConnection.ts index daa34e8c0..f217645e7 100644 --- a/packages/webrtc/src/BaseConnection.ts +++ b/packages/webrtc/src/BaseConnection.ts @@ -387,10 +387,7 @@ export class BaseConnection this.logger.debug('_triggerNewRTCPeer Start') try { this.logger.debug('Build a new RTCPeer') - const rtcPeer = new RTCPeer(this, 'offer') - this.appendRTCPeer(rtcPeer) - this.logger.debug('Run workers for the new RTCPeer', rtcPeer.uuid) - this.runRTCPeerWorkers(rtcPeer.uuid) + const rtcPeer = this._buildPeer('offer') this.logger.debug('Trigger start for the new RTCPeer!') await rtcPeer.start() } catch (error) { @@ -655,10 +652,8 @@ export class BaseConnection invite(): Promise { return new Promise(async (resolve, reject) => { this.direction = 'outbound' - this.peer = new RTCPeer(this, 'offer') + this.peer = this._buildPeer('offer') try { - this.runRTCPeerWorkers(this.peer.uuid) - await this.peer.start() resolve(this as any as T) } catch (error) { @@ -673,11 +668,9 @@ export class BaseConnection return new Promise(async (resolve, reject) => { this.direction = 'inbound' if (!this.peer) { - this.peer = new RTCPeer(this, 'answer') + this.peer = this._buildPeer('answer') } try { - this.runRTCPeerWorkers(this.peer.uuid) - await this.peer.start() resolve(this as any as T) } catch (error) { @@ -1004,6 +997,7 @@ export class BaseConnection /** @internal */ public onVertoBye = (params: OnVertoByeParams) => { + this.logger.debug('onVertoBye', params) const { rtcPeerId, byeCause = 'NORMAL_CLEARING', @@ -1033,6 +1027,7 @@ export class BaseConnection // Set state to hangup only if the rtcPeer is the current one if (this.activeRTCPeerId === rtcPeer?.uuid) { + this.logger.debug('onVertoBye go hangup') this.setState('hangup') } } @@ -1064,8 +1059,18 @@ export class BaseConnection } private _initPeer() { - const rtcType: RTCSdpType = this.options.remoteSdp ? 'answer' : 'offer' - this.peer = new RTCPeer(this, rtcType) + // Build only for answer to be able to reject + if (this.options.remoteSdp) { + this.peer = this._buildPeer('answer') + } + } + + private _buildPeer(type: RTCSdpType) { + const rtcPeer = new RTCPeer(this, type) + this.appendRTCPeer(rtcPeer) + this.runRTCPeerWorkers(rtcPeer.uuid) + + return rtcPeer } /** @internal */ diff --git a/packages/webrtc/src/RTCPeer.ts b/packages/webrtc/src/RTCPeer.ts index 3c8b473cd..20cfecbf3 100644 --- a/packages/webrtc/src/RTCPeer.ts +++ b/packages/webrtc/src/RTCPeer.ts @@ -453,7 +453,7 @@ export default class RTCPeer { onRemoteBye({ code, message }: { code: string; message: string }) { // It could be a negotiation/signaling error so reject the "startMethod" - this._rejectStartMethod({ + this._rejectStartMethod?.({ code, message, })