Skip to content

Instantly share code, notes, and snippets.

@ravnx
Created January 14, 2024 21:36
Show Gist options
  • Save ravnx/b478c590f9f154d6739d064f8caacae8 to your computer and use it in GitHub Desktop.
Save ravnx/b478c590f9f154d6739d064f8caacae8 to your computer and use it in GitHub Desktop.
Checks Asterisk/FreePBX for more than x phones offline, if we have an outage, switch the Call Flow Control to NIGHT. Switches back to DAY on recovery.
#!/usr/bin/perl -w
# This script will check for if more than $maxoffline phones are offline and
# change the first daynight mode via asterisk if we go over the limit, and alert the user
# Set this up in crontab to run during business hours. This probably could be done safer, and better
# using the AMI interface. But needed something done during an outage, so this got hacked together.
use strict;
use MIME::Lite;
# debug mode
my $debug = $ARGV[0] || 0;
# who gets the alert
my $alertto = 'user@gmail.com';
# Who the alert is from
my $alertfrom = 'admin@pbxadmindomain.com';
# Average amount of phones that should be online
my $onlineavg = 64;
# Set the max offline to prevent people moving phones, or some other weirdness.
# If the circuit is down, we should see a lot more offline than this number.
my $maxoffline = 20;
# check asterisk command for phone count
my $asterisk = `/usr/sbin/asterisk -rx "pjsip show contacts"`;
my @contacts = split(/\n/, $asterisk);
# print out the contacts if debug is enabled
if ($debug > 1) {
foreach my $line (@contacts) {
print "$line\n";
}
}
# Search for the line "Objects found: 15"
# if objects found is less than $maxoffline than $onlineavg, then we need to change the daynight mode to night
my $objectsfound = 0;
foreach my $line (@contacts) {
if ($line =~ /Objects found: (\d+)/) {
$objectsfound = $1;
}
}
# print out the objects found if debug is enabled
if ($debug) {
print "Objects found: $objectsfound\n";
}
if ($objectsfound < ($onlineavg - $maxoffline)) {
if ($debug) {
print "Too many offline! Lets check/change DAY/NIGHT.\n";
}
# check if daynight mode is already set to night
my $daynight = `/usr/sbin/asterisk -rx "database show DAYNIGHT/C0"`;
my @daynight = split(/\n/, $daynight);
my $daynightmode = "";
foreach my $line (@daynight) {
if ($line =~ /\/C0\s+:\s+(\w+)/) {
$daynightmode = $1;
}
}
if ($daynightmode ne "NIGHT") {
if ($debug) {
print "Daynight mode was on DAY, changing daynight mode to NIGHT.\n";
}
# change daynight mode to night
`/usr/sbin/asterisk -rx "database put DAYNIGHT C0 NIGHT"`;
sendAlert("Phones are down, system changed to outage IVR mode.", "Outage");
}
} else {
if ($debug) {
print "Not changing to night mode, only ".($onlineavg - $objectsfound)." contacts offline. Making sure we're in DAY mode.\n";
}
# check if daynight mode is already set to day
my $daynight = `/usr/sbin/asterisk -rx "database show DAYNIGHT/C0"`;
my @daynight = split(/\n/, $daynight);
my $daynightmode = "";
foreach my $line (@daynight) {
if ($line =~ /\/C0\s+:\s+(\w+)/) {
$daynightmode = $1;
}
}
if ($daynightmode ne "DAY") {
if ($debug) {
print "Daynight mode was on NIGHT, changing daynight mode to DAY.\n";
}
# change daynight mode to day
`/usr/sbin/asterisk -rx "database put DAYNIGHT C0 DAY"`;
sendAlert("Phones are back up, system changed back to Normal Mode.", "Recovery");
}
else {
if ($debug) {
print "Daynight mode was already on DAY, no need to change.\n";
}
}
}
# ---------------------------------------------------------- #
# Email out alert to user #
# ---------------------------------------------------------- #
sub sendAlert {
my $message = shift;
my $type = shift;
my $msg = MIME::Lite->new(
From => $alertfrom,
To => $alertto,
Subject => 'Internet/Power '.$type.', phones changed',
Type => 'text/plain',
Data => $message
);
$msg->send('smtp','localhost', Debug=>0 );
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment