12.12.2019

callback+freepbx+AMD

Схема работы такая:

Любой разрешенный ip звонит на DID номер pbx, станция перезванивает с DID номера и соединяет с внутренним абонентом) показывая в качестве callerid номер на который осуществляется дозвон.

Особенности: минимум вмешательства в код freepbx чтобы можно было использовать весь функционал станции.

У вас уже установлена: Freepbx, callback модуль, правильно настроены callback и trunk в интерфейсе freepbx

Всё что нам нужно это добавить передачу переменной в callback модуль:

//define the args for Originate
$channel = "Local/".$callback_number."@from-internal";
$exten = $callback_exten;
$context = $callback_context;
$priority = $callback_priority;
$timeout = $callback_timeout;
$callerid = $callback_callerid;
$variable = "__MYVAR4=$callback_number";
$account = "";
$application = "";
$data = "";

затем поймать её в extension_custom.conf

[macro-dialout-one-predial-hook]
exten => s,1,set(CALLERID(all)=${MYVAR4})

[macro-AMD1]
exten => s,1,noop("Check of answering machine")
exten => s,n,background(silence/1)
exten => s,n,AMD()
exten => s,n,NoOp("AMD STATUS IS :"${AMDSTATUS}"…CAUSE:"${AMDCAUSE})
exten => s,n,Set(CDR(userfield)=${AMDSTATUS}|${AMDCAUSE})
exten => s,n,GotoIf($[${AMDSTATUS}=HUMAN]?human:mach)
exten => s,n(mach),Hangup()
exten => s,n(human),noop(This is Human continue)

How to use callback calls at freepbx

  1. Create callback application in menu. It will make you possible to send calls from callback to any registered extension \ Ring groups \ Queues \ IVR or something else.  In CallerID field you should set “${FROM_DID}” to send calls from your DID number. 
  1. Create Trunk for making outbound calls with AMD it may be any trunk but you should add “TM(AMD1)” in Dial options.
  2. Create inbound route for receive call from any IP and to specific DID number: you have example here in interface with number 55555. Choose destination as callback application created at step 1. 
  3. Create outbound route for route calls making by your freepbx (not only from callback app). You should set Dial Patterns to avoid making call to destinations that you don’t want to call. 
  4. Apply changes. That is all you need in web interface. 

21.11.2019

Freepbx using any CAllerID display name as callerID(num) when making external calls

В рамках freepbx вы не можете установить callerid name (display) как вы хотите, вы всегда будете видеть тот display name который установили при создании Extension.

Чтобы исправить эту несправедливость, добавляем в extension_custom.conf

