Command-line apps with Clojure and GraalVM: 300x better start-up times

I am a fond Clojure user, and love to use it for both server-side projects and small command-line tools. I love its expressivity and concision, and I like the fact that I can have a small “script” and hack on it. The problem I have is that while this is fine for interactive use (I don’t mind waiting a second to see results) or for server side projects (where initialization happens just once), it is not a sweet spot for a command-line tool that I want to deploy to automate something. Continue Reading...



Learning Clojure: Transducers how-to

Clojure 1.8 introduced transducers to the world. They are quite an interesting idea that has many possible uses; but as they are very flexible and have a scary name, it is sometimes hard to get started with them. Continue Reading...



Play endless random sounds for testing

This Extension will play random sounds from asterisk standard sound set forever. You might have to adjust the path uses. This example works on Debian:

exten => endless,1,Answer()
exten => endless,2,Set(RANDSOUND=${SHELL(ls /var/lib/asterisk/sounds/en | shuf -n 1 | head -n1 | cut -f1 -d"." | tr -d "\n")})
exten => endless,3,NoOp(*${RANDSOUND}*)
exten => endless,4,Playback(${RANDSOUND})
exten => endless,5,Goto(2)
exten => endless,n,Hangup()
Continue Reading...



Compiling Asterisk13 on Centos65 64-bit

This is a quick tutorial to get started with Asterisk 13 (currently beta) on Centos 6.5 64-bit. Luckily the installation procedure is very similar to Asterisk 12 and it is very easy to go through. First we disable selinux and update the system and install binary dependencies - it may take a while. Disable selinux:

sed -i 's/SELINUX=enforcing/SELINUX=disabled/' /etc/selinux/config
reboot
Note that if you copy the commands below that you must either 1) make single commands all on one line, or 2) add back slashes to carry over to a new line (this wiki does not display the back slashes).
yum update
yum install -y screen lsof mlocate wget
yum install -y gcc-c++ make gnutls-devel kernel-devel libxml2-devel ncurses-devel \
  subversion doxygen texinfo curl-devel net-snmp-devel neon-devel \
  uuid-devel libuuid-devel sqlite-devel sqlite \
  git speex-devel gsm-devel
Installing Jansson
wget http://www.digip.org/jansson/releases/jansson-2.5.tar.gz
tar zxvf jansson-2.5.tar.gz
cd jansson-2.5
./configure --libdir=/usr/lib64
make & make install
cd ..
Installing SRTP
wget http://srtp.sourceforge.net/srtp-1.4.2.tgz
tar zxvf srtp-1.4.2.tgz
cd srtp
autoconf
./configure --enable-pic --libdir=/usr/lib64
make && make install
cd ..
Installing PJSIP
git clone https://github.com/asterisk/pjproject pjproject
cd pjproject
./configure --libdir=/usr/lib64 --prefix=/usr --enable-shared \
             --disable-sound --disable-resample --disable-video --disable-opencore-amr \
             --with-external-speex --with-external-srtp --with-external-gsm 
make dep && make && make install
cd ..
Downloading and installing Asterisk 13
wget http://downloads.asterisk.org/pub/telephony/asterisk/releases/asterisk-13.0.0-beta1.tar.gz
tar zxvf asterisk-13.0.0-beta1.tar.gz
cd asterisk-13.0.0-beta1
./configure --libdir=/usr/lib64
make menuselect
Note that as of 2014 November this works with Asterisk 13.0.0 too now that it is out of beta. Just substitute the current URL for the wget and other commands above, for example:
wget http://downloads.asterisk.org/pub/telephony/asterisk/asterisk-13-current.tar.gz
Under Channels you chack that there is “
  • chan_pjsip” make && make install && make samples cd ..
Running Asterisk
asterisk 
asterisk -vvvr
And you get
localhost*CLI> core show version
Asterisk 13.0.0-beta1 built by root @ localhost.localdomain on a x86_64 running Linux on 2014-09-12 08:28:08 UTC
Happy hacking! ..and of course, if you implement call-centers in Asterisk, do not forget to check out QueueMetrics for reporting and WombatDialer for implementing outbound added value services. :) Continue Reading...



Getting started with ARI

Setting up the Asterisk REST Interface on an Asterisk 12 system for an introductory test-drive is quite straightforward. The idea behind ARI is that you have a RESTful part where you send commands and a websocket to receive events. Asterisk configuration Edit /etc/asterisk/http.conf so that:

