Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

JsSIP 3.7.1 doesn't allow sending DTMF during EarlyMedia #689

Open
divisumma18 opened this issue Feb 26, 2021 · 9 comments
Open

JsSIP 3.7.1 doesn't allow sending DTMF during EarlyMedia #689

divisumma18 opened this issue Feb 26, 2021 · 9 comments
Labels

Comments

@divisumma18
Copy link

JsSIP 3.7.1 seems to have the same issue described here:
https://twinklephone.yahoogroups.narkive.com/aXB3Vk5Q/twinkle-doesn-t-allow-sending-dtmf-during-earlymedia

TLDR: Sending a DTMF tone with JsSIP.RTCSession.sendDTMF() after a "183 Session Progress" and before a "SIP/2.0 200 OK" should be possibile, but JsSIP raises an "INVALID_STATE_ERROR: Invalid status: 2" error instead.

@jmillan
Copy link
Member

jmillan commented Feb 26, 2021

Wow, your pointing a 13 year old forum content.

Can you try this patch:

diff --git a/lib/RTCSession.js b/lib/RTCSession.js
index 7003c25..dcb41c3 100644
--- a/lib/RTCSession.js
+++ b/lib/RTCSession.js
@@ -962,7 +962,11 @@ module.exports = class RTCSession extends EventEmitter
     }

     // Check Session Status.
-    if (this._status !== C.STATUS_CONFIRMED && this._status !== C.STATUS_WAITING_FOR_ACK)
+    if (
+      this._status !== C.STATUS_CONFIRMED &&
+      this._status !== C.STATUS_WAITING_FOR_ACK &&
+      this._status !== C.STATUS_1XX_RECEIVED
+    )
     {
       throw new Exceptions.InvalidStateError(this._status);
     }

Please also try what would happen if you call sendDtmfs() after receiving a 100 but before receiving 18X.

@divisumma18
Copy link
Author

Wow, your pointing a 13 year old forum content.

I thought an old post from Iñaki would still be pretty convincing! 😉

Can you try this patch:

I tried that and similarly patched DTMF.js

diff --git a/lib/RTCSession/DTMF.js b/lib/RTCSession/DTMF.js
index d27b4ac..5665c40 100644
--- a/lib/RTCSession/DTMF.js
+++ b/lib/RTCSession/DTMF.js
@@ -48,9 +48,9 @@ module.exports = class DTMF extends EventEmitter
     this._direction = 'outgoing';
 
     // Check RTCSession Status.