[macro-dialout-trunk-predial-hook]
exten => s,1,Noop(Number translation)
exten => s,n,Set(MYFROM=${PJSIP_HEADER(read,From)})
exten => s,n,set(MYFROM=${CUT(MYFROM, ,1)})
exten => s,n,set(MYFROM=${REPLACE(MYFROM,\")})
exten => s,n,Noop(HEADER - ${MYFROM})
exten => s,n,Set(CALLERID(number)=${MYFROM})

после этого при исходящих звонках через транки, вы будете видеть тот АОН который вы выставить в CAller ID name в своем софтфоне.

2.05.2019

custom script AGI freepbx per each call

to do any custom dialplan per call (inbound from trunk to extensions) use

macro-dialout-one-predial-hook

to do any custom macro action for outgoing from trunk use:

macro-dialout-trunk-predial-hook

Tags: ,
| Posted in Asterisk | No Comments »
3.04.2019

FREEPBX. SURVEY. IVR. REPORT

Задача: написать модуль для freepbx который бы переводил пользователя на ivr оценки качества или просто опрос звонящего

Система обслуживания это несколько вопросов на которые пользователи должны дать ответ нажатием кнопки от 1 до 5.

Ответы должны сохраняться в базу данных с дополнительной информацией о том, какая система опрашивала, какие ответы даны, кто отвечал, запись разговора.

Статья с примером реализации. Кстати отлично показывает как работают некоторые механизмы в freepbx.

итого для создания системы опроса в freepbx можно обойтись вообще без всего и даже отчеты получать в более-менее хорошем виде

1. add content to extensions_custom.conf
;-------Survey logic------------------------------
[macro-survey]

exten => _.,1,answer()

exten => _.,n,Read(answer1,/var/lib/asterisk/sounds/en/custom/${EXTEN}-1,1,,1,2)
exten => _.,n,Read(answer2,/var/lib/asterisk/sounds/en/custom/${EXTEN}-2,1,,1,2)
exten => _.,n,Read(answer3,/var/lib/asterisk/sounds/en/custom/${EXTEN}-3,1,,1,2)
exten => _.,n,Read(answer4,/var/lib/asterisk/sounds/en/custom/${EXTEN}-4,1,,1,2)
exten => _.,n,Read(answer5,/var/lib/asterisk/sounds/en/custom/${EXTEN}-5,1,,1,2)
exten => _.,n,Read(answer6,/var/lib/asterisk/sounds/en/custom/${EXTEN}-6,1,,1,2)
exten => _.,n,Read(answer7,/var/lib/asterisk/sounds/en/custom/${EXTEN}-7,1,,1,2)
exten => _.,n,Read(answer8,/var/lib/asterisk/sounds/en/custom/${EXTEN}-8,1,,1,2)
exten => _.,n,Read(answer9,/var/lib/asterisk/sounds/en/custom/${EXTEN}-9,1,,1,2)

exten => _.,n(finish),set(answer=${answer1}|${answer2}|${answer3}|${answer4}|${answer5}|${answer6}|${answer7}|${answer8}|${answer9})

exten => _.,n,Set(CDR(userfield)=${answer})

exten => _.,n,noop(EXTEN - ${EXTEN})
exten => _.,n,noop(DIDFROM - ${FROM_DID})
exten => _.,n,noop(DEXTEN - ${DEXTEN})
exten => _.,n,noop(TIMESTP - ${TIMESTR})
exten => _.,n,noop(CALLERID - ${CALLERID(num)})
exten => _.,n,noop(RECORDS - ${UNIQUEID})
exten => _.,n,noop(EXTFROM - ${EXTTOCALL})
exten => _.,n,noop(ANSWER1 - ${answer1})
exten => _.,n,noop(ANSWER2 - ${answer2})

exten => _.,n,MYSQL(Connect connid 127.0.0.1 surveyuser 123123 asterisk)
exten => _.,n,MYSQL(Query resultid ${connid} INSERT INTO surveys_report (surveynum,did,surveyname,agent,queue,start_date,calleridorig,callid,answer1,answer2) values ('${EXTEN}','${FROM_DID}',' ','${DEXTEN}',' ','${STRFTIME(${EPOCH},,%Y%m%d-%H%M%S)}','${CALLERID(num)}','${UNIQUEID}','${answer1}','${answer2}'))

exten => _.,n,playback(/var/lib/asterisk/sounds/en/custom/${EXTEN}-thankyou)
;-------------------------------------

2. Prepare Recordings as at image 1
3. create Custom Destination as at image 2
4. create Ring Group as at image 3
5. all is ready for surveys, results and records will be stored at CDRs pages. for saving results in new table at mysql you should add new table in asterisk database;
6. SQL statement for create new table, also you should know user and password for database;
CREATE TABLE `surveys_report` (
`id` int(11) NOT NULL AUTO_INCREMENT,
`surveynum` varchar(12) DEFAULT NULL,
`surveyname` varchar(255) NOT NULL,
`agent` varchar(64) DEFAULT NULL,
`queue` varchar(64) DEFAULT NULL,
`start_date` varchar(128) DEFAULT NULL,
`calleridorig` varchar(64) DEFAULT NULL,
`callid` varchar(128) DEFAULT NULL,
`answer1` varchar(64) DEFAULT NULL,
`answer2` varchar(64) DEFAULT NULL,
`did` varchar(64) DEFAULT NULL,
PRIMARY KEY (`id`)
)

CREATE USER 'surveyuser'@'localhost' IDENTIFIED BY '123123';
grand all on asterisk.* to 'surveyuser'@'localhost' IDENTIFIED BY '123123';

25.03.2019

freepbx + a2biling different places

Чтобы разнести а2биллинг и астериск по разным машинам, нужно определиться будем ли мы запускать скрипты на машине с астериском или через fastAGI

в интернете есть упоминания о том, что при использовании fastAGI возникли проблемы с биллингом по этому,был выбран путь 1. скачать скрипты, подключиться к БД и вперед

Есть одно неудобство, которая пока не знаю как победить – просмотр логов из панели а2биллинга невозможет, т.к. они лежат на другой тачке.

Что нужно чтобы скрипты заработали, за основу берем хорошую статью:

  • Скачать исходники а2биллинга(распаковывать кстати командой unzip, через mc Занимает много времени)
  • добавить AGI

Цитата: Set up AGI

mkdir /var/lib/asterisk/agi-bin
cd /usr/src/a2billing/AGI               
cp a2billing.php /var/lib/asterisk/agi-bin
cp a2billing_monitoring.php /var/lib/asterisk/agi-bin
chown -R asterisk. /var/lib/asterisk/agi-bin
chmod 755 /var/lib/asterisk/agi-bin/a2billing.php
chmod 755 /var/lib/asterisk/agi-bin/a2billing_monitoring.php
ln -s /var/www/html/a2billing/common/lib /var/lib/asterisk/agi-bin/lib
ln -s /var/www/html/a2billing/vendor /var/lib/asterisk/vendor

Add the following extensions to /etc/asterisk/extensions_custom.conf

If not using Freepbx then this would go into /etc/asterisk/extensions.conf.  Customize this to your needs.

The 1 in a2billing.php,1 refers to the default agi-conf1 configuration in a2billing system settings.  It is possible to add additional agi-conf such as agi-conf2 etc. via System Settings > Add agi-conf.

nano /etc/asterisk/extensions_custom.conf
[a2billing-did] 
exten => _X.,1,AGI(a2billing.php,1,did)
exten => _X.,n,Hangup()

[a2billing-out]
exten => _X.,1,AGI(a2billing.php,1)
exten => _X.,n,Hangup()

Add custom destinations to FreePBX via FreePBX GUI>Admin>Custom Destinations

These destinations are referring to the custom extensions created above in /etc/asterisk/extensions_custom.conf

Target: a2billing-did,${EXTEN},1 
Description: A2Billing - Inbound

Target: a2billing-out,${EXTEN},1 
Description: A2Billing - Outbound

Create inbound route

We are creating a universal DID inbound route.  This requires _. in the DID number field.  That is underscore character followed by period or dot character. 

Connectivity > Inbound Routes

Description: Some descriptive name

DID number: _.

Set Destination: Custom Destinations
                               A2Billing - Inbound

13.03.2019

connecting TATA sip trunk

TATA выдает подключает sip-trunkи через локальные сети, т.е. например они дают подсеть 10.0.8.6/32 со шлюзом 10.0.8.5 и только назначив первый ip адрес вы сможете подключиться к их voip сети.

Сразу укажу статью оригинал, которая помогла понять смысл подключения.

В качестве IP SBC\PBX тоже используются локальный адрес, например это может быть 10.0.74.11.

Едем дальше, чтобы получать входящие звонки нужно:

  • добавить интерфейс к centos ip address add 10.0.86.6/30 dev eth0:0
  • создать статический маршрут route add 10.0.74.11 gateway 10.0.8.5
  • регистрироваться на их SBC (пароль по-умолчанию 1234)
    register => 66810000:1234:66810000@10.0.74.11/66810000

для совершения исходящих:

  • нужно звонить по определенным правилам набора, например для индии это набор номера 10 знаков без 5.
  • нужно использовать в поле FROM правильный номер,
  • А также необходимо удостовериться что поле contact соответствует 10.0.8.6 (если такое сделать не получится, то у меня звонки проходили и без этого пункта ),
  • Обязательно добавьте SIP заголовок к исходящим
    P-Preferred-Identity: <sip:66810000@SBC_IP> ,

для FREEPBX добавить sip заголовок к исходящему звонку просто:

  • добавить в файл extensions_custom.conf нужный контекст, например такой:
[add-tata1-header] 
exten => s,1,SipAddHeader(P-Preferred-Identity: ${ARG1})
exten => s,n,Return
  • в настройках транка переопределить DIAL опции на:
B(add-tata1-header^s^1(66810000@10.0.76.11))

Вот так сумбурно, но в целом это все требования.

PS: чтобы freepbx подставлял в поле contact нужные данные, необходимо чтобы был маршрут до SBC. route add sbc_ip gateway gateway_IP. А также сети должны быть прописаны в конфигах Asterisk как localnet

5.03.2019

update elastix 2.5 to FreePBX 14

Оказывается, это можно сделать буквально в два движения.

Вот ссылка на инструкцию, там смысл простой запускаешь на машине-приёмнике команду, затем туже команду на машине-источнике и вуаля.

Кое-что придёт перенести вручную, но 90% работы делается автоматически.

10.12.2018

migrate freepbx inaflash to issabel 2.11

update: После действий необходимо проверить IVR и какие outbound_trunk  включены или выключены. 

автоматический перенос не возможен, но вполне возможно перенести основные данные через таблицы, для этого нужно:

  1. развернуть дам базы данных freepbx в новую базу данных на машине, где расположен issabel, например в test_aster
  2. дополнить удалить колонки в старой базе данных:  

alter table test_aster.fax_users add column faxattachformat varchar(10);
alter table test_aster.incoming drop column faxexten;
alter table test_aster.incoming drop column faxemail;
alter table test_aster.incoming drop column answer;
alter table test_aster.incoming drop column wait;
alter table test_aster.queues_config add column destcontinue varchar(50);
alter table test_aster.queues_config add column callback_id varchar(8);
alter table test_aster.ivr_details add column timeout_ivr_ret tinyint(1);
alter table test_aster.ivr_details add column invalid_ivr_ret tinyint(1);
alter table test_aster.ivr_details drop column timeout_enabled;
alter table test_aster.timeconditions add column timeconditions varchar(50);

Теперь можно копировать данные из этих таблиц простым запросом:

insert into asterisk.ivr_entries select * from test_aster.ivr_entries;

Список таблиц которые надо скопировать, все таблицы копировать я полагаю нельзя, т.к. в них содержится конфигурация всей системы – это может привести к неисправимым поломкам в GUI. 

insert into asterisk.announcement select * from test_aster.announcement;
insert into asterisk.cidlookup select * from test_aster.cidlookup;
insert into asterisk.cidlookup_incoming select * from test_aster.cidlookup_incoming;
insert into asterisk.daynight select * from test_aster.daynight;
insert into asterisk.devices select * from test_aster.devices;
//directory tables not found in issabelPBX maybe we have to install directory module;
insert into asterisk.fax_users select * from test_aster.fax_users;
//featurecodes table is present and seems we don’t need to update it
//freepbx_users not in issabel maybe we have to install it
//hotelwakeup_calls not in issabelPBX
insert into asterisk.incoming select * from test_aster.incoming;
insert into asterisk.ivr_details select * from test_aster.ivr_details;
//outbound_route_patterns linked with route_id so it maybe differend between systems
insert into asterisk.outbound_route_patterns select * from test_aster.outbound_route_patterns;
insert into asterisk.outbound_routes select * from test_aster.outbound_routes;
insert into asterisk.paging_groups select * from test_aster.paging_groups;
insert into asterisk.queues_config select * from test_aster.queues_config;
insert into asterisk.queues_details select * from test_aster.queues_details;
insert into asterisk.recordings select * from test_aster.recordings;
insert into asterisk.ringgroups select * from test_aster.ringgroups;
insert into asterisk.sip select * from test_aster.sip;
//superfectaconfig tables not present maybe we have to install module superfecta
insert into asterisk.timeconditions select * from test_aster.timeconditions;
insert into asterisk.timegroups_details select * from test_aster.timegroups_details;
insert into asterisk.timegroups_groups select * from test_aster.timegroups_groups;
insert into asterisk.trunks select * from test_aster.trunks;
insert into asterisk.users select * from test_aster.users;