Статья
Попалась под руки Avaya IPO500, весьма кстати распространенная в наших широтах. Стало интересно - как бы с нее детализацию звонков (smdr в аваевской терминологии) получить.
Попалась под руки Avaya IPO500, весьма кстати распространенная в наших широтах. Стало интересно - как бы с нее детализацию звонков (smdr в аваевской терминологии) получить. Настройка станции весьма проста - там указывается ип-адрес сервера назначения, коллектора, и порт)
Wintarrif со сбором звонков справился на ура, но он триальный, на две недели, неинтересно, разумеется хотелось чего-нить бесплатного. Попробовали посмотреть netcat'ом, а что там собственно приходит-то, со станции, может как-нить получится формат понят и пропарсить - так вот, вы не представляете - там обычный текст идет! Один звонок - одна запись, поля разделены запятыми. Ну сами понимаете - сам торвалдс велел взять в руки напильничек, в результате чего родился вот такой вот нижеприведенный перловый скрипт-демон, который висит себе (в нашем случае на 60100-м порту) пишет звонки в логфайл, и заодно еще и в базу пишет. Ну а уж с этими данными все что душа пожелает можно сделать - например всякие отчеты по направлениям, дозвоном/недозвоном, длительностью ожидания, тарификацию ту же. Скриптом делюсь (названия полей кстати взял из документашки - почти все названия вполне понятны и говорят сами за себя)
Download file smdr.perl#!/usr/bin/perl use strict; use warnings; use DBI; package SimpleServer; use base qw(Net::Server); my $dbhost = 'localhost'; my $dbname.= 'smdr'; my $dbuser = 'smdr'; my $dbpass = 'smdr'; my $DEBUG = 0; if((defined($ARGV[0]))&&(($ARGV[0] eq '-x')||($ARGV[0] eq '-X'))) { $DEBUG = 1; } sub process_request { while () { s/\r?\n$//; print STDERR "Received [$_]\n" if $DEBUG; open FH, ">>/var/log/smdr-ip500.dump"; print FH "$_\n"; close FH; my ($CallStart, $ConnectedTime, $RingTime, $Caller, $Direction, $CalledNumber, $DialledNumber, $Account, $IsInternal, $CallID, $Continuation, $Party1Device, $Party1Name, $Party2Device, $Party2Name, $HoldTime, $ParkTime, $AuthValid, $AuthCode, $UserCharged, $CallCharge, $Currency, $AmountatLastUserChange, $CallUnits, $UnitsatLastUserChange, $CostperUnit, $MarkUp, $ExternalTargetingCause, $ExternalTargeterId, $ExternalTargetedNumber) = split /\,/; $CallStart =~ s/\//-/g; my ($h,$m,$s) = split /\:/, $ConnectedTime; $ConnectedTime = $h*3600+$m*60+$s; $RingTime = 0 if $RingTime eq ''; $IsInternal = 0 if $IsInternal eq ''; $CallID = 0 if $CallID eq ''; $Continuation = 0 if $Continuation eq ''; $HoldTime = 0 if $HoldTime eq ''; $ParkTime = 0 if $ParkTime eq ''; $AuthValid = 0 if $AuthValid eq ''; my $dbh = DBI->connect('DBI:mysql:'.$dbname.':'.$dbhost,$dbuser,$dbpass,{RaiseError => 1}) or print STDERR "connecting: $DBI::errstr\n"; $dbh->do("SET NAMES UTF8"); my $cmd = "insert into smdr set ". "CallStart = '$CallStart',". "ConnectedTime = $ConnectedTime,". "RingTime = $RingTime,". "Caller = '$Caller',". "Direction = '$Direction',". "CalledNumber = '$CalledNumber',". "DialledNumber = '$DialledNumber',". "Account = '$Account',". "IsInternal = $IsInternal,". "CallID = $CallID,". "Continuation = $Continuation,". "Party1Device = '$Party1Device',". "Party1Name = '$Party1Name',". "Party2Device = '$Party2Device',". "Party2Name = '$Party2Name',". "HoldTime = $HoldTime,". "ParkTime = $ParkTime,". "AuthValid = $AuthValid,". "AuthCode = '$AuthCode',". "UserCharged = '$UserCharged',". "CallCharge = '$CallCharge',". "Currency = '$Currency',". "AmountatLastUserChange = '$AmountatLastUserChange',". "CallUnits = '$CallUnits',". "UnitsatLastUserChange = '$UnitsatLastUserChange',". "CostperUnit = '$CostperUnit',". "MarkUp = '$MarkUp',". "ExternalTargetingCause = '$ExternalTargetingCause',". "ExternalTargeterId = '$ExternalTargeterId',". "ExternalTargetedNumber = '$ExternalTargetedNumber'"; print STDERR "SQL: $cmd\n" if $DEBUG; my $sth = $dbh->do($cmd); last if /quit/i; } } if($DEBUG) { SimpleServer->run(port => 60010); } else { SimpleServer->run(port => 60010, background => 1, setsid => 1); }