Showing posts with label lua. Show all posts
Showing posts with label lua. Show all posts

Thursday, October 12, 2017

FreeSwitch variable length

Googling does not helps, so, made own bicycle.
Quick inliner to get variable length in FreeSwitch.

In $1 assuming our variable.

dest_len=${lua(~stream:write(tostring("$1"):len()))}

Wednesday, August 9, 2017

FusionPBX/FreeSWITCH save CLID on transfer

Idea is when call is received, transfer to next destination should come with callerID was received originally, not updated in moment of transfer. Sometimes it's needed for correct CRM integration or peoples just get used to it, cause it's default with blind transfer.

Actually, same ideas that described here, but for use in FusionPBX.

1. Create context save_transfer with order ~85
condition - <empty>
action - export - nolocal:execute_on_answer_1=lua number_save_on_transfer_store.lua
action - export - api_hangup_hook=lua number_save_on_transfer_db_cleanup.lua

2. Create context restore_transfer with order higher, than save_trasfer, ~80
condition - ${db(exists/number_transfer_store/${sip_from_user})} - ^true$
action - set - restored_number_on_transfer=${db(select/number_transfer_store/${sip_from_user})} - inline
action - set - effective_caller_id_number=${restored_number_on_transfer}
action - set - effective_caller_id_name=${restored_number_on_transfer}
action - db - delete/number_transfer_store/${sip_from_user}
condition - ${db(exists/number_transfer_store/${sip_from_user}_name)} - ^true$
action - set - restored_number_on_transfer_name=${db(select/number_transfer_store/${sip_from_user}_name)} - inline
action - set  - effective_caller_id_name=${restored_number_on_transfer_name}
action - db - delete/number_transfer_store/${sip_from_user}_name

Lua files:
/usr/share/freeswitch/scripts/number_save_on_transfer_store.lua

-- Save number_answered / original caller_id to database

--api = freeswitch.API()

if (session:ready()) then
    answered_extension = session:getVariable("dialed_user")

    caller_id = session:getVariable("restored_number_on_transfer")
    caller_name = session:getVariable("restored_number_on_transfer_name")

    if (caller_id == nil) then
        caller_id = session:getVariable("sip_from_user")
    end
    if (caller_name == nil) then
        caller_name = session:getVariable("sip_from_display")
    end
    if (answered_extension ~= nil and caller_id ~= nil) then
        freeswitch.consoleLog("INFO", "[NUMBER_ON_TRANSFER_SAVE] Got answered call from "..caller_id.." to "..answered_extension.."\n")
        session:execute('db', 'insert/number_transfer_store/'..answered_extension..'/'..caller_id)
        if (caller_name ~= nil) then
            session:execute('db', 'insert/number_transfer_store/'..answered_extension..'_name/'..caller_name)
        end
    end
end

/usr/share/freeswitch/scripts/number_save_on_transfer_db_cleanup.lua

-- Cleanup database

api = freeswitch.API()
sip_to_user = env:getHeader("variable_last_sent_callee_id_number")

if (sip_to_user ~= nil) then
--serialized = env:serialize()
--freeswitch.consoleLog("INFO","[hangup]\n" .. serialized .. "\n")

    freeswitch.consoleLog("INFO", "[DB_CLEANUP] Cleaning " .. sip_to_user .. "\n")
    api:executeString('db delete/number_transfer_store/'..sip_to_user)
    api:executeString('db delete/number_transfer_store/'..sip_to_user..'_name')
end



P.S.: At the end, db is can be easily replaced with hash. As we don't need persistence storage here.

Monday, January 25, 2016

FusionPBX(Freeswitch) HA sync gateways across servers

There was a little task to do.
Assume, we have several FusionPBX in HA (shared database incl. runtime data is on). On "master managing" server we add a gateway to external profile. To add them on other servers we have to go to each server and push rescan on external profile. Eh... To lazy for this.
We will use script, that will subscribe to CUSTOM sofia::gateway_add and gateway_delete event and run sofia profile external rescan over other servers.
We will do this over xmlrpc, so no need to add ssh keys or so.

"Slave" servers:

  • Go to Advanced -> Modules and enable XML RPC module
  • Go to Advanced -> Settings on each "slave" server and put common data for XMLRPC connection, like username, pass and port
  • Restart mod_xml_rpc on each "slave" server
"Master" server
  • Create files /usr/local/freeswitch/scripts/app/gateway_states/resources/gateway_states_add.lua and /usr/local/freeswitch/scripts/app/gateway_states/resources/gateway_states_delete.lua
(I can't get add and delete event work from a single file)
  • gateway_states_add.lua
--description
--monitor custom sofia:gateway_* event and run sofia profile external rescan over other servers
--protect xmlrpc using a firewall on the server to limit access by ip address

--iptables
-- /sbin/iptables -I INPUT -j ACCEPT -p tcp --dport 8080 -s x.x.x.x/32

--define the servers running freeswitch do not include local
servers = {}
x = 0;
servers[x] = {}
servers[x]['username'] = "freeswitch";
servers[x]['password'] = "work";
servers[x]['hostname'] = "10.0.0.2";
servers[x]['port'] = "8080";
x = x + 1;
servers[x] = {}
servers[x]['username'] = "freeswitch";
servers[x]['password'] = "work";
servers[x]['hostname'] = "10.0.0.3";
servers[x]['port'] = "8080";
--x = x + 1;
--servers[x] = {}
--servers[x]['username'] = "ccc";
--servers[x]['password'] = "xxxxx";
--servers[x]['hostname'] = "127.0.0.3";
--servers[x]['port'] = "8080";

--subscribe to the events
--events = freeswitch.EventConsumer("all");
events = freeswitch.EventConsumer("CUSTOM", "sofia::gateway_add");
        -- events = freeswitch.EventConsumer("CUSTOM", "sofia::gateway_delete");
        -- Modify line above to get gateway_states_delete.lua
--prepare the api object
api = freeswitch.API();

--get the events
for event in (function() return events:pop(1) end) do
api_command_argument = "profile%20external%20rescan";
  -- event_gateway = event:getHeader("Gateway");
  -- api_command_argument = "profile%20external%20killgw%20"..event_gateway;
  -- Modify line above to get gateway_states_delete.lua
for key,row in pairs(servers) do
url = [[http://]]..row.username..[[:]]..row.password..[[@]]..row.hostname..[[:]]..row.port..[[/webapi/sofia?]]..api_command_argument;
response = api:execute("curl", url);
freeswitch.consoleLog("INFO", "[notice] ".. url .. " "..response.."\n");
end
end



  • Modify /usr/local/freeswitch/conf/autoload_configs/lua.conf.xml

    <param name="startup-script" value="app/gateway_states/resources/gateway_states_add.lua"/>
    <param name="startup-script" value="app/gateway_states/resources/gateway_states_delete.lua"/>


  • Restart "master" server. At this point, every gateway add or delete will trigger an event, that will go across all our servers and command them pull new config from common database.

This script was modified from memcache.lua, that flushes memcaches over all Fusion servers.