Click here to Skip to main content
15,867,330 members
Articles / Programming Languages / Perl

Monitor Your Website Performance and Uptime with Perl

Rate me:
Please Sign up or sign in to vote.
4.00/5 (8 votes)
3 Aug 20042 min read 74.9K   13   12
Receive email notification if your website is down or slow

Sample Image - backlog.gif

Introduction

Be notified if your website is down or slow.

What It Does

This simple Perl script is designed to run on a schedule. If you are on Windows, you can use the Windows Task Scheduler, if you are on Linux, you can run schedule it as a Cron job. The script will check a website, actually "grab" the default page, then record how long this takes. You can then receive an email if the page is down, or if the response time is greater than what you have set.

How It Works

The script has 3 files:

  • URLS.txt - This file holds all the URLs (websites) that you wish to check. Each URL is on one line. This makes it easy to update and change your list without having to dig into the Perl script.
  • SMTP_Settings.txt - This file holds the SMTP settings that the script should use to send the notifications, as well as who to send it to. Again, these settings are located out of the script in a text file to make things easier to change.
  • responser.pl - Is the script that does the task of checking the website and attempting to grab the default file. You do need to set your minimum response time that is acceptable to you within the script itself. Keep in mind that if the connection you are running the script from is slow, you may also hit your response time limit, thus triggering the email.

Other files created by the script:

The script will also create an error file, where any reported errors are written to. This is handy for troubleshooting, this file can be deleted at anytime.

The script will also create a daily log file each time it's run. The daily log file will append, so each day you'll have a record of what happened.

The complete script with the readme file can be downloaded for free from here.

Sample Output From the Log File

******************************************************
+--------------------------------------------------------------------------------+
|                              Time: 23:26:31                                    |
|          HOST                                  STATUS       RESPONSE           |
+--------------------------------------------------------------------------------+
| http://www.yahoo.com/                          ACCESSED   Response 1 seconds   |
| http://www.hotmail.com/                        ACCESSED   Response 1 seconds   |
| http://www.ebay.com/                           ACCESSED   Response 1 seconds   |
| http://www.example.com/                        ACCESSED   Response 0 seconds   |
| http://www.not/ a real site.com                WRONG       N/A                 |
+--------------------------------------------------------------------------------+
|                              Time: 23:30:17                                    |
|          HOST                                  STATUS       RESPONSE           |
+--------------------------------------------------------------------------------+
| http://www.yahoo.com/                          ACCESSED   Response 0 seconds   |
| http://www.hotmail.com/                        ACCESSED   Response 0 seconds   |
| http://www.ebay.com/                           ACCESSED   Response 1 seconds   |
| http://www.example.com/                        ACCESSED   Response 0 seconds   |
| http://www.not/ a real site.com                WRONG       N/A                 |
+--------------------------------------------------------------------------------+
|                              Time: 23:31:26                                    |
|          HOST                                  STATUS       RESPONSE           |
+--------------------------------------------------------------------------------+
| http://www.yahoo.com/                          ACCESSED   Response 0 seconds   |
| http://www.hotmail.com/                        ACCESSED   Response 1 seconds   |
| http://www.ebay.com/                           ACCESSED   Response 0 seconds   |
| http://www.example.com/                        ACCESSED   Response 0 seconds   |
| http://www.not/ a real site.com                WRONG       N/A                 |
PERL
#!/usr/bin/perl
use warnings;
use strict;
use Tie::File;
use Net::SMTP;
use LWP::UserAgent;

#################################################################
#             Program  Settings
#
my $error_log  = 'Responser_errors.txt';# File to store errors of program
my $input_file = 'urls.txt';       # From where program will read WEB Addresses
my $smtp_file  = 'SMTP_Settings.txt';   # File for SMTP Settings
my $response_limit = 12; #In Seconds    # Positively diggit -> SendMail;
                                        #        0 -> will not send mail
