InnovateAsterisk / Browser-Phone

A fully featured browser based WebRTC SIP phone for Asterisk
https://www.innovateasterisk.com
GNU Affero General Public License v3.0
488 stars 240 forks source link

Anonymous call #121

Open vieridipaola opened 3 years ago

vieridipaola commented 3 years ago

Hi,

It seldom happens, but once in a while a user reports receiving a call from "anonymous - Anonymous". No one seems to be on the other end. Anyway, that's how the contact is ID'ed in Browser-Phone's buddy list. I tried to trace the call in the Asterisk server, but couldn't find it. I can only see the aftermath of trying to subscribe to it: res_pjsip_pubsub.c: Subscription 'web7024->anonymous' is not to a list where web7024 is the Browser-Phone extension that received the anonymous call.

I don't know if this is an Asterisk issue I should keep searching in its logs, or if it's a Browser-Phone artifact with buddy lists.

Any clues?

InnovateAsterisk commented 3 years ago

You will have to check the SIP trace, there would have to be an INVITE inbound to the browser phone for it to setup a call. You can either check the Asterisk box by leaving some kind of wireshark trace running, or you can use the developer tools and inspect the /ws web socket message history. (Or both)

vieridipaola commented 3 years ago

The extension I mention above (web7024) is webrtc, so listening on 5060 with tcpdump or wireshark won't do. I'd probably have to listen on https port 8090 in my case, but that's encrypted. So I guess the only way is to ask Asterisk to produce the SIP trace for me. Well, more precisely I think I'd need to ask pjsip to do so. Maybe the easiest way would be to use

pjsip set history on
pjsip show history

However, I've read that leaving history on for a long time can use up all the RAM. The problem is that these "anonymous" calls seem to show up once every few months. Looking them up in the history may be tedious. Maybe the best approach would be to ask pjsip to log to an external pcap file with something like:

pjsip set logger pcap /tmp/SIP_trace.pcap
pjsip set logger on

However, this also produces a lot of output in the console and in "full". I'll have to take that into consideration.

Incidentally, there's no trace of "anonymous" in Master.csv. Shouldn't there be if an INVITE was received or is that alone not enough to create a CDR?

Thanks

InnovateAsterisk commented 3 years ago

Phew... once every few months... that's going to be tricky! You definitely want only the SIP trace, so pjsip set logger pcap /tmp/SIP_trace.pcap may be your best approach and maybe run a cron job to keep the file to a manageable size.

The INVITE would have to have come from your Asterisk box, as it's not possible for connections to establish between any other resource and the browser. So another approach would be to apply SIP trace logging in the Web Application. Something similar to the remote error logging.

Another point: if you are saving SIPCALLID in your CSV/CDR(and i can highly recommend that you do), the CDR's of the browser phone are saving the SIPCALLID. The SIPCALLID can create a 1:1 link between client logs and your server SIP logs.

image

vieridipaola commented 3 years ago

Interesting... Would it be possible to add yet another configurable item for traceSIP?

The following code in phone.js enables SIP tracing in the console (I don't know what the traceSip option does in transportOptions, but I know that traceSIP: true in SIP.UA does enable SIP tracing -- that would be the last occurrence of traceSIP in the code below):

function CreateUserAgent() {
    try {
        console.log("Creating User Agent...");
        userAgent = new SIP.UA({
            displayName: profileName,
            uri: SipUsername + "@" + wssServer,
            transportOptions: {
                wsServers: "wss://" + wssServer + ":"+ WebSocketPort +""+ ServerPath,
                traceSip: false,
                connectionTimeout: TransportConnectionTimeout,
                maxReconnectionAttempts: TransportReconnectionAttempts,
                reconnectionTimeout: TransportReconnectionTimeout,
            },
            sessionDescriptionHandlerFactoryOptions:{
                peerConnectionOptions :{
                    alwaysAcquireMediaFirst: true, // Better for firefox, but seems to have no effect on others
                    iceCheckingTimeout: IceStunCheckTimeout,
                    rtcConfiguration: {
                        iceServers : [
                            { urls: IceStunServerProtocol + ":"+ IceStunServerAddress +":"+ IceStunServerPort }
                        ]
                    }
                }
            },
            authorizationUser: SipUsername,
            password: SipPassword,
            registerExpires: RegisterExpires,
            hackWssInTransport: WssInTransport,
            hackIpInContact: IpInContact,
            userAgentString: userAgentStr,
            autostart: false,
            register: false,
            traceSip: true,
        });
        console.log("Creating User Agent... Done");

So it would be something like:

traceSip: enableSIPtrace,

where enableSIPtrace is a boolean I could set in a custom "pre" js script.

It's heavy logging though.... I'm afraid it can drastically slow down client performance especially if I enable remote logging of the console. I'll have to test that first.

Thanks for the SIPCALLID tip. I'm afraid I'm not logging it. It should be in Master.csv, right? And I should enable it in cdr.conf? Or maybe I should manually set it in the dialplan.

I tried the following in my extensions files, before a DIAL() command:

same => n,Set(CDR(userfield)=SIPCALLID:${SIPCALLID})

Now, in Master.csv I can see the userfield with "SIPCALLID:", ie. the ${SIPCALLID} variable is empty.

[EDIT] I also tried this: same => n,Set(CDR(userfield)=SIPCALLID:${CHANNEL(pjsip,call-id)}) but still empty variable.

[EDIT 2] I finally traced the anonymous calls even without the SIP call-ID. THey seem to be coming from ISDN lines I have connected to another Asterisk box which is IAX2-trunked to the Asterisk server where Browser-Phone is connecting to. These calls come in without caller ID (no name, no number). I'm supposing sipjs manipulates the caller ID to add "Anonymous" (ie. external/lib/SipJS/sip-0.11.6.js: options.params.from_displayName = 'Anonymous'; when the name or number are empty strings. It would still be nice to know how to set SIPCALLID in Asterisk (PJSIP) and to be able to customize traceSIP in phone.js. ;-)

[EDIT 3] OK, so this actually works: same => n,Set(CDR(userfield)=SIPCALLID:${CHANNEL(pjsip,call-id)}) but I was actually putting a space between pjsip, and call-id.... No space there! So now I'm getting somethign like: "SIPCALLID:f6t6u1g00lef5hm26mqs" in Master.csv. It almost matches the caller-ID in Browser-Phone... almost because it's truncated. Maybe "userfield" is not the best place for this value unless I remove the "SIPCALLID:" string in front? Where would you store ${CHANNEL(pjsip,call-id)}?

InnovateAsterisk commented 3 years ago

It's possible that SIPCALLID was an old chan_sip variable... sorry, i didn't actually use it recently, it was only from what I recall.

Glad you managed to solve your issue. The SIPCALLID i found to be useful when endusers need to trace down a call, but cant give exact details, or are being vague about the details. Asking them to provide the actual SIPCALLID gives a point-point result.

I have only ever used CDR logging to a database. I realise the CSV is easier in the short run, but found the post processing to be must stronger on a MySQL/Miria database.

With MySQL you should use a custom field, and the field length is defined by the column details.

Otherwise, the csv also has a custom field, defined in cdr_custom.conf... not sure if there is a limit when using the custom field, but it would probably default to something like 255, and that should be enough.