#!/usr/bin/perl # check_email.pl - nagios plugin # # # Copyright (C) 2003 andrew fresh # # This program is free software; you can redistribute it and/or # modify it under the terms of the BSD License. # # Report bugs to: andrew@mad-techies.org # # 11.15.2003 Version 1.0 # # $RedRiver: check_email,v 1.2 2006/09/27 18:54:27 andrew Exp $ use POSIX; use lib "/usr/local/libexec/nagios" ; use utils qw($TIMEOUT %ERRORS &print_revision &support); use strict; use warnings; use diagnostics; use Net::SMTP; use Net::POP3; use Getopt::Long; Getopt::Long::Configure('bundling'); my $PROGNAME = "check_email"; my $status; my $state = "UNKNOWN"; my $answer = ""; my $opt_h ; my $opt_V ; my $hostname; my $smtp_server; my $from_address = "Nagios <>"; my $to_address; my $pop_server; my $pop_user; my $pop_password; my $wait_time = 1; # Just in case of problems, let's not hang Nagios $SIG{'ALRM'} = sub { print ("ERROR: No response from $hostname (alarm timeout)\n"); exit $ERRORS{"UNKNOWN"}; }; alarm($TIMEOUT); #Option checking $status = GetOptions( "V" => \$opt_V, "version" => \$opt_V, "h" => \$opt_h, "help" => \$opt_h, "H=s" => \$hostname, "hostname=s" => \$hostname, "S=s" => \$smtp_server, "smtpserver=s" => \$smtp_server, "P=s" => \$pop_server, "popserver=s" => \$pop_server, "t=s" => \$to_address, "to=s" => \$to_address, "f=s" => \$from_address, "from=s" => \$from_address, "u=s" => \$pop_user, "username=s" => \$pop_user, "p=s" => \$pop_password, "password=s" => \$pop_password, "w:i" => \$wait_time, "wait=i" => \$wait_time, ); if ($status == 0) { print_help() ; exit $ERRORS{'OK'}; } if ($opt_V) { print_revision($PROGNAME,'$Revision: 1.3 $ '); exit $ERRORS{'OK'}; } if ($opt_h) { print_help(); exit $ERRORS{'OK'}; } if (! utils::is_hostname($hostname) || ! defined $pop_user || ! defined $pop_password ){ usage(); exit $ERRORS{"UNKNOWN"}; } ### Actions go here my $subject = scalar localtime; my $received_subject; $smtp_server ||= $hostname; $pop_server ||= $hostname; $to_address ||= ( $pop_user =~ /\@/ ) ? $pop_user : "$pop_user\@$smtp_server"; my $smtp = Net::SMTP->new($smtp_server) || done('CRITICAL', "Couldn't connect to SMTP Server $smtp_server"); $smtp->mail($from_address) || done('WARNING', "Couldn't specify smtp from address $from_address on SMTP server $smtp_server"); $smtp->to($to_address) || done('CRITICAL', "Couldn't specify smtp to address $to_address on SMTP server $smtp_server"); $smtp->data() || done('CRITICAL', "Couldn't begin data on SMTP server $smtp_server"); $smtp->datasend("To: $to_address\n") || done('CRITICAL', "Couldn't smtp datasend To: header on SMTP server $smtp_server"); $smtp->datasend("From: $from_address\n") || done('CRITICAL', "Couldn't smtp datasend From: header on SMTP server $smtp_server"); $smtp->datasend("Subject: $subject\n") || done('CRITICAL', "Couldn't smtp datasend Subject: header on SMTP server $smtp_server"); $smtp->datasend("\n") || done('CRITICAL', "Couldn't smtp datasend blank line on SMTP server $smtp_server"); $smtp->datasend("A simple test message sent on $subject\n") || done('CRITICAL', "Couldn't smtp datasend message body on SMTP server $smtp_server"); $smtp->dataend() || done('CRITICAL', "Couldn't smtp dataend on SMTP server $smtp_server"); $smtp->quit || done('CRITICAL', "Couldn't smtp quit on SMTP server $smtp_server"); sleep $wait_time; my $pop = Net::POP3->new($pop_server) || done('CRITICAL', "Couldn't connect to POP server $pop_server"); $pop->user($pop_user) || done('CRITICAL', "POP username $pop_user failed on POP server $pop_server"); $pop->pass($pop_password) || done('CRITICAL', "POP password for $pop_user failed on POP server $pop_server"); my $messages = $pop->list() || done('CRITICAL', "Couldn't get message list from POP server $pop_server"); foreach my $message (sort { $a <=> $b } keys %{ $messages } ) { #print $message; #print "\n"; my $lines = $pop->get($message) || done('CRITICAL', "Couldn't get message $message from POP server $pop_server"); foreach my $line ( @{ $lines } ) { #print $line; if ( $line =~ /^Subject:\s+(.*)$/o ) { $received_subject = $1; last; } } $pop->delete($message) || done('CRITICAL', "Couldn't delete message $message from POP server $pop_server"); } $pop->quit() || done('CRITICAL', "Couldn't quit from POP server $pop_server"); #print "Subject: $subject\n"; #print "Received: $received_subject\n"; if (not defined $received_subject) { $state = "WARNING"; $answer = "No subject line received"; } elsif ($subject eq $received_subject) { $state = "OK"; $answer = "Sent and received message correctly"; } else { $state = "WARNING"; $answer = "Subject lines did not match wrong message received"; } done($state, $answer); sub done { my $state = shift; my $answer = shift; print ("$state: $answer"); exit $ERRORS{$state}; } sub usage { print "\nMissing arguments!\n"; print "\n"; print "check_email -H -u -p \n"; print "Copyright (C) 2003 andrew fresh\n"; print "\n\n"; support(); exit $ERRORS{"UNKNOWN"}; } sub print_help { print "check_email plugin for Nagios monitors operational \n"; print "status of email flow on the target host.\n"; print "It sends an e-mail to a test user, and then checks \n"; print "a POP account. Failing at any point during if there is \n"; print "a problem. It gives a WARNING if the mail is not received \n"; print "in time, and gives a CRITICAL if it cannot connect to any \n"; print "services. Do not use an account that you want to receive \n"; print "mail from. This program will delete ALL mail in the mailbox \n"; print "that you specify."; print "\n"; print "\nUsage:\n"; print " -H (--hostname) Hostname to query - (required)\n"; print " -u (--username) Username whose mail to check - (required)\n"; print " -p (--password) Password for user - (required)\n"; print " -P (--popserver) Server to check mail on, defaults to --hostname\n"; print " -S (--smtpserver) Server to send mail to, defaults to --hostname\n"; print " -t (--to) Address to send mail to, defaults to --username\@--hostname\n"; print " -f (--from) Address to send mail from, defaults to Nagios <>\n"; print " -w (--wait) Time (in seconds) to wait between sending the mail and checking for it, defaults to 1 second. \n"; print_revision($PROGNAME, '$Revision: 1.3 $'); }