my $send_mail  = 1;                # my $send_mail  = 1; ->SMTP option is ON,
                                   # my $send_mail  = 0; ->SMTP option is OFF
##################################################################
#                      END OF SETTINGS
# Do not edit bellow if you dont understand it.
##################################################################
die "File $input_file is not exist\n" unless (-e $input_file);
die "SMTP is ON, but file $smtp_file is not exist\n" unless (-e $smtp_file);
my $localtime     = localtime;
our @errors;
my ($day,$month,$date,$hour,$year) = split /\s+/,scalar localtime;
my $output_file = 'report-'.$date.'.'.$month.'.'.$year.'.txt';
my ($smtp_host,$recipient,$reverse_path, @all_addr) = ();
tie @all_addr, 'Tie::File', 
    $input_file or error("Cant open $input_file to read addresses");
if (-e $output_file) {
   open(OUT,">> $output_file") 
      or error("Cant open exist file $output_file for append");
} else {
   open(OUT,"> $output_file") 
      or error("Cant open new file $output_file for writting");
}
my @smtp_settings;
if ($^O =~ /win/i) {
        tie @smtp_settings, 'Tie::File', $smtp_file,, 
            recsep => "\012" 
            or error("Cant open $smtp_file to read SMTP settings");
} else {
tie @smtp_settings, 'Tie::File', $smtp_file,autochomp => '0' 
    or error("Cant open $smtp_file to read SMTP settings");
}
for (@smtp_settings) {
   chomp;
   next if /^#/;
   #next if /^$/;
 if (/^(\w+)\s=\s'(\S+)'/) {
   $smtp_host     = $2 if ($1 eq 'SMTPHost');
   $recipient     = $2 if ($1 eq 'Recipient');
   $reverse_path  = $2 if ($1 eq 'Reverse');
 }
}
print OUT "\n+" .('-' x 84) . "+\n";
print OUT   "|", ' ' x 30,"Time: $hour",' ' x 40,"|\n";
print OUT   "|",' 'x 10,'HOST',' ' x 37,'STATUS',' ' x 7, 
                               "RESPONSE            |\n";
print OUT   "+" .('-' x 84) . "+\n";
for (0 .. $#all_addr) {
 chop $all_addr[$_] if ($all_addr[$_] =~ /\s+$/);
 next if ($all_addr[$_]  eq "");
 if ($all_addr[$_] =~ /^http:\/\/\S+\.\w{2,4}$/) {  
      #address will beginnig with http://,next some string
      # finish with point and 2 to 4 letters
   check_url($all_addr[$_]);    #call subroutine check_url()
 } else {
   my $out_format = sprintf "| %-50.50s %-10s  %-20s|\n", 
                           $all_addr[$_], "WRONG", "N/A";
   printf OUT $out_format;
   printf $out_format;
         push @errors, "$all_addr[$_] is WRONG Address.";
 }
}

my $err = join "\015\012",@errors;
my $err_num = scalar @errors;  # How match DOWN + WRONG Sites have
$send_mail = 0 unless $err_num;
untie @all_addr or error("Unable to close file $input_file");
if ($send_mail) {
 my $smtp = Net::SMTP->new($smtp_host,
                    -Debug=>1,
                    -Timeout=>20,
                    -Hello=>"$smtp_host") 
                        or error("Cant connect to $smtp_host");
# Begin Compare mail message
my $msg = <<__END_OF_MAIL__;
To: $recipient
Subject: $err_num Error Sites | $localtime .
$localtime
$err

__END_OF_MAIL__
# End Compare

 $smtp->mail("$reverse_path") 
       or error("Failed to specify a reverse-path");#  If all is OK
 $smtp->to($recipient) 
       or error("Failed to specify a recipient");   #  that will
 $smtp->data([$msg]) 
       or error("Failed to send a message");     #  send mail
 $smtp->quit or error("Failed to quit");         #  to You
} else {
  print "Send Mail is OFF\n" if $err_num; # If you do not wish to receive mail
}

