Продолжение экспериментов над установленной и рабочей системы из статьи: "Raspberry Pi + FreeBPX(asterisk) + Mikrotik = АТС мини с переходом на PJSIP (sipnet, zadarma, multifon)", подключение telegram бота.
Обновление
apt update && apt upgrade
Стандартная процедура, но учитывая что система работает на стареньком Debian Buster, то актуальные репозитории уходят в архивы и могут возникать некоторые ошибки, как например:
Пример ошибки связанный с репозиторием sury.org
The following signatures were invalid: EXPKEYSIG B188E2B695BD4743 DEB.SURY.ORG Automatic Signing Key <deb@sury.org>
Решение этой ошибки:
apt-key adv --keyserver keyserver.ubuntu.com --recv-keys B188E2B695BD4743
И по ходу обновления соглашаться с заменой путей к репозиториям.
Установка дополнительных программ для телеграм бота:
apt install python3-pip
pip3 install pyTelegramBotAPI
Переход на PJSIP
Поддался современным веяниям в отказе от протокола SIP в пользу PJSIP.
Во время манипуляций не забываем сохранять изменения кнопкой Submit.
Заходим на веб своего freepbx -> setting -> advansed setting -> sip channel driver:
отключение sip
PJSIP общие настройки:
setting -> sip setting -> pjsip
настройки
Настройка транков провайдеров
SIPNET
Zadarma ( Novofon)
Мультифон (multifon)
Создание extension (номера для абонентов) ничем не отличается от обычного sip -> задаете логин (номер) и пароль, для приема сообщений прописать в Messages Context - messages (как написано в файле /etc/asterisk/extensions_custom.conf ).
Подключение Telegram
Для чего? Т.к. у меня подключены модемы и иногда приходят смс нужные. И заметил такую особенность, что если отправитель смс какой-то мутный сервис, который любит сложности в своем названии (использовать буквы и символы, без номера) и особенно с символом @ на конце, то стандартная схема сообщения в sip теряет его на этапе пересылки в экстеншен, хотя в файл записывает нормально. Телеграм пересылает все сообщения без потерь и еще удобно показывает с какого донгла пришло. Так же этот скрипт работает, как дополнительный журнал звонков и помогает в работе уведомлений ( типа сервера пуш уведомлений).
Скрипт телегам бота
/usr/local/bin/sms2tg.py (Не забываем заменить API:KEY и CHATID на свои)
!/usr/bin/python3.7
import base64
import telebot
import sys
bot = telebot.TeleBot('API:KEY')
chat_id = CHATID
bot.send_message(chat_id, sys.argv[1])
Созданному файлу назначаем владельца asterisk и права на выполнение 755.
полная инфа по скрипту : здесь
Получение API:KEY через системного бота @BotFather (создаем своего бота, придумываем название, получаем). Chat_ID ищем в телеграмме, там полно ботов (например Get My ID), которые дают эту информацию.
Переходим в консоль сервера к файлу: /etc/asterisk/extensions_custom.conf
/etc/asterisk/extensions_custom.conf
[from-trunk-dongle]
exten => sms,1,Verbose(Incoming SMS: From: ${CALLERID(num)} ${BASE64_DECODE(${SMS_BASE64})})
exten => sms,n,Set(MESSAGE(body)=${BASE64_DECODE(${SMS_BASE64})})
exten => sms,n,System(echo '${STRFTIME(${EPOCH},,%Y-%m-%d %H:%M:%S)} - ${DONGLENAME} - ${CALLERID(num)}: ${BASE64_DECODE(${SMS_BASE64})})' >> /var/log/asterisk/sms.txt)
exten => sms,n,Set(MESSAGE(from)="${CALLERID(num)}"); <${CALLERID(num)}>)
exten => sms,n,Set(CALLERID(name)=${CALLERID(num)})
exten => sms,n,Verbose(1,${MESSAGE(from)})
exten => sms,n,MessageSend(pjsip:300,${MESSAGE(from)})
exten => sms,n,System(/usr/local/bin/sms2tg.py 'СМС: ${DONGLENAME}${CALLERID(name)}: ${MESSAGE(body)}')
exten => sms,n,Hangup()
exten => _+X.,1,Set(CALLERID(name)=${CALLERID(num)})
exten => _+X.,n,System(/usr/local/bin/sms2tg.py 'Звонил: ${DONGLENAME}${CALLERID(name)}')
exten => _+X.,n,Goto(from-trunk,${EXTEN},1)
exten => h,n,Hangup()
exten => ussd,1,Verbose(Incoming USSD: ${BASE64_DECODE(${USSD_BASE64})})
exten => ussd,n,System(echo '${STRFTIME(${EPOCH},,%Y-%m-%d %H:%M:%S)} - ${DONGLENAME}: ${BASE64_DECODE(${USSD_BASE64})}' >> /var/log/asterisk/ussd.txt)
exten => ussd,n,Hangup()
[messages]
include => send-sms
exten => _XXX,1,MessageSend(pjsip:${EXTEN},"${CALLERID(name)}"${MESSAGE(from)})
[send-sms]
exten => _+X.,1,NoOp(SMS send to dongle)
same => n,NoOp(To ${MESSAGE(to)})
same => n,NoOp(From ${MESSAGE(from)})
same => n,NoOp(Body ${MESSAGE(body)})
same => n,Set(SMSTO=${EXTEN})
same => n,DongleSendSMS(dongle1,${SMSTO},"${MESSAGE(body)}",1440,yes)
same => n,Hangup()
Есть небольшая особенность при приеме звонков через модемы - будут приниматься звонки только с нормальных номеров в соответствии с указанным шаблоном (exten => _+X.,), с сервисных номеров 3х-4х значных входящий звонок не пройдет. Можно заменить на шаблон _. , но это порождает дополнительные сложности в дублировании уведомлений и так не рекомендуют, хотя я сам почти год его использовал.
Очистка памяти сим-карт и модемов от СМС
Для очистки памяти SIM череp консоль астериска дать команды:
dongle cmd dongle0 AT+CPMS=\"SM\",\"SM\",\"SM\"
dongle cmd dongle0 AT+CMGD=1,4
Для очистки памяти модема через консоль астериска дать команды:
dongle cmd dongle0 AT+CPMS=\"ME\",\"ME\",\"ME\"
dongle cmd dongle0 AT+CMGD=1,4
dongle0 меняете на свои, которые в файле dongle.conf
Команды для применения изменений, выполнять в консоли астериска CLI
core reload now
dialplan reload
dongle reload now
Комментарии (3)
enamchuk
10.12.2022 13:58"Поддался современным веяниям в отказе от протокола SIP в пользу PJSIP. ".
Протокола PJSIP не существует, это просто другой драйвер, другая реализация протокола SIP."при приеме звонков через модемы - будут приниматься звонки только с нормальных номеров в соответствии с указанным шаблоном (exten => _+X.,), с сервисных номеров 3х-4х значных входящий звонок не пройдет."
Всё проходит корректно, вообще не важно, с какого номера вам звонят - с "нормальных", сервисных или международных, т.к. входящий вызов поступает на номер SIM, указанный в конфиге (dongle.conf - пропишите exten=ваш_номер в контекстах ваших номеров), и только на этот номер и поступит вызов.
Кстати, проблем с "@" также нет, если экранировать все передаваемые параметры.
Входящие сообщения отправляю на несколько внутренних SIP-телефонов, сохраняю в базу данных MySQL (в отдельную таблицу, ранее сохранял в поле userfield в таблице CDR, но длинные sms мешают просмотру детализации вызовов), а также в Telegram-бот (bash-скрипт).
Исходящие сообщения также хорошо отправляются с SIP-телефонов через модем.Статья полезная, и наверняка кому-нибудь пригодится.
Приходите к нам в Telegram-чат: https://t.me/asterisk_ruDmitry27 Автор
10.12.2022 17:18Всё проходит корректно, вообще не важно, с какого номера вам звонят - с "нормальных", сервисных или международных, т.к. входящий вызов поступает на номер SIM, указанный в конфиге (dongle.conf - пропишите exten=ваш_номер в контекстах ваших номеров), и только на этот номер и поступит вызов. Кстати, проблем с "@" также нет, если экранировать все передаваемые параметры.
В донгле все прописано. Я вечер сидел подбирал варианты шаблонов, не проходят звонки если шаблон не соответствует (_. или _+X.). И что значит экранировать @? Во входящем имени отправителя смс? Я проблему @ на конце имени отправителя вообще заметил когда устал ждать код подтверждения от мвидео.
Исходящие - проблем нет. Мне очень понравилось с ботом, когда разделил смс и звонки уведомления удобочитаемые стали, чем просто в клиента приходит. И я преимущественно на мобильном клиенте, соответственно некоторые не любят ждать долго гудков, бросают трубку, у мой телефон не успел принять звонок, но в телеге уже есть уведомление.
Dmitry27 Автор
Еще вопрос в догонку: почему не работает экстен вида exten => s,1,... для входящих, только при указании конкретного шаблона?