#!/usr/bin/perl
# $Id: check_wfrog 211 2011-11-17 01:16:53Z mwall $
# check_wfrog - nagios plugin to monitor wfrog weather station
#   by Matthew Wall
#
# Copyright (c) 2011 Matthew Wall, all rights reserved
#
# Permission to use, copy, modify, and distribute this software for any
# purpose with or without fee is hereby granted, provided that the above
# copyright notice and this permission notice appear in all copies.
#
#
# This plugin checks the last entry of the wfrog csv data file and compares
# that with the current time.  If the delta is greater than the warning or
# critical threshold, then warning or critical is reported.  The delta is
# reported as performance data.  If not warning or critical, the weather data
# are also reported as performance data.
#
# Revision History
#   0.3 16nov11
#     * do not report weather data if warn or critical
#   0.2 14nov11
#     * record time since last update as perfdata
#     * do not drop last metric
#     * remove extraneous newline
#   0.1 14nov11 initial release
#
# Prerequisites
#   wfrog weather data collection system

use Time::Local;
use strict;

my $STATE_OK = 0;
my $STATE_WARN = 1;
my $STATE_CRIT = 2;
my $STATE_UNKNOWN = 3;
my $state = $STATE_UNKNOWN;
my @STATESTR = ( 'OK', 'WARN', 'CRITICAL', 'UNKNOWN' );

my $PROG = 'check_wfrog';

# location of the wfrog csv data file
my $datafn = '/var/lib/wfrog/wfrog.csv';

# minutes without update until we warn
my $mwarn = 30;

# minutes without update until we go critical
my $mcrit = 120;

# number of metrics in a single row in the csv file.  wfrog 0.8.1 defines the
# following metrics, in this order, when it emits csv data for a ws2080
# weather station.
my @metrics = ('timestamp',
               'localtime',
               'temp',
               'hum',
               'wind',
               'wind_dir',
               'wind_gust',
               'wind_gust_dir',
               'dew_point',
               'rain',
               'rain_rate',
               'pressure',
               'uv_index');
# these metrics were added my mwall for a ws2080 weather station to record
# the internal temperature and humidity.  if you have not hacked wfrog, then
# you do not need these.
#push @metrics, 'temp_in','hum_in';

while($ARGV[0]) {
    my $arg = shift;
    if ($arg eq '--data-file') {
        $datafn = shift;
    } elsif ($arg eq '-w') {
        $mwarn = shift;
    } elsif ($arg eq '-c') {
        $mcrit = shift;
    } elsif ($arg ne q()) {
        if ($arg ne '--help') {
            print "unknown argument '$arg'\n";
        }
        print "usage: $PROG [options]\n";
        print "options include:\n";
        print "  --help\n";
        print "  --data-file filename        $datafn\n";
        print "  -w minutes                  $mwarn\n";
        print "  -c minutes                  $mcrit\n";
        exit $state;
    }
}

if ($mwarn > $mcrit) {
    print "$STATESTR[$state] - warn threshold must be less than critical threshold\n";
    exit $state;
}

my $msg = q();
my $perfdata = q();
my $now = time;
my $result = `tail -1 $datafn`;
chop($result);
my (@values) = split(',', $result);
if ($#values == $#metrics) {
    my $deltaT = ($now - $values[0]) / 60;
    my $mstr = sprintf("%.0f", $deltaT);
    $msg = "last update was $values[1] ($mstr minutes ago)";
    $perfdata .= " lastupdate=$deltaT;$mwarn;$mcrit";

    if ($deltaT > $mcrit) {
        $state = $STATE_CRIT;
    } elsif ($deltaT > $mwarn) {
        $state = $STATE_WARN;
    } else {
        $state = $STATE_OK;
        for (my $i=0; $i<$#values+1; $i++) {
            if ($values[$i] ne q() &&
                $metrics[$i] ne 'timestamp' && $metrics[$i] ne 'localtime') {
                $perfdata .= " $metrics[$i]=$values[$i]";
            }
        }
    }
} else {
    $msg = "cannot parse values from $datafn";
}

print "$STATESTR[$state] - $msg";
print "|$perfdata" if $perfdata ne q();
print "\n";

exit $state;