[general]
enabled=yes
bindaddr=0.0.0.0
bindport=8088
And then create an ARI user in /etc/asterisk/ari.conf:
[general]
enabled = yes

[aritest]
type = user
read_only = no
password = testme
password_format = plain
This creates a new user called aritest with password testme. Now have Asterisk reload and test that the configuration was picked up.
localhost*CLI> reload
...
localhost*CLI> ari show users
r/o?  Username
----  --------
No    aritest
localhost*CLI> ari show status
ARI Status:
Enabled: Yes
Output format: compact
Auth realm: Asterisk REST Interface
Allowed Origins:
User count: 1
Testing ARI - the websocket You can install the wscat tool to test the ARI. It is a part of the EPEL repository that, though not technically a part of CentOS 6, it surely complements it (see https://fedoraproject.org/wiki/EPEL if you do not have it available).
yum install nodejs nodejs-options nodejs-commander
yum install nodejs-ws
Then type:
# wscat --connect 'ws://localhost:8088/ari/events?app=hello&api_key=aritest:testme'
connected (press CTRL+C to quit)
If so far everything is okay, we can now run a test that is a little more meaningful. First edit your /etc/asterisk/extensions.conf and add the following stanza:
[testari]
exten => 1,1,Noop()
same => n,Stasis(hello,world)
same => n,Hangup()
This just creates a new context that sends calls to the Stasis (ARI) app called “hello” with a parameter of “world”. We reload Asterisk so that the dialplan is picked up and in a new window we run again the wscat command above. While wscat is running, go to the Asterisk CLI and type:
localhost*CLI> channel originate Local/1@testari application wait 100
On the websocket window you’ll see:
< {
  "type": "StasisStart",
  "timestamp": "2013-12-30T15:21:45.688+0100",
  "args": [
    "world"
  ],
  "channel": {
    "id": "1388413305.5",
    "name": "Local/1@testari-00000002;2",
    "state": "Ring",
    "caller": {
      "name": "",
      "number": ""
    },
    "connected": {
      "name": "",
      "number": ""
    },
    "accountcode": "",
    "dialplan": {
      "context": "testari",
      "exten": "1",
      "priority": 2
    },
    "creationtime": "2013-12-30T15:21:45.688+0100"
  },
  "application": "hello"
}

< {
  "type": "StasisEnd",
  "timestamp": "2013-12-30T15:22:15.716+0100",
  "channel": {
    "id": "1388413305.5",
    "name": "Local/1@testari-00000002;2",
    "state": "Ring",
    "caller": {
      "name": "",
      "number": ""
    },
    "connected": {
      "name": "",
      "number": ""
    },
    "accountcode": "",
    "dialplan": {
      "context": "testari",
      "exten": "1",
      "priority": 2
    },
    "creationtime": "2013-12-30T15:21:45.688+0100"
  },
  "application": "hello"
}
(Ok I turned on pretty printing in ari.conf in order to make this readable). Testing ARI - the RESTful part Running REST commands through the interface is very straightforward:
[root@localhost ~]# curl -v -u aritest:testme -X GET "http://localhost:8088/ari/asterisk/info"
* About to connect() to localhost port 8088 (#0)
*   Trying 127.0.0.1... connected
* Connected to localhost (127.0.0.1) port 8088 (#0)
* Server auth using Basic with user 'aritest'
> GET /ari/asterisk/info HTTP/1.1
> Authorization: Basic YXJpdGVzdDp0ZXN0bWU=
> User-Agent: curl/7.19.7 (i386-redhat-linux-gnu) libcurl/7.19.7 NSS/3.14.0.0 zlib/1.2.3 libidn/1.18 libssh2/1.4.2
> Host: localhost:8088
> Accept: */*
>
< HTTP/1.1 200 OK
< Server: Asterisk/12.0.0
< Date: Wed, 01 Jan 2014 13:20:15 GMT
< Connection: close
< Cache-Control: no-cache, no-store
< Content-Length: 535
< Content-type: application/json
<
{
  "build": {
    "os": "Linux",
    "kernel": "2.6.32-431.el6.i686",
    "machine": "i686",
    "options": "LOADABLE_MODULES, OPTIONAL_API",
    "date": "2013-12-30 13:25:41 UTC",
    "user": "root"
  },
  "system": {
    "version": "12.0.0",
    "entity_id": "52:54:00:26:9d:07"
  },
  "config": {
    "name": "",
    "default_language": "en",
    "setid": {
      "user": "",
      "group": ""
    }
  },
  "status": {
    "startup_time": "2013-12-30T14:30:39.344+0100",
    "last_reload_time": "2013-12-30T15:21:39.354+0100"
  }
* Closing connection #0
You’ll have to look up each command - so better using a library. See also: Continue Reading...



Compiling Asterisk 12 on CentOS 6.5

Compiling Asterisk 12 (with PJSIP support) on a brand-new CentOS 6 system is pretty straightforward. Most of the packages come prebuilt so it’s not very complex to do. Prerequisites Let’s check the current version.

[root@localhost ~]# cat /etc/redhat-release
CentOS release 6.5 (Final)
[root@localhost ~]# uname -a
Linux localhost.localdomain 2.6.32-431.el6.i686 #1 SMP Fri Nov 22 00:26:36 UTC 2013 i686 i686 i386 GNU/Linux
First we update the system so that we have everything needed to compile plus the packages we need.
yum update
yum install gcc-c++ make gnutls-devel kernel-devel libxml2-devel ncurses-devel subversion doxygen texinfo curl-devel net-snmp-devel neon-devel
yum install uuid-devel libuuid-devel sqlite-devel sqlite git speex-devel gsm-devel
Compiling PJSIP We have everything for PJSIP but the SRTP library.
wget http://srtp.sourceforge.net/srtp-1.4.2.tgz
tar zxvf srtp-1.4.2.tgz
cd srtp
autoconf
./configure
make
make install
cp /usr/local/lib/libsrtp.a /lib
cd ..
Now we are ready for PJSIP itself. Make sure you download the patched version that works with Asterisk.
git clone https://github.com/asterisk/pjproject pjproject
cd pjproject/
./configure --prefix=/usr --enable-shared --disable-sound --disable-resample --disable-video --disable-opencore-amr --with-external-speex --with-external-srtp --with-external-gsm
make dep
make
make install
cd ..
Note: if compiling on a 64-bit CentOS system, remember to add –libdir=/usr/lib64 to have Asterisk find it later (Thanks Jakub!) Compiling Asterisk We start by compiling Jansson - it is available in the CentOS repos, but it’s an old version.
wget http://www.digip.org/jansson/releases/jansson-2.5.tar.gz
tar zxvf jansson-2.5.tar.gz
cd jansson-2.5
./configure --prefix=/
make
make install
cd ..
Note: I had to set –prefix=/usr/ to stop Asterisk borking when detecting the Jansson library. (Centos 6.5 (Final) 64-bit) Now it’s time for Asterisk itself:
wget http://downloads.asterisk.org/pub/telephony/asterisk/asterisk-12-current.tar.gz
cd asterisk-12.0.0/
./configure
make menuselect
Under Channel Drivers check that chan_pjsip is checked (and disable chan_sip is you really feel brave!). If building on a KVM box, better uncheck BUILD_NATIVE under Compiler Flags (press x to save).
make 
make install
make samples
cd ..
If all went well…
[root@localhost asterisk-12.0.0]# asterisk
[root@localhost asterisk-12.0.0]# asterisk -vvvvr
Asterisk 12.0.0, Copyright (C) 1999 - 2013 Digium, Inc. and others.
Created by Mark Spencer <markster@digium.com>
Asterisk comes with ABSOLUTELY NO WARRANTY; type 'core show warranty' for details.
This is free software, with components licensed under the GNU General Public
License version 2 and other licenses; you are welcome to redistribute it under
certain conditions. Type 'core show license' for details.
=========================================================================
Connected to Asterisk 12.0.0 currently running on localhost (pid = 18101)
See also Continue Reading...



WombatDialer

WombatDialer is a next-generation dialer platform for the Asteriskâ„¢ PBX. It is meant as a way to implement a number of functions that are not easily handled in an Asterisk-based call center, like: Continue Reading...



Compiling Asterisk 1.8 on CentOS 5.5 64-bit

After the first official release of Asterisk 1.8, I decided to test how it is and compiled it on a clean-slate 64-bit CentOS system. The experience went very smoothly and the configure script was able to pick up all the packages needed to activate various interesting extensions (it was not always so with previous releases). Continue Reading...