-    if (this._session.status !== this._session.C.STATUS_CONFIRMED &&
-      this._session.status !== this._session.C.STATUS_WAITING_FOR_ACK)
-    {
+    if (
+      this._session.status !== this._session.C.STATUS_CONFIRMED && 
+      this._session.status !== this._session.C.STATUS_WAITING_FOR_ACK &&
+      this._session.status !== this._session.C.STATUS_1XX_RECEIVED
+      ) {
       throw new Exceptions.InvalidStateError(this._session.status);
     }

but apparently there's still something wrong:

jssip-senddtmf-err

@jmillan
Copy link
Member

jmillan commented Feb 26, 2021

but apparently there's still something wrong:

You don't specify whether you were trying to send the DTMF after receiving 100 or 1XX. I'm certain it won't work before 1XX, not 100% sure if it would after 1XX.

@divisumma18
Copy link
Author

Sorry, you're right, but the error looks exactly the same to me, in both conditions.

This is the console log of a sendDTMF() call just after a SIP 100 Trying:

JsSIP:Transport received text message:
SIP/2.0 100 Trying
Via: SIP/2.0/WSS iifbbidgggba.invalid;branch=z9hG4bK3721326;received=109.106.30.130;rport=39900
From: ...
To: ...
Call-ID: ad7iof3u1dvpk3gfd4ok
CSeq: 2470 INVITE
User-Agent: FreeSWITCH-mod_sofia/1.6.20+git~20180123T214909Z~987c9b9a2a~64bit
Content-Length: 0

 +45ms
JsSIP:RTCSession receiveInviteResponse() +57ms
JsSIP:RTCSession sendDTMF() | tones: 1 +174ms
JsSIP:RTCSession newDTMF() +3ms
JsSIP:RTCSession sendRequest() +1ms
RTCSession.js:1266 Uncaught (in promise) TypeError: Cannot read property 'sendRequest' of null
    at n.value (RTCSession.js:1266)
    at n.value (DTMF.js:116)
    at n.s (RTCSession.js:955)
    at n.value (RTCSession.js:929)
    ...

And this is the log just after a 183 Session progress:

JsSIP:Transport received text message:
SIP/2.0 183 Session Progress
Via: SIP/2.0/WSS dajefeiaclea.invalid;branch=z9hG4bK4945751;received=109.106.30.130;rport=11172
From: ...
To: ...
Call-ID: v6d4ftm2jjooa7dda7g9
CSeq: 4340 INVITE

[...]

JsSIP:RTCSession receiveInviteResponse() +805ms
JsSIP:Dialog new UAC dialog created with status EARLY +0ms
JsSIP:RTCSession emit "sdp" +2ms
JsSIP:RTCSession session progress +5ms
JsSIP:RTCSession emit "progress" +0ms
JsSIP:RTCSession sendDTMF() | tones: 1 +6ms
JsSIP:RTCSession newDTMF() +1ms
JsSIP:RTCSession sendRequest() +1ms
RTCSession.js:1266 Uncaught (in promise) TypeError: Cannot read property 'sendRequest' of null
    at n.value (RTCSession.js:1266)
    at n.value (DTMF.js:116)
    at n.s (RTCSession.js:955)
    at n.value (RTCSession.js:929)

@mattdimeo
Copy link
Contributor

Just a note that this also exists in 3.9.1, and also in sendInfo. A similar patch also doesn't fix that one; _dialog is null when it goes to do the actual send.

@ibc
Copy link
Member

ibc commented Jun 23, 2022

Does the 183 response has a Contact header?

@ibc
Copy link
Member

ibc commented Jun 23, 2022

The 183 in an above comment doesn't have any Contact header so indeed there is no early dialog established yet and hence JsSIP cannot send in-dialog requests to the remote (because there is no remote URI yet).

@mattdimeo
Copy link
Contributor

mattdimeo commented Jun 23, 2022

In my case, it looks like this before I try to send dtmf:

JsSIP:Transport received text message:

SIP/2.0 183 Session Progress
Via: SIP/2.0/WSS fe9k20u30hek.invalid;rport=52114;received=127.0.0.1;branch=z9hG4bK9015859
Call-ID: ai63m0pjh4i7midd413e
From: sip:[email protected];tag=dp1k5cp7tp
To: sip:[email protected];tag=37495e77-f108-466d-af9a-d7b68f608615
CSeq: 2145 INVITE
Server: FPBX-15.0.23.12(16.17.0)
Contact: sip:127.0.0.1:8088;transport=ws
Allow: OPTIONS, INVITE, ACK, BYE, CANCEL, UPDATE, PRACK, REGISTER, SUBSCRIBE, NOTIFY, PUBLISH, MESSAGE, REFER
Content-Type: application/sdp
Content-Length: 905

So in my case, yes, there's a contact header.

@Kumargaurav11998
Copy link

Kumargaurav11998 commented Dec 22, 2023

Wow, your pointing a 13 year old forum content.

Can you try this patch:

diff --git a/lib/RTCSession.js b/lib/RTCSession.js
index 7003c25..dcb41c3 100644
--- a/lib/RTCSession.js
+++ b/lib/RTCSession.js
@@ -962,7 +962,11 @@ module.exports = class RTCSession extends EventEmitter
     }

     // Check Session Status.
-    if (this._status !== C.STATUS_CONFIRMED && this._status !== C.STATUS_WAITING_FOR_ACK)
+    if (
+      this._status !== C.STATUS_CONFIRMED &&
+      this._status !== C.STATUS_WAITING_FOR_ACK &&
+      this._status !== C.STATUS_1XX_RECEIVED
+    )
     {
       throw new Exceptions.InvalidStateError(this._status);
     }

Please also try what would happen if you call sendDtmfs() after receiving a 100 but before receiving 18X.

this need to change to sip server of frontend developer ?

I tried this but did not work .
Here is how I send DTMF

async DTMFCall(tone) {
try {
var options = {
'duration': 160,
'interToneGap': 500,
'transportType': 'INFO'

  };
  if (this.currentCallSession) {
    this.currentCallSession.sendDTMF(tone,options);

    console.log('DMTF call: ');
  }
} catch (err) {
  console.error('DMTF call: error ', err);
}

}

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Development

No branches or pull requests

5 participants