# Register the function the plugin registry
$PLUGINS{'nut'} = \&check_nut;

# This routine check NUT (http://www.networkupstools.org) a UPS monitoring
# system.
#
# This plugin is currently known to work against NUT 0.45.5 (which is
# packaged for Debian Stable).
#
# Configuration looks like:
#
# 'pluto.actrix.co.nz' =>        { services => 'ping: ntp ssh dns nut',
#                                  contact  => 'puck',
#                                  nut      => ['rack09-apc3000-1'] },
#
# Where the nut parameter is a list of UPS's to monitor.

use Spong::SafeExec qw(safe_exec);

# This can be overridden in spong.conf.
my ($client) = $NUT_CLIENT || 'upsc';

sub check_nut { 
  my( $host ) = @_;
  my( $color, $summary, $message ) = ( "green", "NUT ok", "", "" );

  my ( @problems ) = ();

  for my $ups (@{ $HOSTS{$host}{'nut'} }) {
    my ($cmd) = "$client $ups\@$host";
    $message = safe_exec($cmd);

    if ($message =~ /^Unable to get variable list - Receive timeout/) {
      $color = 'yellow' unless $color eq 'red';
      push @problems, "Timeout on query for $ups";
      next;
    }

    for (split("\n", $message)) {
      my ($key, $value) = split(/:\s+/);

      if ($key eq 'STATUS'  ) {
        if ($value =~ /OB/) {
          $color = 'red';
  
          if ($value =~ /LB/) {
            push @problems, "$ups on battery and battery is low";
          } else {
            push @problems, "$ups on battery";
          }
        } else {
          if ($value =~ /OFF/) {
            $color = 'yellow';
            push @problems, "$ups is off";
          }

          if ($value =~ /LB/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups has a low battery";
          }

          if ($value =~ /TRIM/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups trimming incoming voltage";
          }

          if ($value =~ /BOOST/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups boosting incoming voltage";
          }

          if ($value =~ /OVER/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups overloaded";
          }

          if ($value =~ /RB/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups battery needs replacing";
          }

          if ($value =~ /FSD/) {
            $color = 'yellow' unless $color eq 'red';
            push @problems, "$ups in forced shutdown mode";
          }
        }
      }
    }
  }

  if (scalar(@problems) == 1) {
    $summary = $problems[0];
    $message = "$summary\n" . ('-' x 80) . "\n$message";
  } elsif (scalar(@problems) > 1) {
    $summary = "multiple problems";
    $message = join("\n", @problems) . "\n" . ('-' x 80) . "\n$message";
  }

  &debug( "nut - $host - $color, $summary" );
  return( $color, $summary, $message );
}

1;
