Phone number validation, sanitization and formatting for FreeSWITCH

mod_phonenumber

Exposes libphonenumber library to FreeSWITCH

Build Status Version License

Introduction

Built on top of Google’s libphonenumber, mod_phonenumber exposes a number of validation, sanitization and formatting functions to FreeSWITCH. The module can be used in three modes: as a dialplan application, through the API interface or whenever a new channel is created through hooks; regardless of the usage method, there are three common concepts:

  • actions: one or more libphonenumber functions exposed by the module;
  • phone number: the input the actions will be executed against;
  • parameters: one or more arguments controlling the actions’ behaviour;

In some cases, the parameter values are constant in most circumstances, therefore they can be omitted once the desired values are set as default ones in the module’s configuration.

Installation

As with FreeSWITCH, Debian is reference platform for mod_phonenumber:

curl -sL \
  https://rtckit.io/mod_phonenumber/freeswitch-mod-phonenumber_`curl -s https://rtckit.io/mod_phonenumber/release.txt`_`dpkg --print-architecture`.deb \
  -o freeswitch-mod-phonenumber.deb
sudo dpkg -i freeswitch-mod-phonenumber.deb

Ensure the module is added to your modules.conf.xml file:

<configuration name="modules.conf" description="Modules">
  <modules>
    <!-- ... your modules ... -->
    <load module="mod_phonenumber"/>
  <modules>
</configuration>

Or, load it manually:

freeswitch@test> load mod_phonenumber
[CONSOLE] switch_loadable_module.c:1804 Successfully Loaded [mod_phonenumber]
[NOTICE] switch_loadable_module.c:350 Adding Application 'phonenumber'
[NOTICE] switch_loadable_module.c:412 Adding API Function 'phonenumber'

+OK Reloading XML
+OK

Getting started

For a brief introductory example, let’s look at the get_region_code action; given a phone number as it’s input, it will return a two character region code corresponding to its jurisdiction. For example, in the case of +16172531000 the return value is US. Let’s consider the latter being the preferred region for our use case, therefore we would configure it as the default value in our phonenumber.conf.xml file:

<configuration name="phonenumber.conf" description="mod_phonenumber">
  <settings>
    <param name="default_region" value="US"/>
    <!-- ... other settings ... -->
  </settings>
</configuration>

For the dialplan application use case, let’s assume we are expecting an inbound call from this number on the 1234 extension with the dialplan section similar to the one below:

<extension name="test">
  <condition field="destination_number" expression="^1234$">
    <action application="phonenumber" data="get_region_code caller"/>
    <action application="answer"/>
    <!-- ... other actions ... -->
  </condition>
</extension>

When the inbound call from +16172531000 is handled by the dialplan, the phonenumber application will set a phonenumber_caller_region_code channel variable with the value set to US. The variable can be further used for routing or informational purposes. When used in dialplan application mode, all actions will set a specific channel variable containing the result. Should we want to assume a different default region for this specific use case, say GB, the data attribute would be defined as data="get_region_code caller default_region=GB".

For the API interface use case, we need to explicitly pass the phone number (as opposed to using placeholders); consider running the following command in the FreeSWITCH console:

freeswitch@test> phonenumber get_region_code +16172531000

US

Since the default region is set to US, the same result would be returned if the input was passed in national format as 6172531000 or even '(617) 253-1000'. That would not be the case for a foreign number in national format, say:

freeswitch@test> phonenumber get_region_code 02076792000

ZZ

ZZ is libphonenumber’s return value for numbers which cannot be resolved to a region. Should we have overridden the default region, we would have received the correct result:

freeswitch@test> phonenumber get_region_code 02076792000 default_region=GB

GB

Lastly, for the hook use case, let’s assume we are expecting inbound calls in the default FreeSWITCH context and we want to get the region code of the calling number; our configuration file would look similar to:

<configuration name="phonenumber.conf" description="mod_phonenumber">
  <settings>
    <param name="default_region" value="US"/>
  </settings>
  <hooks>
    <hook>
      <param name="direction" value="inbound"/>
      <param name="context" value="default"/>
      <param name="scope" value="caller"/>
      <param name="actions" value="get_region_code"/>
      <!-- One could override the default region only for this hook, e.g.: -->
      <!-- <param name="default_region" value="GB"/> -->
    </hook>
  </hooks>
</configuration>

Whenever a new inbound channel is created in the default FreeSWITCH context, get_region_code will be executed against caller’s number and the result will be stored in the phonenumber_caller_region_code channel variable. Should we need to override any of the default parameters for a hook, they can be passed as XML parameters in the hook’s scope (see above commented XML code).

What’s next

Familiarize yourself with the configuration and the action parameters then look at some practical examples. The usage modes and the available actions are also described in detail, just follow the items in the website’s navigation.