Files
ViciDialSVN/agc_2-X/trunk/agi/agent_monitor.agi
T
mattf 446b80719a Added filtering to AGI processes to help prevent DID SQL injection attacks
Added nanpa filtering log viewing to new NANPA updating process
Fixed span order in vicidial.php
Fixed issue with list webform overrides in agent interface
other small variable filtering fixes

git-svn-id: svn://192.168.202.10@2023 3d104415-ff17-0410-8863-d5cf3c621b8a
2013-09-26 01:27:15 +00:00

711 lines
23 KiB
Perl

#!/usr/bin/perl
#
# agent_monitor.agi version 2.8
#
# This script is designed to allow managers to listen to agent sessions by
# dialing a phone exten number or user ID number. For this to work, the user ID
# or phone extension must be only digits. If you are using the phone extension,
# then all phone extensions on the system must be unique.
#
# user is prompted for a user ID or phone login then press #
# then the user is forwarded to monitor the active vicidial agent session
#
# ; settings for this script:
# ; 1. USER, PHONE, PLOGIN or REDIRECT, lookup by user id, phone extension or phone login (default is USER)
# ; 2. Y or N, log in api log (default is N)
# ; 3. BARGE or LISTEN, (default is LISTEN)
# ; 4. Prepopulated ID, for use in context by itself
# ; 5. Campaign limits, double-dash-delimited, i.e. "TEST--TEST2", (default is disabled)
# ; 6. Y or N, play user IDs to listen to (default is N)
#
# can be added as an AGI to a Call Menu, or just a direct extension transfer:
#
# ; call menu AGI with options:
# agent_monitor.agi,USER---N---LISTEN------TEST--TEST2---N
#
# ; or as extension transfer to "up_monitor" context and "s" extension
#
# Copyright (C) 2013 Matt Florell <vicidial@gmail.com> LICENSE: AGPLv2
#
# CHANGELOG
# 130716-1315 - First build based upon agi-phone_monitor.agi
# 130925-1823 - Added variable filter to prevent DID SQL injection attack
#
&get_time_now;
$start_epoch = $now_date_epoch;
$script = 'agent_monitor.agi';
$now_date_epoch = time();
$now_date = "$year-$mon-$mday $hour:$min:$sec";
($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(time);
$year = ($year + 1900);
$mon++;
if ($mon < 10) {$mon = "0$mon";}
if ($mday < 10) {$mday = "0$mday";}
if ($hour < 10) {$hour = "0$hour";}
if ($min < 10) {$min = "0$min";}
if ($sec < 10) {$sec = "0$sec";}
$SQLdate = "$year-$mon-$mday $hour:$min:$sec";
$CIDdate = "$mon$mday$hour$min$sec";
while (length($CIDdate) > 9) {$CIDdate =~ s/^.//gi;} # 0902235959 changed to 902235959
$US='_';
# default path to astguiclient configuration file:
$PATHconf = '/etc/astguiclient.conf';
open(conf, "$PATHconf") || die "can't open $PATHconf: $!\n";
@conf = <conf>;
close(conf);
$i=0;
foreach(@conf)
{
$line = $conf[$i];
$line =~ s/ |>|\n|\r|\t|\#.*|;.*//gi;
if ( ($line =~ /^PATHlogs/) && ($CLIlogs < 1) )
{$PATHlogs = $line; $PATHlogs =~ s/.*=//gi;}
if ( ($line =~ /^PATHsounds/) && ($CLIsounds < 1) )
{$PATHsounds = $line; $PATHsounds =~ s/.*=//gi;}
if ( ($line =~ /^PATHmonitor/) && ($CLImonitor < 1) )
{$PATHmonitor = $line; $PATHmonitor =~ s/.*=//gi;}
if ( ($line =~ /^VARserver_ip/) && ($CLIserver_ip < 1) )
{$VARserver_ip = $line; $VARserver_ip =~ s/.*=//gi;}
if ( ($line =~ /^VARDB_server/) && ($CLIDB_server < 1) )
{$VARDB_server = $line; $VARDB_server =~ s/.*=//gi;}
if ( ($line =~ /^VARDB_database/) && ($CLIDB_database < 1) )
{$VARDB_database = $line; $VARDB_database =~ s/.*=//gi;}
if ( ($line =~ /^VARDB_user/) && ($CLIDB_user < 1) )
{$VARDB_user = $line; $VARDB_user =~ s/.*=//gi;}
if ( ($line =~ /^VARDB_pass/) && ($CLIDB_pass < 1) )
{$VARDB_pass = $line; $VARDB_pass =~ s/.*=//gi;}
if ( ($line =~ /^VARDB_port/) && ($CLIDB_port < 1) )
{$VARDB_port = $line; $VARDB_port =~ s/.*=//gi;}
$i++;
}
if (!$VARDB_port) {$VARDB_port='3306';}
if (!$AGILOGfile) {$AGILOGfile = "$PATHlogs/agent_monitor.$year-$mon-$mday";}
use Time::HiRes ('gettimeofday','usleep','sleep'); # necessary to have perl sleep command of less than one second
($START_s_hires, $START_usec) = gettimeofday();
$START_usec = sprintf("%06s", $START_usec);
use DBI;
use Asterisk::AGI;
$AGI = new Asterisk::AGI;
$dbhA = DBI->connect("DBI:mysql:$VARDB_database:$VARDB_server:$VARDB_port", "$VARDB_user", "$VARDB_pass")
or die "Couldn't connect to database: " . DBI->errstr;
### BEGIN parsing run-time options ###
if (length($ARGV[0])>1)
{
if ($AGILOG) {$agi_string = "Perl Environment Dump:"; &agi_output;}
$i=0;
while ($#ARGV >= $i)
{
$args = "$args $ARGV[$i]";
if ($AGILOG) {$agi_string = "$i|$ARGV[$i]"; &agi_output;}
$i++;
}
### list of command-line array arguments:
@ARGV_vars = split(/---/, $ARGV[0]);
$user_phone = $ARGV_vars[0];
$api_log = $ARGV_vars[1];
$barge_listen = $ARGV_vars[2];
$prepop_id = $ARGV_vars[3];
$campaigns_limit = $ARGV_vars[4];
$users_list = $ARGV_vars[5];
}
if ( (length($user_phone) < 1) || ($user_phone !~ /USER|PHONE|PLOGIN|REDIRECT/) )
{$user_phone = 'USER';}
if ( (length($api_log) < 1) || ($api_log !~ /Y|N/) )
{$api_log = 'N';}
if ( (length($barge_listen) < 1) || ($barge_listen !~ /BARGE|LISTEN/) )
{$barge_listen = 'LISTEN';}
if ( (length($users_list) < 1) || ($users_list !~ /Y|N/) )
{$users_list = 'N';}
$campaigns_limitSQL='';
if (length($campaigns_limit) > 1)
{
$campaigns_limitSQL = $campaigns_limit;
$campaigns_limitSQL =~ s/--/','/gi;
$campaigns_limitSQL = "and campaign_id IN('$campaigns_limitSQL')";
$campaigns_limitSQL =~ s/,''//gi;
}
### END parsing run-time options ###
$|=1;
while(<STDIN>)
{
chomp;
last unless length($_);
if ($V)
{
if (/^agi_(\w+)\:\s+(.*)$/)
{
$AGI{$1} = $2;
}
}
if (/^agi_context\:\s+(.*)$/) {$context = $1;}
if (/^agi_uniqueid\:\s+(.*)$/) {$unique_id = $1; $uniqueid = $1;}
if (/^agi_extension\:\s+(.*)$/) {$extension = $1;}
if (/^agi_channel\:\s+(.*)$/) {$channel = $1;}
if (/^agi_callerid\:\s+(.*)$/) {$callerid = $1;}
if (/^agi_calleridname\:\s+(.*)$/) {$calleridname = $1;}
}
$callerid =~ s/\'|\\\\|\\\|\\|\\;|\\\;|\;|;//gi;
$calleridname =~ s/\'|\\\\|\\\|\\|\\;|\\\;|\;|;//gi;
$extension =~ s/\'|\"|\\\\|\\\|\\|\\;|\\\;|\;|;//gi;
if ( ($callerid =~ /\".*\"/) && ( (!$calleridname) or ($calleridname =~ /unknown/) ) )
{
$calleridname = $callerid;
$calleridname =~ s/\<\d\d\d\d\d\d\d\d\d\d\>//gi;
$calleridname =~ s/\"|\" //gi;
}
$orig_callerid = $callerid;
$callerid =~ s/\D//gi;
$calleridname =~ s/unknown//gi;
if ( (!$callerid) or ($callerid =~ /unknown/) )
{$callerid = $calleridname;}
$phone_number=$callerid;
### Grab Server values from the database
$stmtA = "SELECT ext_context,agi_output FROM servers where server_ip = '$VARserver_ip';";
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
$rec_count=0;
while ($sthArows > $rec_count)
{
@aryA = $sthA->fetchrow_array;
$DBext_context = $aryA[0];
$DBagi_output = $aryA[1];
if ($DBext_context) {$ext_context = $DBext_context;}
if ($DBagi_output =~ /STDERR/) {$AGILOG = '1';}
if ($DBagi_output =~ /FILE/) {$AGILOG = '2';}
if ($DBagi_output =~ /BOTH/) {$AGILOG = '3';}
$rec_count++;
}
$sthA->finish();
if ($calleridname =~ /^AGMON/)
{
$user_REDIRECT=0;
if ($user_phone =~ /REDIRECT/)
{$user_REDIRECT++;}
$stmtA = "SELECT channel,server_ip,user_phone,api_log,barge_listen,prepop_id,campaigns_limit,users_list,context FROM vicidial_monitor_calls where callerid='$calleridname';";
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$channel = $aryA[0];
$server_ip = $aryA[1];
$user_phone = $aryA[2];
$api_log = $aryA[3];
$barge_listen = $aryA[4];
$prepop_id = $aryA[5];
$campaigns_limit = $aryA[6];
$users_list = $aryA[7];
$context = $aryA[8];
}
$sthA->finish();
if ($AGILOG) {$agi_string = "EXISTING MONITOR SESSION: |$calleridname|$channel|$server_ip|$user_phone|$api_log|$barge_listen|$prepop_id|$campaigns_limit|$users_list|$context|"; &agi_output;}
$campaigns_limitSQL='';
if (length($campaigns_limit) > 1)
{
$campaigns_limitSQL = $campaigns_limit;
$campaigns_limitSQL =~ s/--/','/gi;
$campaigns_limitSQL = "and campaign_id IN('$campaigns_limitSQL')";
$campaigns_limitSQL =~ s/,''//gi;
}
if ($user_REDIRECT > 0)
{
$MHGqueryCID = "AGMHG$CIDdate$START_usec";
### insert a NEW record to the vicidial_manager table to be processed
$stmtA = "INSERT INTO vicidial_manager values('','','$SQLdate','NEW','N','$server_ip','','Redirect','$MHGqueryCID','Channel: $channel','Context: $context','Exten: s','Priority: 1','CallerID: $MHGqueryCID','','','','','')";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "-- AGENT MONITOR CALL RESET: |$affected_rows|$calleridname|$channel|$server_ip|$context|$MHGqueryCID|"; &agi_output;}
sleep(5);
exit;
}
}
else
{
### Insert agent monitor record entry to keep track of the call
$MONqueryCID = "AGMON$CIDdate$START_usec";
$calleridname = $MONqueryCID;
$AGI->set_callerid($MONqueryCID);
print STDERR "Setting CID \"$MONqueryCID\"\n";
$stmtA="INSERT INTO vicidial_monitor_calls set server_ip='$VARserver_ip',callerid='$MONqueryCID',channel='$channel',context='$context',uniqueid='$uniqueid',monitor_time=NOW(),user_phone='$user_phone',api_log='$api_log',barge_listen='$barge_listen',prepop_id='$prepop_id',campaigns_limit='$campaigns_limit',users_list='$users_list';";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "MONITOR CALLS INSERT $affected_rows|$stmtA|"; &agi_output;}
}
$AGI->stream_file('sip-silence');
$AGI->stream_file('sip-silence');
if ($users_list =~ /Y/i)
{
### find sox binary to do the combination of audio files for agent listing
$soxbin = '';
if ( -e ('/usr/bin/sox')) {$soxbin = '/usr/bin/sox';}
else
{
if ( -e ('/usr/local/bin/sox')) {$soxbin = '/usr/local/bin/sox';}
else
{
print "Can't find sox binary! Exiting...\n";
$AGI->stream_file('an-error-has-occured');
exit;
}
}
}
$entry_chances=0;
$VALID_login=0;
$ACTIVE_login=0;
$VDADremDIALstr='';
while ( ($entry_chances < 3) && ($VALID_login < 1) )
{
$entry_chances++;
if (length($prepop_id)<2)
{
&user_phone_gather;
}
else
{$PIN_number = $prepop_id;}
###### Check userID and password against vicidial_users table
$stmtA = "SELECT count(*) FROM vicidial_users where user='$PIN_number' and active='Y';";
if ($user_phone =~ /PHONE/)
{$stmtA = "SELECT count(*) FROM phones where extension='$PIN_number' and active='Y';";}
if ($user_phone =~ /PLOGIN/)
{$stmtA = "SELECT count(*) FROM phones where login='$PIN_number' and active='Y';";}
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$VALID_login = $aryA[0];
}
$sthA->finish();
if ($VALID_login > 0)
{
$AGI->stream_file('pin-number-accepted');
}
else
{
if ($api_log =~ /Y/)
{
$stmtA="INSERT INTO vicidial_api_log set user='$calleridname',agent_user='$PIN_number',function='phone_monitor',value='',result='ERROR',result_reason='No user found',source='monitor',data='$calleridname|$callerid',api_date='$now_date',api_script='$script',run_time='0';";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "API LOG INSERT $affected_rows|$stmtA|"; &agi_output;}
}
$AGI->stream_file('pin-invalid');
}
}
if ($VALID_login < 1)
{
if ($AGILOG) {$agi_string = "PHONE MONITOR END: Invalid Login |$VALID_login|$PIN_number|"; &agi_output;}
if ($use_call_menu =~ /Y/)
{
if ($AGILOG) {$agi_string = "exiting the agent dial-in app, transferring call to B @ $context"; &agi_output;}
print "SET CONTEXT $context\n";
$result = <STDIN>;
checkresult($result);
print "SET EXTENSION B\n";
$result = <STDIN>;
checkresult($result);
print "SET PRIORITY 1\n";
$result = <STDIN>;
checkresult($result);
}
else
{
$AGI->stream_file('vm-goodbye');
$AGI->hangup();
$dbhA->disconnect();
}
exit;
}
else
{
$secX = time();
$PDtarget = ($secX - 30);
($Psec,$Pmin,$Phour,$Pmday,$Pmon,$Pyear,$Pwday,$Pyday,$Pisdst) = localtime($PDtarget);
$Pyear = ($Pyear + 1900);
$Pmon++;
if ($Pmon < 10) {$Pmon = "0$Pmon";}
if ($Pmday < 10) {$Pmday = "0$Pmday";}
if ($Phour < 10) {$Phour = "0$Phour";}
if ($Pmin < 10) {$Pmin = "0$Pmin";}
if ($Psec < 10) {$Psec = "0$Psec";}
$PDtsSQLdate = "$Pyear$Pmon$Pmday$Phour$Pmin$Psec";
###### Check if user is logged in, vicidial_live_agents table
$stmtA = "SELECT count(*) FROM vicidial_live_agents where user='$PIN_number' and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL;";
if ($user_phone =~ /PHONE/)
{$stmtA = "SELECT count(*) FROM vicidial_live_agents where extension LIKE \"%/$PIN_number\" and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL;";}
if ($user_phone =~ /PLOGIN/)
{
$PLOGIN_extension='XXXXXXXXXXXXXXXXXX';
$PLOGIN_server_ip='1.1.1.1';
$stmtA = "SELECT extension,server_ip FROM phones where login='$PIN_number' and active='Y';";
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$PLOGIN_extension = $aryA[0];
$PLOGIN_server_ip = $aryA[1];
}
$sthA->finish();
if ($AGILOG) {$agi_string = "PLOGIN DEBUG: |$PLOGIN_extension|$PLOGIN_server_ip|$stmtA|"; &agi_output;}
$stmtA = "SELECT count(*) FROM vicidial_live_agents where extension LIKE \"%/$PLOGIN_extension\" and server_ip='$PLOGIN_server_ip' and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL;";
}
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$ACTIVE_login = "$aryA[0]";
}
$sthA->finish();
if ($ACTIVE_login < 1)
{
if ($AGILOG) {$agi_string = "PHONE MONIOR END: Inactive Login |$VALID_login|$PIN_number|$PASS_word| |$ACTIVE_login|$PDtsSQLdate|$stmtA|"; &agi_output;}
if ($api_log =~ /Y/)
{
$stmtA="INSERT INTO vicidial_api_log set user='$calleridname',agent_user='$PIN_number',function='phone_monitor',value='',result='ERROR',result_reason='Inactive Login',source='monitor',data='$calleridname|$callerid',api_date='$now_date',api_script='$script',run_time='0';";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "API LOG INSERT $affected_rows|$stmtA|"; &agi_output;}
}
$AGI->stream_file('login-fail');
$AGI->stream_file('vm-goodbye');
$AGI->hangup();
$dbhA->disconnect();
exit;
}
else
{
$stmtA = "SELECT conf_exten,extension,server_ip,campaign_id from vicidial_live_agents WHERE user='$PIN_number' and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL limit 1;";
if ($user_phone =~ /PHONE/)
{$stmtA = "SELECT conf_exten,extension,server_ip,campaign_id FROM vicidial_live_agents where extension LIKE \"%/$PIN_number\" and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL limit 1;";}
if ($user_phone =~ /PLOGIN/)
{
$PLOGIN_extension='XXXXXXXXXXXXXXXXXX';
$PLOGIN_server_ip='1.1.1.1';
$stmtA = "SELECT extension,server_ip FROM phones where login='$PIN_number' and active='Y';";
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$PLOGIN_extension = $aryA[0];
$PLOGIN_server_ip = $aryA[1];
}
$sthA->finish();
$stmtA = "SELECT conf_exten,extension,server_ip,campaign_id FROM vicidial_live_agents where extension LIKE \"%/$PLOGIN_extension\" and server_ip='$PLOGIN_server_ip' and extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL limit 1;";
}
if ($AGILOG) {$agi_string = "|$stmtA|"; &agi_output;}
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
$rec_countCUSTDATA=0;
if ($sthArows > 0)
{
@aryA = $sthA->fetchrow_array;
$VDADconf_exten = $aryA[0];
$VDADextension = $aryA[1];
$VDADserver_ip = $aryA[2];
$VDADcampaign_id = $aryA[3];
}
$sthA->finish();
### format the remote server dialstring to get the call to the overflow agent meetme room
$S='*';
if( $VDADserver_ip =~ m/(\S+)\.(\S+)\.(\S+)\.(\S+)/ )
{
$a = leading_zero($1);
$b = leading_zero($2);
$c = leading_zero($3);
$d = leading_zero($4);
# use double-star prefix to go through native bridge IAX path
$VDADremDIALstr = "$S$S$a$S$b$S$c$S$d$S";
}
$barge_listen_prefix = '58';
if($barge_listen =~ /BARGE/)
{$barge_listen_prefix = '59';}
$VDADremDIALstr .= "$barge_listen_prefix$VDADconf_exten";
if ($api_log =~ /Y/)
{
$stmtA="INSERT INTO vicidial_api_log set user='$orig_callerid',agent_user='$PIN_number',function='phone_monitor',value='',result='SUCCESS',result_reason='',source='monitor',data='$VDADconf_exten|$VDADextension|$VDADserver_ip|$calleridname|$callerid',api_date='$now_date',api_script='$script',run_time='0';";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "API LOG INSERT $affected_rows|$stmtA|"; &agi_output;}
}
$stmtA="INSERT INTO vicidial_monitor_log set server_ip='$VARserver_ip',callerid='$calleridname',channel='$channel',context='$context',uniqueid='$uniqueid',monitor_time=NOW(),user='$PIN_number',campaign_id='$VDADcampaign_id';";
$affected_rows = $dbhA->do($stmtA);
if ($AGILOG) {$agi_string = "MONITOR LOG INSERT $affected_rows|$stmtA|"; &agi_output;}
if ($AGILOG) {$agi_string = "Agent $PIN_number sent to $VDADremDIALstr"; &agi_output;}
print "SET CONTEXT $ext_context\n";
$result = <STDIN>;
checkresult($result);
print "SET EXTENSION $VDADremDIALstr\n";
$result = <STDIN>;
checkresult($result);
print "SET PRIORITY 1\n";
$result = <STDIN>;
checkresult($result);
}
}
$dbhA->disconnect();
exit;
################################################################################
##### SUBROUTINES ##############################################################
################################################################################
##### BEGIN collect the user and password ######################################
sub user_phone_gather
{
################################################################################
# please enter the pin number followed by the pound key
$gsm = '.gsm';
$gather_prompt = 'ld_welcome_pin_number';
if ($users_list =~ /Y/i)
{
### generate user list for live agents available for monitoring
$sox_cmd = "$soxbin --combine concatenate /var/lib/asterisk/sounds/ld_welcome_pin_number.gsm /var/lib/asterisk/sounds/silence.wav";
$secX = time();
$PDtarget = ($secX - 30);
($Psec,$Pmin,$Phour,$Pmday,$Pmon,$Pyear,$Pwday,$Pyday,$Pisdst) = localtime($PDtarget);
$Pyear = ($Pyear + 1900);
$Pmon++;
if ($Pmon < 10) {$Pmon = "0$Pmon";}
if ($Pmday < 10) {$Pmday = "0$Pmday";}
if ($Phour < 10) {$Phour = "0$Phour";}
if ($Pmin < 10) {$Pmin = "0$Pmin";}
if ($Psec < 10) {$Psec = "0$Psec";}
$PDtsSQLdate = "$Pyear$Pmon$Pmday$Phour$Pmin$Psec";
$stmtA = "SELECT user FROM vicidial_live_agents where last_update_time > \"$PDtsSQLdate\" and extension NOT LIKE \"R/%\" $campaigns_limitSQL order by last_update_time desc limit 100;";
if ($user_phone =~ /PHONE/)
{$stmtA = "SELECT extension FROM vicidial_live_agents where extension NOT LIKE \"R/%\" and last_update_time > \"$PDtsSQLdate\" $campaigns_limitSQL limit 100;";}
$sthA = $dbhA->prepare($stmtA) or die "preparing: ",$dbhA->errstr;
$sthA->execute or die "executing: $stmtA ", $dbhA->errstr;
$sthArows=$sthA->rows;
if ($AGILOG) {$agi_string = "Available Agents Found: |$sthArows|$stmtA|"; &agi_output;}
$i=0;
while ($sthArows > $i)
{
@aryA = $sthA->fetchrow_array;
$sox_cmd .= " /var/lib/asterisk/sounds/silence.wav /var/lib/asterisk/sounds/user.gsm";
$sox_user = $aryA[0];
$sox_user =~ s/IAX2\/|IAX\/|SIP\///gi;
$sox_user =~ s/\D//gi;
foreach $user_char (split //, $sox_user)
{
$sox_cmd .= " /var/lib/asterisk/sounds/digits/$user_char$gsm";
}
$i++;
}
$sthA->finish();
if ($sthArows < 1)
{
$sox_cmd .= " /var/lib/asterisk/sounds/silence.wav /var/lib/asterisk/sounds/user.gsm /var/lib/asterisk/sounds/unavailable.gsm";
}
$sox_cmd .= " /var/lib/asterisk/sounds/mtemp/$calleridname$gsm";
if ($AGILOG) {$agi_string = "SoX CLI: |$i|$sox_cmd|"; &agi_output;}
@sox_cmd_output = `$sox_cmd`;
sleep(2);
if ( -e ("/var/lib/asterisk/sounds/mtemp/$calleridname$gsm"))
{$gather_prompt = "./mtemp/$calleridname";}
else
{
print "ERROR! Dynamic user list not created! Exiting...\n";
$AGI->stream_file('an-error-has-occured');
exit;
}
}
$interrupt_digit='';
$interrupt_digit = $AGI->stream_file("$gather_prompt",'0123456789');
print STDERR "interrupt_digit |$interrupt_digit|\n";
$digits_being_entered=1;
$PIN_number='';
if ($interrupt_digit > 0)
{
# if ($interrupt_digit == 35) {$interrupt_digit='#';}
# if ($interrupt_digit == 42) {$interrupt_digit='*';}
if ($interrupt_digit == 48) {$interrupt_digit=0;}
if ($interrupt_digit == 49) {$interrupt_digit=1;}
if ($interrupt_digit == 50) {$interrupt_digit=2;}
if ($interrupt_digit == 51) {$interrupt_digit=3;}
if ($interrupt_digit == 52) {$interrupt_digit=4;}
if ($interrupt_digit == 53) {$interrupt_digit=5;}
if ($interrupt_digit == 54) {$interrupt_digit=6;}
if ($interrupt_digit == 55) {$interrupt_digit=7;}
if ($interrupt_digit == 56) {$interrupt_digit=8;}
if ($interrupt_digit == 57) {$interrupt_digit=9;}
$PIN_number=$interrupt_digit;
}
$digit_loop_counter=0;
while ( ($digits_being_entered > 0) && ($digit_loop_counter < 20) )
{
$digit = chr($AGI->wait_for_digit('10000')); # wait 10 seconds for input or until the pound key is pressed
if ($digit =~ /\d/)
{
$PIN_number = "$PIN_number$digit";
print STDERR "digit |$digit| PIN_number |$PIN_number|\n";
# $AGI->say_digits("$digit");
undef $digit;
}
else
{
$digits_being_entered=0;
}
$digit_loop_counter++;
}
$PIN_number =~ s/\D//gi;
if ($PIN_number) {print STDERR "digit |$digit| PIN_number |$PIN_number|\n";}
}
##### END collect the user and password ###############################################
sub get_time_now #get the current date and time and epoch for logging call lengths and datetimes
{
($sec,$min,$hour,$mday,$mon,$year,$wday,$yday,$isdst) = localtime(time);
$year = ($year + 1900);
$mon++;
if ($mon < 10) {$mon = "0$mon";}
if ($mday < 10) {$mday = "0$mday";}
if ($hour < 10) {$hour = "0$hour";}
if ($min < 10) {$min = "0$min";}
if ($sec < 10) {$sec = "0$sec";}
$now_date_epoch = time();
$now_date = "$year-$mon-$mday $hour:$min:$sec";
$filedate = "$year$mon$mday$hour$min$sec";
}
sub checkresult
{
my ($res) = @_;
my $retval;
$tests++;
chomp $res;
if ($res =~ /^200/) {
$res =~ /result=(-?\d+)/;
if (!length($1))
{
print STDERR "FAIL ($res)\n";
$fail++;
}
else
{
print STDERR "PASS ($1)\n";
$pass++;
}
}
else
{
print STDERR "FAIL (unexpected result '$res')\n";
$fail++;
}
}
sub agi_output
{
if ($AGILOG >=2)
{
### open the log file for writing ###
open(Lout, ">>$AGILOGfile")
|| die "Can't open $AGILOGfile: $!\n";
print Lout "$now_date|$script|$agi_string\n";
close(Lout);
}
### send to STDERR writing ###
if ( ($AGILOG == '1') || ($AGILOG == '3') )
{print STDERR "$now_date|$script|$agi_string\n";}
$agi_string='';
}
sub leading_zero($)
{
$_ = $_[0];
s/^(\d)$/0$1/;
s/^(\d\d)$/0$1/;
return $_;
} # End of the leading_zero() routine.