FreeSWITCH: dial through VoIP provider

January 16th, 2014

Register against megavoip.com sbc:
Add a file sip.megavoip.com.xml to /usr/local/freeswitch/conf/sip_profiles/external/ to dial through Megavoip.com:

fs-megavoip

Register against multifon.ru sbc:
Add a file multifon.xml to /usr/local/freeswitch/conf/sip_profiles/external/ to dial through multifon.ru:

fs-multifon

Now it’s time to check if the REGISTER is OK.
Execute in the FS CLI:

freeswitch@internal> sofia status
Name Type Data State
=================================================================================================
external profile sip:mod_sofia@10.145.13.21:5080 RUNNING (0)
external::example.com gateway sip:joeuser@example.com NOREG
external::sip.megavoip.com gateway sip:megavoip_username@sip.megavoip.com REGED
external::multifon gateway sip:79221234567@sbc.multifon.ru REGED
10.145.13.21 alias internal ALIASED
internal profile sip:mod_sofia@10.145.13.21:5060 RUNNING (0)
internal-ipv6 profile sip:mod_sofia@[::1]:5060 RUNNING (0)
=================================================================================================
3 profiles 1 alias

or:
freeswitch@internal> sofia status gateway
Profile::Gateway-Name Data State IB Calls(F/T) OB Calls(F/T)
=================================================================================================
external::example.com sip:joeuser@example.com NOREG 0/0 0/0
external::sip.megavoip.com sip:megavoip_username@sip.megavoip.com REGED 0/0 0/0
external::multifon sip:79221234567@sbc.multifon.ru REGED 0/1 0/0
=================================================================================================
3 gateways: Inbound(Failed/Total): 0/1,Outbound(Failed/Total):0/0

or with more info:
freeswitch@internal> sofia status gateway sip.megavoip.com
...

Dial through (let’s dial via megavoip.com):

Add to /usr/local/freeswitch/conf/dialplan/default.xml to the beginning of ‘default’ context:

fs-dial-through

FreeSWITCH and Asterisk: equivalent commands

January 16th, 2014

fs_cli -l 5 = console loglevel 5

sofia global siptrace on|off = calls debug

console loglevel help
console loglevel [0-7] = core set verbose X

sofia profile default start

sofia status profile internal
sofia status profile internal reg = sip show peers. Show devices, registered against your FreeSWITCH
list_users = sip show peers. Show devices, registered against your FreeSWITCH

sofia profile internal rescan = sip reload (not sure! Command below is BETTER!)
sofia profile external restart reloadxml = equivalent of ‘sip reload’. Execute after editing /usr/local/freeswitch/conf/sip_profiles/external (or internal)

F6 = dialplan reload
reloadxml

xml_locate dialplan = dialplan show

reload mod_sofia

http://wiki.freeswitch.org/wiki/Rosetta_stone

FreeSWITCH unexpected behavior

January 4th, 2014

FreeSWITCH is a new telephony engine for me, so I’m just learning it when I have free time.
Today I discovered a 'system' command in FS CLI and for the sake of curiosity typed 'system ping 8.8.8.8'. Nothing changed in the CLI.
Some time later I started to learn how to reload the SIP stack of FreeSWITCH ('reload mod_sofia'). And each time I saw an error:

...
2014-01-04 09:02:57.468709 [ERR] sofia.c:1501 Error Creating SIP UA for profile: internal
2014-01-04 09:02:57.468709 [ERR] sofia.c:1501 Error Creating SIP UA for profile: internal-ipv6
2014-01-04 09:02:57.468709 [ERR] sofia.c:1501 Error Creating SIP UA for profile: external
...

All of SIP-profiles failed when restarting them.

I started searching – who is listening on port 5060. That’s what I’ve discovered:
root@server:/opt/freeswitch/bin# netstat -tulpan | grep 5060
tcp 0 0 10.15.9.10:5060 0.0.0.0:* LISTEN 6887/ping
udp 124576 0 10.15.9.10:5060 0.0.0.0:* 6887/ping

My ping, that 'system' application. I killed it and restarted FreeSWITCH. After that everything works fine.

Cell phone as a queue member

December 19th, 2013

