Траблшутинг и оптимизация базы данных CDR / CEL в Asterisk: MySQL и PostgreSQL
- Прекращение записи статистики звонков в таблицу
cdrилиcel. - В CLI Asterisk регистрируются ошибки
res_odbc: Error SQLFetch / Could not execute query. - Зависание завершения вызовов и резкий рост нагрузки на сервер БД из-за гигантского размера таблицы CDR (>10 млн записей).
- Несоответствие длительности разговора (Billsec) реальному времени вызова.
1. Настройка коннектора unixODBC (/etc/odbc.ini)
Файл /etc/odbc.ini:
[asterisk-connector]
Description = MySQL connection to Asterisk CDR
Driver = MySQL
Server = 127.0.0.1
Database = asteriskdb
Port = 3306
User = asterisk_user
Password = SecureDbPassword
Option = 3
Socket = /var/run/mysqld/mysqld.sockПроверьте соединение через утилиту isql:
isql -v asterisk-connector2. Конфигурация res_odbc.conf и cdr_adaptive_odbc.conf
Файл /etc/asterisk/res_odbc.conf:
[asteriskdb]
enabled => yes
dsn => asterisk-connector
max_connections => 20
pooling => yes
limit => 10
username => asterisk_user
password => SecureDbPassword
pre-connect => yesФайл /etc/asterisk/cdr_adaptive_odbc.conf:
[first]
connection=asteriskdb
table=cdr
alias start => calldate3. Оптимизация и индексация таблицы CDR в MySQL/MariaDB
-- Создание композитных индексов для быстрых выборок в CRM
ALTER TABLE cdr ADD INDEX idx_calldate (calldate);
ALTER TABLE cdr ADD INDEX idx_src_dst (src, dst);
ALTER TABLE cdr ADD INDEX idx_uniqueid (uniqueid);
ALTER TABLE cdr ADD INDEX idx_disposition_calldate (disposition, calldate);4. Партиционирование таблицы CEL (Call Event Logging)
Для таблиц с миллионами строк настройте помесячное секционирование:
ALTER TABLE cel PARTITION BY RANGE (UNIX_TIMESTAMP(eventtime)) (
PARTITION p2026_01 VALUES LESS THAN (UNIX_TIMESTAMP('2026-02-01 00:00:00')),
PARTITION p2026_02 VALUES LESS THAN (UNIX_TIMESTAMP('2026-03-01 00:00:00')),
PARTITION p_max VALUES LESS THAN MAXVALUE
);5. Проверка статуса подсистемы в CLI
asterisk -rx "odbc show asteriskdb"
asterisk -rx "cdr show status" Частые вопросы (FAQ)
В чем отличие между CDR и CEL?
CDR (Call Detail Records) сохраняет одну итоговую запись о вызове (кто, кому, когда, сколько секунд говорил, статус). CEL (Call Event Logging) сохраняет подробный лог каждого микро-события внутри звонка (старт, ответ, перевод на удержание, трансфер, вход в очередь).
Почему при потере связи с базой данных Asterisk начинает зависать?
Если драйвер CDR настроен на синхронную блокирующую запись без пула потоков, каждый завершающийся звонок ждет ответа от упавшего сокета MySQL. Использование res_odbc с пулом соединений устраняет эту проблему.
Как писать CDR в PostgreSQL вместо MySQL?
Установите odbc-postgresql, опишите DSN в /etc/odbc.ini с драйвером PostgreSQL Unicode и укажите этот DSN в res_odbc.conf.
Что означает поле disposition = 'NO ANSWER' при наличии billsec > 0?
Это признак аномалии, возникающей при некорректном выполнении команды ResetCDR() в диалплане перед выполнением вызова или ошибке в логике трансфера.