close OUT or error("Unable to close file $output_file");
print "\nProcess FINISH\n";

sub check_url {  # subroutine who check given URL
    my $target = $_[0];
        my $ua = LWP::UserAgent->new;
        $ua->agent("$0/0.1 " . $ua->agent);
        my $req = HTTP::Request->new(GET => "$target");
        $req->header('Accept' => 'text/html');          #Accept HTML Page
        # send request
        my $start = time;      # Start timer
        my $res = $ua->request($req);
        # check the outcome
        if ($res->is_success) {
        # Success....all content of page has been received
          my $time = time;     # End timer
          my $out_format;
          $time = ($time - $start); # Result of timer
          if ($response_limit && ($response_limit <= $time)) {
             push(@errors, "Slow response from $target\: $time seconds");
             $out_format = sprintf "| %-50.50s %-10s %-20s |\n", 
                      $target, "SLOW", "Response $time seconds";
          } else {
             $out_format = sprintf "| %-50.50s %-10s %-20s |\n", 
                  $target, "ACCESSED", "Response $time seconds";
          }
          print OUT $out_format; # write to file
          print $out_format;     # print to console
        } else { # Error .... Site is DOWN and script send e-mail to you..
          my $out_format = sprintf "| %-50.50s %-10s %-20s |\n", 
                                          $target, "DOWN", " N/A";
          push(@errors, "$target is DOWN." . $res->status_line) 
                           or error("Cannot push error for DOWN");
          print OUT $out_format; # write to file
          print $out_format;     # print to console
    }
}
sub error {      # subroutine who print in Error Log
  my $error_msg = shift;
  open ERR,">> $error_log" 
       or die "Cannot open log file $error_log : $!\n";
  print ERR "$localtime\: $error_msg : $!\n";
  close ERR or die "Cannot close log file $error_log : $!\n";
}

License

This article has no explicit license attached to it, but may contain usage terms in the article text or the download files themselves. If in doubt, please contact the author via the discussion board below.

A list of licenses authors might use can be found here.


Written By
United States United States
Live in Michigan, USA

Comments and Discussions

 
QuestionNew to perl and looking to use this script Pin
Member 148535344-Jun-20 5:35
Member 148535344-Jun-20 5:35 
QuestionURL status is down Pin
Member 473212918-Mar-12 23:39
Member 473212918-Mar-12 23:39 
AnswerSMTP Authentication patch Pin
adx44216-Feb-12 2:20
adx44216-Feb-12 2:20 
Questionsend email notification for a specific error message appearing on the website Pin
mohankz27-Apr-09 21:21
mohankz27-Apr-09 21:21 
Generalquerystring value in url Pin
sankarmca1-Nov-06 18:08
sankarmca1-Nov-06 18:08 
GeneralMonitor Script does not send alert email Pin
sonny227-Jan-06 11:20
sonny227-Jan-06 11:20 
GeneralCouple ideas Pin
dmoses18-Apr-04 7:11
dmoses18-Apr-04 7:11 
GeneralRe: Couple ideas Pin
Anonymous26-Sep-05 17:36
Anonymous26-Sep-05 17:36 
Generalthoughts... Pin
l a u r e n7-Apr-04 10:32
l a u r e n7-Apr-04 10:32 
GeneralRe: thoughts... Pin
aa2max7-Apr-04 11:04
aa2max7-Apr-04 11:04 
GeneralRe: thoughts... Pin
l a u r e n7-Apr-04 11:11
l a u r e n7-Apr-04 11:11 
GeneralRe: thoughts... Pin
darthzep11-Mar-09 9:02
darthzep11-Mar-09 9:02 

General General    News News    Suggestion Suggestion    Question Question    Bug Bug    Answer Answer    Joke Joke    Praise Praise    Rant Rant    Admin Admin   

Use Ctrl+Left/Right to switch messages, Ctrl+Up/Down to switch threads, Ctrl+Shift+Left/Right to switch pages.