From time to time I’m asked by my customers if it is possible to include a cellular phone as a queue member. Yes, it is easy to do. You may include any phone number, not only cell or SIP, which is registered on your Asterisk server. Asterisk must be compiled with the local channel support. Everything is done with its help.

queues.conf:

[queue_cell_and_sip]
strategy = ringall
servicelevel = 10
joinempty = yes
music = default

member => SIP/1301
member => Local/79221234567@your-context

extensions.ael:

...
        1810 =>
        {
                Answer;
                Queue(queue_cell_and_sip);
                Hangup;
        }
...

PostgreSQL notes

October 31st, 2013

1. Edit postgresql.conf line listen_addresses = '10.14.1.21' to your appropriate value.
2. Add to pg_hba.conf a line, which will allow connection to the database from certain IP address/subnet: host johnsdb john 10.14.1.201/32 md5
3. service postgresql reload
4. As root, ‘su - postgres‘ , then ‘psql‘ , then:

4.1. postgres=# CREATE USER john WITH ENCRYPTED PASSWORD 'johnstailislong' ;
4.2. postgres=# CREATE DATABASE johnsdb WITH OWNER john ;
( If the database owner is wrong, change it: postgres=# ALTER DATABASE johnsdb OWNER TO john ; )
5. Then connect from outside to the already created database and create a table inside it:
psql -d johnsdb -U john -h 10.14.1.21
johnsdb=> CREATE TABLE johnstable (type varchar(6),name varchar(128),secret varchar(128),context varchar(128),host varchar(128)) WITH (OIDS=FALSE);

Hints:

Change DB’s owner (as postgresql user):
ALTER DATABASE johnsdb OWNER TO john ;

Change table’s owner (as postgresql user):
ALTER TABLE johnstable OWNER TO john ;

Table permissions: (as postgresql user):
GRANT ALL ON TABLE johnstable TO john ;

Change default values in a column:
ALTER TABLE tablename ALTER COLUMN columnname SET DEFAULT 'green,red' ;

Rename a column:
ALTER TABLE tablename RENAME COLUMN oldcolname TO newcolname;

Change column type:
ALTER TABLE tablename ALTER COLUMN columnname TYPE varchar(30);

Get last N rows:
SELECT * FROM mytable ORDER BY record_date DESC LIMIT 5;

Get first N rows:
SELECT * FROM mytable ORDER BY record_date ASC LIMIT 5;

Select between X and Y values:
SELECT name,callerid FROM sip_conf WHERE name BETWEEN '1301' and '1310' ORDER BY name;

Show databases:

astertest=> \list
                                  List of databases
   Name    |   Owner   | Encoding |   Collate   |    Ctype    |   Access privileges   
-----------+-----------+----------+-------------+-------------+-----------------------
 astertest | astertest | UTF8     | ru_RU.UTF-8 | ru_RU.UTF-8 | 
 postgres  | postgres  | UTF8     | ru_RU.UTF-8 | ru_RU.UTF-8 | 
 template0 | postgres  | UTF8     | ru_RU.UTF-8 | ru_RU.UTF-8 | =c/postgres          +
           |           |          |             |             | postgres=CTc/postgres
 template1 | postgres  | UTF8     | ru_RU.UTF-8 | ru_RU.UTF-8 | =c/postgres          +
           |           |          |             |             | postgres=CTc/postgres
(4 rows)

Show tables in the current database:

astertest=> \d
                   List of relations
 Schema |          Name          |   Type   |   Owner   
--------+------------------------+----------+-----------
 public | sip_conf_office        | table    | astertest
 public | sip_conf_office_id_seq | sequence | astertest
(2 rows)

Show table structure:

astertest=> \d sip_conf_office
                                     Table "public.sip_conf_office"
     Column     |          Type          |                          Modifiers                           
----------------+------------------------+--------------------------------------------------------------
 id             | integer                | not null default nextval('sip_conf_office_id_seq'::regclass)
 name           | character varying(80)  | not null default ''::character varying
 accountcode    | character varying(20)  | 
 amaflags       | character varying(7)   | 
 callgroup      | character varying(10)  | 
 callerid       | character varying(80)  | 
 canreinvite    | character varying(3)   | default 'no'::character varying
 context        | character varying(80)  | 
 defaultip      | character varying(15)  | 
 dtmfmode       | character varying(7)   | 
 fromuser       | character varying(80)  | 
 fromdomain     | character varying(80)  | 
 host           | character varying(31)  | not null default ''::character varying
 insecure       | character varying(4)   | 
 language       | character varying(2)   | 
 mailbox        | character varying(50)  | 
 md5secret      | character varying(80)  | 
 nat            | character varying(5)   | not null default 'no'::character varying
...

To insert many lines in SQL-syntax from txt file:

psql -U asterisk -h localhost -d asterisk -f /root/peers.txt

… assuming that peers.txt looks like:

INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('0001','Operator 0001 <0001>','0001','operators','5060');
INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('0001d','Operator 0001 <0001>','0001d','operators','5061');
INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('0002','Operator 0002 <0002>','0002','operators','5060');
INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('0002d','Operator 0002 <0002>','0002d','operators','5061');
...
INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('9999','Operator 9999 <9999>','9999','operators','5060');
INSERT INTO sip_conf_new (name,callerid,defaultuser,context,port) VALUES ('9999d','Operator 9999 <9999>','9999d','operators','5061');

Answer please

October 31st, 2013

Those who visit my blog from north, get in touch please, I’m just interested who are you and from where have you known of this inconspicuous weblog. :)
I’m available at kurgan-rus a t inbox ddot ru and/or at http://zantsev.com/.
sever

Asterisk AMI

October 28th, 2013

Let your first-line support do ‘sip reload’ neither with knowing Asterisk, nor with a priveleged account in the system.
Set up manager.conf:

[general]
enabled = yes
webenabled = no

port = 5038
bindaddr = 10.190.52.14

[support]
secret = supportpass
deny=0.0.0.0/0.0.0.0
permit=10.190.52.0/255.255.255.0
permit=10.190.51.4/255.255.255.255

displayconnects = yes
read = system,command
write = system,command

Create a php page on some host with Apache and PHP configured:

';
}
fclose($socket);
}
?>

Asterisk run user

September 27th, 2013

When installing Asterisk from source, you need to create an unprivileged user manually.
Add to /etc/group something like:
asterisk:x:110:
and to /etc/passwd:
asterisk:x:107:110:Asterisk PBX daemon,,,:/var/lib/asterisk:/bin/false
Just set unused GID and UID.

Then change permissions:
chown -R asterisk:asterisk /var/lib/asterisk/
chown -R asterisk:asterisk /var/spool/asterisk/
chown -R asterisk:asterisk /var/log/asterisk/
chown -R asterisk:asterisk /var/run/asterisk/

And finally, set the running user in asterisk.conf.

It is not mentioned in the Book, but I think chown‘ing /etc/asterisk/ with the -R option is also worth doing; changing config files (not directories, if exist) permissions in /etc/asterisk to 640 either.

Putting a plenty of numbers to the blacklist

September 16th, 2013

for i in (list_numbers); do
asterisk -rx "database put blacklist $i 1"
done

Where ‘list_numbers’ is your file with numbers.
Tnanks to zzuz.

How to define an Asterisk module by function name

September 16th, 2013

Asterisk has a nice function PITCH_SHIFT, which can modify caller’s/callee’s voice. Let’s imagine, we have a system without autoloaded modules, and we need to find which module provides this function.

1. Go to the astmoddir (I have a Debian system):

cd /usr/lib/asterisk/modules

2. Find.

root@voiprouter1:/usr/lib/asterisk/modules# grep PITCH *
Binary file func_pitchshift.so matches
root@voiprouter1:/usr/lib/asterisk/modules#

3. We can also find the dependencies:

root@voiprouter1:/usr/lib/asterisk/modules# ldd func_pitchshift.so
linux-gate.so.1 => (0xb776e000)
libpthread.so.0 => /lib/i386-linux-gnu/i686/cmov/libpthread.so.0 (0xb7747000)
libc.so.6 => /lib/i386-linux-gnu/i686/cmov/libc.so.6 (0xb75e4000)
/lib/ld-linux.so.2 (0xb776f000)

4. That’s it! Thanks to meral.