Проблема записи вызовов
Добавлено: 24 окт 2019, 11:40
Доброго всем дня!
Разрешите немного потупить?
На астериске написан план набора, который однозначно через MixMonitor инициирует запись всех входящих со стороны провайдера (внешние входящие вызовы).
Входящий звонок после IVR попадает в очередь, где на него отвечает один из свободных секретарей. Тут вопросов нет, всё работает. Так же всё без проблем работает, если вызывающая сторона наберёт добавочный номер в процессе прослушивания IVR. Тут тоже всё отлично, поскольку у меня в плане набора стоит проверка на канал, с которого пришёл вызов (Если ${CHANNEL:0:5} = DAHDI , то включаем MixMonitor)
Но, если клиент просит секретаря перевести вызов на другого сотрудника, то возникает проблема, поскольку текущая запись останавливается, а новая не начинается.
Да, она может начаться, если в БД установлен нужный ключ для sippeer-а. Другими словами, в БД MySQL в таблицу sip добавлено мной вручную поле "rec", принимающее значения 0 или 1. В контексте, который обрабатывает местные вызовы, происходит обращение к БД и среди прочего считывается значение этого поля для вызывающей стороны и для вызываемой стороны. Если хотя бы одно из них равно 1, то задействуется MixMonitor.
Что, как я думаю, происходит в момент перевода вызова:
1. Если для местного номера секретаря и у номера, на который звонок будет переведён, в поле "rec" не стоит 1, то вызов переводится, но запись заканчивается, как только секретарь положила трубку.
2. Если же 1 в поле стоит, то в момент перевода формируется новый файл для записи и начинается запись в него.
Мне же надо, чтобы система писала вызов от и до в один файл: звонок пришёл, запись пошла, секретарь ответил, секретарь перевёл, сотрудник ответил на переведённый звонок, сотрудник закончил разговор, запись закончилась. Но так не получается. (((
Я сломал голову и не знаю, как сделать так, чтобы при переводе звонка астериск проверял - "А не идёт ли уже запись?" - и не обрубал её, начиная новую.
Пример кода:
;Сюда маршрутизируется звонок на номер 7654321
[7654321]
exten => 7654321,1,
same => n,MYSQL(Connect connid localhost asterisk Пароль asterisk) ; Подключаемся к базе данных
same => n,MYSQL(Query resultid ${connid} SELECT id FROM blacklist WHERE number = '${CALLERID(num)}') ; Выбираем поле id из таблицы blacklist, где поле number = номеру вызывающей стороны
same => n,MYSQL(Fetch fetchid ${resultid} BLIST) ; Присваиваем результат переменной BLIST
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Disconnect ${connid}) ; Разъединяемся
same => n,GotoIf($["${ISNULL(${BLIST})}" = "1"]?in:out)
same => n(in),Macro(ivr,${EXTEN})
same => n,Goto(end)
same => n(out),Wait(1)
same => n,Playback(incorect-number)
same => n(end),HangUp
;IVR
[macro-ivr]
exten => s,1,Set(CALLFILENAME=${UNIQUEID}_${STRFTIME(${EPOCH},,%Y%m%d-%H%M%S)})
same => n,Set(CDR(userfield)=${CALLFILENAME}.gsm)
same => n,MixMonitor(/records/${CALLFILENAME}.gsm)
same => n,Set(QUEUENAME=q${ARG1})
same => n,Wait(0.5)
same => n,Read(IntNum,hello&nomer_sotr&na_linii,5,,1,3)
same => n,GotoIf($["${ISNULL(${IntNum})}" = "1"]?queue:intcall)
same => n(queue),Queue(${QUEUENAME},tT,,announceoverride,3000)
same => n,NoOp(${DIALSTATUS})
same => n,NoOp(${QUEUESTATUS})
same => n,Goto(end)
same => n(intcall),Goto(internal,${IntNum},1)
same => n,Goto(end)
same => n(end),HangUp
exten => i,1,Playback(invalid)
exten => i,n,HangUp
;Ну и собственно контекст internal
[internal]
exten => _5XXX,1,Set(SECLINE=${SIPPEER(${EXTEN},curcalls)})
same => n,GotoIf($["${SECLINE}" = "0"]?notsecline:secline)
same => n(secline),Playback(abonent-razgovarivaet)
same => n(notsecline),MYSQL(Connect connid localhost asterisk пароль asterisk)
same => n,MYSQL(Query resultid ${connid} SELECT rec FROM sip WHERE name = '${EXTEN}')
same => n,MYSQL(Fetch fetchid ${resultid} REC1)
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Query resultid ${connid} SELECT rec FROM sip WHERE name = '${CALLERID(num)}')
same => n,MYSQL(Fetch fetchid ${resultid} REC2)
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Disconnect ${connid})
same => n,GotoIf($[$["${REC1}" = "1"] | $["${REC2}" = "1"] | $["${CHANNEL:0:5}" = "DAHDI"]]?recordingenabled:recordingdisabled)
same => n(recordingenabled),Set(CALLFILENAME=${UNIQUEID}_${EPOCH})
same => n,Set(CDR(userfield)=${CALLFILENAME}.gsm)
same => n,MixMonitor(/records/${CALLFILENAME}.gsm)
same => n(recordingdisabled),Dial(SIP/${EXTEN},60,tg)
same => n,StopMonitor()
same => n,HangUp()
Я знаю, что тут есть много людей, которые на много лучше меня разбираются в теме.
Прошу помочь, указать на ошибки и сказать в какую сторону копать. Если будут примеры, то этим вы меня просто осчастливите.
Всем спасибо.
Разрешите немного потупить?
На астериске написан план набора, который однозначно через MixMonitor инициирует запись всех входящих со стороны провайдера (внешние входящие вызовы).
Входящий звонок после IVR попадает в очередь, где на него отвечает один из свободных секретарей. Тут вопросов нет, всё работает. Так же всё без проблем работает, если вызывающая сторона наберёт добавочный номер в процессе прослушивания IVR. Тут тоже всё отлично, поскольку у меня в плане набора стоит проверка на канал, с которого пришёл вызов (Если ${CHANNEL:0:5} = DAHDI , то включаем MixMonitor)
Но, если клиент просит секретаря перевести вызов на другого сотрудника, то возникает проблема, поскольку текущая запись останавливается, а новая не начинается.
Да, она может начаться, если в БД установлен нужный ключ для sippeer-а. Другими словами, в БД MySQL в таблицу sip добавлено мной вручную поле "rec", принимающее значения 0 или 1. В контексте, который обрабатывает местные вызовы, происходит обращение к БД и среди прочего считывается значение этого поля для вызывающей стороны и для вызываемой стороны. Если хотя бы одно из них равно 1, то задействуется MixMonitor.
Что, как я думаю, происходит в момент перевода вызова:
1. Если для местного номера секретаря и у номера, на который звонок будет переведён, в поле "rec" не стоит 1, то вызов переводится, но запись заканчивается, как только секретарь положила трубку.
2. Если же 1 в поле стоит, то в момент перевода формируется новый файл для записи и начинается запись в него.
Мне же надо, чтобы система писала вызов от и до в один файл: звонок пришёл, запись пошла, секретарь ответил, секретарь перевёл, сотрудник ответил на переведённый звонок, сотрудник закончил разговор, запись закончилась. Но так не получается. (((
Я сломал голову и не знаю, как сделать так, чтобы при переводе звонка астериск проверял - "А не идёт ли уже запись?" - и не обрубал её, начиная новую.
Пример кода:
;Сюда маршрутизируется звонок на номер 7654321
[7654321]
exten => 7654321,1,
same => n,MYSQL(Connect connid localhost asterisk Пароль asterisk) ; Подключаемся к базе данных
same => n,MYSQL(Query resultid ${connid} SELECT id FROM blacklist WHERE number = '${CALLERID(num)}') ; Выбираем поле id из таблицы blacklist, где поле number = номеру вызывающей стороны
same => n,MYSQL(Fetch fetchid ${resultid} BLIST) ; Присваиваем результат переменной BLIST
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Disconnect ${connid}) ; Разъединяемся
same => n,GotoIf($["${ISNULL(${BLIST})}" = "1"]?in:out)
same => n(in),Macro(ivr,${EXTEN})
same => n,Goto(end)
same => n(out),Wait(1)
same => n,Playback(incorect-number)
same => n(end),HangUp
;IVR
[macro-ivr]
exten => s,1,Set(CALLFILENAME=${UNIQUEID}_${STRFTIME(${EPOCH},,%Y%m%d-%H%M%S)})
same => n,Set(CDR(userfield)=${CALLFILENAME}.gsm)
same => n,MixMonitor(/records/${CALLFILENAME}.gsm)
same => n,Set(QUEUENAME=q${ARG1})
same => n,Wait(0.5)
same => n,Read(IntNum,hello&nomer_sotr&na_linii,5,,1,3)
same => n,GotoIf($["${ISNULL(${IntNum})}" = "1"]?queue:intcall)
same => n(queue),Queue(${QUEUENAME},tT,,announceoverride,3000)
same => n,NoOp(${DIALSTATUS})
same => n,NoOp(${QUEUESTATUS})
same => n,Goto(end)
same => n(intcall),Goto(internal,${IntNum},1)
same => n,Goto(end)
same => n(end),HangUp
exten => i,1,Playback(invalid)
exten => i,n,HangUp
;Ну и собственно контекст internal
[internal]
exten => _5XXX,1,Set(SECLINE=${SIPPEER(${EXTEN},curcalls)})
same => n,GotoIf($["${SECLINE}" = "0"]?notsecline:secline)
same => n(secline),Playback(abonent-razgovarivaet)
same => n(notsecline),MYSQL(Connect connid localhost asterisk пароль asterisk)
same => n,MYSQL(Query resultid ${connid} SELECT rec FROM sip WHERE name = '${EXTEN}')
same => n,MYSQL(Fetch fetchid ${resultid} REC1)
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Query resultid ${connid} SELECT rec FROM sip WHERE name = '${CALLERID(num)}')
same => n,MYSQL(Fetch fetchid ${resultid} REC2)
same => n,MYSQL(Clear ${resultid})
same => n,MYSQL(Disconnect ${connid})
same => n,GotoIf($[$["${REC1}" = "1"] | $["${REC2}" = "1"] | $["${CHANNEL:0:5}" = "DAHDI"]]?recordingenabled:recordingdisabled)
same => n(recordingenabled),Set(CALLFILENAME=${UNIQUEID}_${EPOCH})
same => n,Set(CDR(userfield)=${CALLFILENAME}.gsm)
same => n,MixMonitor(/records/${CALLFILENAME}.gsm)
same => n(recordingdisabled),Dial(SIP/${EXTEN},60,tg)
same => n,StopMonitor()
same => n,HangUp()
Я знаю, что тут есть много людей, которые на много лучше меня разбираются в теме.
Прошу помочь, указать на ошибки и сказать в какую сторону копать. Если будут примеры, то этим вы меня просто осчастливите.
Всем спасибо.