1
0
Fork 0
mirror of https://github.com/munin-monitoring/contrib.git synced 2025-07-22 14:16:00 +00:00
This commit is contained in:
Steve Schnepp 2012-01-12 15:31:22 +01:00
commit a2fead05ca
7 changed files with 2136 additions and 454 deletions

234
plugins/other/boinc_credit Executable file
View file

@ -0,0 +1,234 @@
#!/usr/bin/perl
# -*- cperl -*-
=head1 NAME
boinc_credit - Munin plugin to monitor BOINC credit for a user
=head1 APPLICABLE SYSTEMS
Any
=head1 CONFIGURATION
All that should be needed is to add the following to your config:
[boinc_credit]
env.cpid 1234abcd....
Where the value is your Cross Project ID (CPID).
=head1 MAGIC MARKERS
#%# family=auto contrib
#%# capabilities=autoconf
=head1 VERSION
1.0
=head1 AUTHOR
Paul Saunders <darac+munin@darac.org.uk>
=cut
use strict;
use warnings;
use lib $ENV{'MUNIN_LIBDIR'};
use Munin::Plugin;
my $CPID = $ENV{cpid};
my $STATSURL = $ENV{statsurl}
|| "http://boinc.netsoft-online.com/get_user.php?cpid=$CPID";
my $TICK = $ENV{tick} || 60; # minutes
my $ret;
if ( !eval "require XML::Simple;" ) {
$ret += "Could not load XML::Simple; ";
}
if ( !eval "require LWP::Simple;" ) {
$ret += "Could not load LWP::Simple; ";
}
if ( defined $ARGV[0] and $ARGV[0] eq 'autoconf' ) {
# Can't auto configure at the moment.
# At least, until we can calculate CPID
print "no\n";
exit 0;
}
my $lastread;
sub save_data {
my @projdata = @_;
# Do we need to save this data?
if ( !defined $lastread or time >= $lastread + ( $TICK * 60 ) ) {
$lastread = time;
my @save_vector;
push @save_vector, $lastread;
foreach (@projdata) {
# Serialise the hash
my @tempbuf;
foreach my $key ( keys %{$_} ) {
push @tempbuf, $key . '¬' . $_->{$key};
}
push @save_vector, join( '^^', @tempbuf );
}
save_state(@save_vector);
}
}
sub load_data {
# Bring the data back in
my @save_vector = restore_state();
# Read the timestamp, Do we need to refresh the data?
$lastread = shift @save_vector;
my @projarray;
foreach (@save_vector) {
my $hashref;
foreach ( split /\^\^/ ) {
my ( $key, $value ) = split /¬/;
$hashref->{$key} = $value;
}
push @projarray, $hashref;
}
if ( !defined $lastread or time >= ( $lastread + ( $TICK * 60 ) ) ) {
# Data is stale
eval {
# Fetch the XML
my $content;
unless ( defined( $content = LWP::Simple::get $STATSURL) ) {
die "Could not get $STATSURL";
}
my $xmlref = XML::Simple::XMLin( $content, ForceArray => 1 );
my @temparray;
foreach ( @{ $xmlref->{project} } ) {
my $temphash;
$temphash->{name} = $_->{name}[0];
$temphash->{id} = $_->{project_id}[0];
$temphash->{credit} = $_->{total_credit}[0];
$temphash->{creditfract} =
$_->{total_credit}[0] / $xmlref->{total_credit}[0];
$temphash->{totalcredit} = $xmlref->{total_credit}[0];
$temphash->{rank} = $_->{project_rank_total_credit}[0];
push @temparray, $temphash;
}
# If the above threw an error, we won't overwrite the old data
@projarray = @temparray;
1;
} or do {
print $@;
}
}
return @projarray;
}
# Project Colours from http://boinc.netsoft-online.com/e107_plugins/forum/forum_viewtopic.php?3
sub rgb($$$) {
return sprintf( '%02x%02x%02x', shift, shift, shift );
}
my %project_colour = (
'climatepredition.net' => rgb( 0, 139, 69 ),
'Predictor@Home' => rgb( 135, 206, 235 ),
'SETI@home' => rgb( 65, 105, 225 ),
'Einstein@Home' => rgb( 255, 165, 0 ),
'Rosetta@home' => rgb( 238, 130, 238 ),
'PrimeGrid' => rgb( 205, 197, 191 ),
'LHC@home' => rgb( 255, 127, 80 ),
'World Community Grid' => rgb( 250, 128, 114 ),
'BURP' => rgb( 0, 255, 127 ),
'SZTAKI Desktop Grid' => rgb( 205, 79, 57 ),
'uFluids' => rgb( 0, 0, 0 ),
'SIMAP' => rgb( 143, 188, 143 ),
'Folding@Home' => rgb( 153, 50, 204 ),
'MalariaControl' => rgb( 30, 144, 255 ),
'The Lattice Project' => rgb( 0, 100, 0 ),
'Pirates@Home' => rgb( 127, 255, 0 ),
'BBC Climate Change Experiment' => rgb( 205, 173, 0 ),
'Leiden Classical' => rgb( 140, 34, 34 ),
'SETI@home Beta' => rgb( 152, 245, 255 ),
'RALPH@Home' => rgb( 250, 240, 230 ),
'QMC@HOME' => rgb( 144, 238, 144 ),
'XtremLab' => rgb( 130, 130, 130 ),
'HashClash' => rgb( 255, 105, 180 ),
'cpdn seasonal' => rgb( 255, 255, 255 ),
'Chess960@Home Alpha' => rgb( 165, 42, 42 ),
'vtu@home' => rgb( 255, 0, 0 ),
'LHC@home alpha' => rgb( 205, 133, 63 ),
'TANPAKU' => rgb( 189, 183, 107 ),
'other' => rgb( 255, 193, 37 ),
'Rectilinear Crossing Number' => rgb( 83, 134, 139 ),
'Nano-Hive@Home' => rgb( 193, 205, 193 ),
'Spinhenge@home' => rgb( 255, 240, 245 ),
'RieselSieve' => rgb( 205, 183, 158 ),
'Project Neuron' => rgb( 139, 58, 98 ),
'RenderFarm@Home' => rgb( 210, 105, 30 ),
'Docking@Home' => rgb( 178, 223, 238 ),
'proteins@home' => rgb( 0, 0, 255 ),
'DepSpid' => rgb( 139, 90, 43 ),
'ABC@home' => rgb( 222, 184, 135 ),
'BOINC alpha test' => rgb( 245, 245, 220 ),
'WEP-M+2' => rgb( 0, 250, 154 ),
'Zivis Superordenador Ciudadano' => rgb( 255, 239, 219 ),
'SciLINC' => rgb( 240, 248, 255 ),
'APS@Home' => rgb( 205, 91, 69 ),
'PS3GRID' => rgb( 0, 139, 139 ),
'Superlink@Technion' => rgb( 202, 255, 112 ),
'BRaTS@Home' => rgb( 255, 106, 106 ),
'Cosmology@Home' => rgb( 240, 230, 140 ),
'SHA 1 Collision Search' => rgb( 255, 250, 205 ),
);
if ( defined $ARGV[0] and $ARGV[0] eq 'config' ) {
if ($ret) {
print $ret;
exit 1;
}
my @projdata = load_data();
print <<EOF;
graph_args --base 1000 --logarithmic
graph_vlabel Cobblestones
graph_category boinc
graph_title BOINC Total Credit
EOF
foreach ( sort { $a->{id} <=> $b->{id} } @projdata ) {
my $fieldname = 'proj' . $_->{id};
print <<EOF;
$fieldname.label $_->{name}
$fieldname.type GAUGE
$fieldname.info Total Credit for project $_->{name}
EOF
if ( exists $project_colour{ $_->{name} } ) {
print "$fieldname.colour $project_colour{$_->{name}}\n";
}
}
save_data(@projdata);
exit 0;
}
my @projdata = load_data();
foreach ( sort { $a->{id} <=> $b->{id} } @projdata ) {
my $fieldname = 'proj' . $_->{id};
print "$fieldname.value $_->{credit}\n";
printf "$fieldname.extinfo %.2f%% of Total Credit (%.2f out of %.2f)\n",
$_->{creditfract} * 100, $_->{credit}, $_->{totalcredit};
}
save_data(@projdata);
exit 0;

View file

@ -226,6 +226,7 @@ if ( (defined $ARGV[0]) && ($ARGV[0] eq "config") ) {
print "graph_category BOINC\n"; print "graph_category BOINC\n";
print "graph_args --base 1000 -l 0\n"; print "graph_args --base 1000 -l 0\n";
print "graph_vlabel BOINC applications\n"; print "graph_vlabel BOINC applications\n";
print "graph_total Total\n";
# First project is AREA, next are STACK # First project is AREA, next are STACK
# Not nice, but fast: # Not nice, but fast:

View file

@ -43,11 +43,12 @@ This configuration section shows the defaults of the plugin:
env.tick 6 env.tick 6
env.currency £ env.currency £
env.rate1 13.9 env.rate1 13.9
env.rate1qty 900 nenv.rate1qty 900
env.rate2 8.2 env.rate2 8.2
env.nightrate 0 env.nightrate 0
env.nighthours 23:30-06:30 env.nighthours 23:30-06:30
env.standingcharge 0.0 env.standingcharge 0.0
env.metertype CC128
The configuration can be broken down into the following subsections: The configuration can be broken down into the following subsections:
@ -101,16 +102,20 @@ The time period for which C<env.nightrate> applies. This should be of the form C
The standing charge in hundreths of a C<env.currency> per month. If you do not have a standing charge, set this to 0. The standing charge in hundreths of a C<env.currency> per month. If you do not have a standing charge, set this to 0.
=item env.metertype
The type of the meter. Currently "CC128" and "CC02" are supported.
=back =back
=head1 MAGIC MARKERS =head1 MAGIC MARKERS
#%# family=manual contrib #%# family=auto contrib
#%# capabilities=multigraph #%# capabilities=multigraph autoconf
=head1 AUTHOR =head1 AUTHOR
Paul Saunders L<darac@darac.org.uk> Paul Saunders L<darac+munin@darac.org.uk>
=cut =cut
@ -118,14 +123,12 @@ use strict;
use warnings; use warnings;
use utf8; use utf8;
use Munin::Plugin; use Munin::Plugin;
use Data::Dump qw{pp};
need_multigraph(); need_multigraph();
my $device_node = $ENV{device} || "/dev/ttyUSB0"; my $device_node = $ENV{device} || "/dev/ttyUSB0";
my $baud_rate = $ENV{baud} || "2400"; # or 9600 or 57600 my $baud_rate = $ENV{baud} || "2400"; # or 9600 or 57600
my $tick_rate = $ENV{tick} || "6"; my $tick_rate = $ENV{tick} || "6";
# Tick_Rate is how long to consider data valid for (in seconds) # Tick_Rate is how long to consider data valid for (in seconds)
# Costs # Costs
@ -136,6 +139,9 @@ my $rate2 = $ENV{rate2} || "8.2"; # in pence/cents
my $nightrate = $ENV{nightrate} || "0"; # 0 = disabled my $nightrate = $ENV{nightrate} || "0"; # 0 = disabled
my $nighthours = $ENV{nighthours} || "23:30-06:30"; my $nighthours = $ENV{nighthours} || "23:30-06:30";
my $standingcharge = $ENV{standingcharge} || "0.0"; # pence/cents per month my $standingcharge = $ENV{standingcharge} || "0.0"; # pence/cents per month
my $metertype = $ENV{metertype} || "CC128"; # or "CC02"
my $MUNIN_DEBUG = $ENV{MUNIN_DEBUG} || 0; # Set by munin-run
my $ret; my $ret;
if ( !eval "require XML::Simple;" ) { if ( !eval "require XML::Simple;" ) {
@ -168,6 +174,10 @@ sub save_data {
if ( !@lastread if ( !@lastread
or time >= Time::Local::timelocal(@lastread) + ($tick_rate) ) or time >= Time::Local::timelocal(@lastread) + ($tick_rate) )
{ {
print "# Saving Data (Data is "
. ( time - Time::Local::timelocal(@lastread) )
. " seconds old)\n"
if $MUNIN_DEBUG;
@lastread = localtime(time); @lastread = localtime(time);
my @save_vector; my @save_vector;
@ -198,12 +208,27 @@ sub load_data {
{ {
# Data is stale # Data is stale
print "# Data is stale ("
. ( time - Time::Local::timelocal(@lastread) )
. " seconds). Re-reading device\n"
if $MUNIN_DEBUG;
eval { eval {
# Fetch the XML # Fetch the XML
my @temparray = collect_cc128_data( $device_node, $baud_rate ); my @temparray;
if ( $metertype eq "CC128" ) {
@temparray = collect_cc128_data( $device_node, $baud_rate );
}
elsif ( $metertype eq "CC02" ) {
@temparray = collect_cc02_data( $device_node, $baud_rate );
}
else {
die "Unknown meter type $metertype.";
}
# Read the time so we know whether to reset daily/monthly/yearly counters # Read the time so we know whether to reset
# daily/monthly/yearly counters
my @now = localtime(time); my @now = localtime(time);
my %is_new; my %is_new;
$is_new{daily} = ( $now[3] != $lastread[3] ) ? 1 : 0; $is_new{daily} = ( $now[3] != $lastread[3] ) ? 1 : 0;
@ -222,6 +247,8 @@ sub load_data {
if ( $is_new{$period} ) { if ( $is_new{$period} ) {
# Start of a new period, reset the counter # Start of a new period, reset the counter
print "# Start of a new $period period." .
" Resetting counter\n" if $MUNIN_DEBUG;
$temparray[$i]->{data}[$j]->{$period} = 0; $temparray[$i]->{data}[$j]->{$period} = 0;
} }
else { else {
@ -266,9 +293,11 @@ sub is_night_rate {
if ( $now_time >= $start_time if ( $now_time >= $start_time
or $now_time <= $stop_time ) or $now_time <= $stop_time )
{ {
print "# Night rate is ACTIVE\n" if $MUNIN_DEBUG;
return 1; return 1;
} }
else { else {
print "# Night rate is enabled, but NOT active\n" if $MUNIN_DEBUG;
return 0; return 0;
} }
} }
@ -279,34 +308,34 @@ The device will periodically output a string of XML. The string will be all on o
=head2 Classic format =head2 Classic format
Note: I can't find an official spec for this format so, for now, this plugin doesn't support it. As per L<http://cumbers.wordpress.com/2008/05/07/breakdown-of-currentcost-xml-output/>:
<msg> <msg>
<date> <date>
<dsb>00014</dsb> <dsb>00014</dsb> days since birth
<hr>14</hr> <hr>14</hr> the time
<min>07</min> <min>07</min>
<sec>07</sec> <sec>07</sec>
</date> </date>
<src> <src>
<name>CC02</name> <name>CC02</name> name of this device
<id>03280</id> <id>03280</id> communication channel for device
<type>1</type> <type>1</type> hardware version of the device
<sver>0.07</sver> <sver>0.07</sver> software version
</src> </src>
<ch1> <ch1>
<watts>00080</watts> <watts>00080</watts> value from the first channel clamp
</ch1> </ch1>
<ch2> <ch2>
<watts>00000</watts> <watts>00000</watts> value from the second channel clamp
</ch2> </ch2>
<ch3> <ch3>
<watts>00000</watts> <watts>00000</watts> value from the third channel clamp
</ch3> </ch3>
<tmpr>28.8</tmpr> <tmpr>28.8</tmpr> current temperature (degrees celsius)
<hist> <hist>
<hrs> <hrs>
<h02>000.0</h02> <h02>000.0</h02> total Kwh used in 2 hour blocks
<h04>000.1</h04> <h04>000.1</h04>
<h06>000.1</h06> <h06>000.1</h06>
<h08>000.0</h08> <h08>000.0</h08>
@ -321,7 +350,7 @@ Note: I can't find an official spec for this format so, for now, this plugin doe
<h26>000.0</h26> <h26>000.0</h26>
</hrs> </hrs>
<days> <days>
<d01>0000</d01> <d01>0000</d01> total Kwh used per day(s)
<d02>0000</d02> <d02>0000</d02>
<d03>0000</d03> <d03>0000</d03>
<d04>0000</d04> <d04>0000</d04>
@ -354,7 +383,7 @@ Note: I can't find an official spec for this format so, for now, this plugin doe
<d31>0000</d31> <d31>0000</d31>
</days> </days>
<mths> <mths>
<m01>0000</m01> <m01>0000</m01> total Kwh used per month(s)
<m02>0000</m02> <m02>0000</m02>
<m03>0000</m03> <m03>0000</m03>
<m04>0000</m04> <m04>0000</m04>
@ -368,7 +397,7 @@ Note: I can't find an official spec for this format so, for now, this plugin doe
<m12>0000</m12> <m12>0000</m12>
</mths> </mths>
<yrs> <yrs>
<y1>0000000</y1> <y1>0000000</y1> total Kwh used per year(s)
<y2>0000000</y2> <y2>0000000</y2>
<y3>0000000</y3> <y3>0000000</y3>
<y4>0000000</y4> <y4>0000000</y4>
@ -419,15 +448,18 @@ sub collect_cc128_data {
my %seen_sensors; my %seen_sensors;
while (<$ttydev>) { while (<$ttydev>) {
print "# Read from device: $_\n" if $MUNIN_DEBUG;
if (m{(<msg>.*</msg>)}) { if (m{(<msg>.*</msg>)}) {
my $xmlref = XML::Simple::XMLin( $1, KeepRoot => 1 ); my $xmlref = XML::Simple::XMLin( $1, KeepRoot => 1 );
my $sensor = $xmlref->{msg}->{sensor}; my $sensor = $xmlref->{msg}->{sensor};
print "# Parsing Sensor $sensor\n" if $MUNIN_DEBUG;
next unless defined $sensor; next unless defined $sensor;
if ( defined $seen_sensors{$sensor} ) { if ( defined $seen_sensors{$sensor} ) {
# We've seen this sensor before. # We've seen this sensor before.
# Time to stop reading data # Time to stop reading data
print "# Hello again, Sensor $sensor\n" if $MUNIN_DEBUG;
last; last;
} }
$seen_sensors{$sensor} = 1; $seen_sensors{$sensor} = 1;
@ -436,6 +468,56 @@ sub collect_cc128_data {
$temphash->{sensor} = $sensor; $temphash->{sensor} = $sensor;
$temphash->{temp} = $xmlref->{msg}->{tmpr}; $temphash->{temp} = $xmlref->{msg}->{tmpr};
my @temparr; my @temparr;
foreach my $key ( keys %{ $xmlref->{msg} } ) {
if ( $key =~ /ch(\d+)/ ) {
my $channel = $1;
my $unit = ( keys %{ $xmlref->{msg}->{"ch$channel"} } )[0];
my $val = $xmlref->{msg}->{"ch$channel"}->{$unit};
print "# Channel $channel, Unit $unit, Value $val\n"
if $MUNIN_DEBUG;
push @temparr,
{
"channel" => $channel,
"unit" => $unit,
"value" => $val
};
}
}
$temphash->{data} = \@temparr;
push @cc_data_arr, $temphash;
}
}
close($ttydev);
return @cc_data_arr;
}
sub collect_cc02_data {
# Function supplied by David Edmondson <dme@dme.org>
# Read data from the serial port
my ( $port, $baud ) = @_;
my $tty = Device::SerialPort->new($port) || die "Can't open $port: $!";
$tty->baudrate($baud) || die "Can't set serial baudrate";
$tty->parity("none") || die "Can't set serial parity";
$tty->databits(8) || die "Can't set serial databits";
$tty->handshake("none") || die "Can't set serial handshake";
$tty->write_settings || die "Can't set serial parameters";
open( my $ttydev, "<", $port ) || die "Can't open $port: $?";
my @cc_data_arr;
while (<$ttydev>) {
if (m{(<msg>.*</msg>)}) {
my $xmlref = XML::Simple::XMLin( $1, KeepRoot => 1 );
my $temphash;
$temphash->{sensor} = 0; # Only one sensor.
$temphash->{temp} = $xmlref->{msg}->{tmpr};
my @temparr;
foreach my $key ( keys %{ $xmlref->{msg} } ) { foreach my $key ( keys %{ $xmlref->{msg} } ) {
if ( $key =~ /ch(\d+)/ ) { if ( $key =~ /ch(\d+)/ ) {
my $channel = $1; my $channel = $1;
@ -452,6 +534,8 @@ sub collect_cc128_data {
$temphash->{data} = \@temparr; $temphash->{data} = \@temparr;
push @cc_data_arr, $temphash; push @cc_data_arr, $temphash;
last;
} }
} }
close($ttydev); close($ttydev);
@ -475,7 +559,7 @@ if ( defined $ARGV[0] and $ARGV[0] eq 'config' ) {
} }
elsif ( $unit != $key->{unit} ) { elsif ( $unit != $key->{unit} ) {
print STDERR print STDERR
"Conflicting units ($unit and $key->{unit}) on sensor $datum->{sensor}"; "# Conflicting units ($unit and $key->{unit}) on sensor $datum->{sensor}";
} }
} }
@ -512,7 +596,8 @@ ${fieldname}_n.type GAUGE
${fieldname}_n.min 0 ${fieldname}_n.min 0
${fieldname}_t.cdef ${fieldname}_n,UN,${fieldname},${fieldname},IF,3600,TRENDNAN ${fieldname}_t.cdef ${fieldname}_n,UN,${fieldname},${fieldname},IF,3600,TRENDNAN
EOF EOF
} else { }
else {
print "${fieldname}_t.cdef ${fieldname},3600,TRENDNAN\n"; print "${fieldname}_t.cdef ${fieldname},3600,TRENDNAN\n";
} }
} }

View file

@ -1,6 +1,41 @@
#!/bin/bash #!/bin/bash
: <<=cut
=head1 NAME
sa-learn - Munin plugin to monitor spamassasin bayes database size
=head1 APPLICABLE SYSTEMS
Any server running spamassassin
=head1 CONFIGURATION
This plugin assumes your Spamassassin database is in /var/lib/MailScanner.
If it's elsewhere (or you want to use a different database) you will need
a configuration such as:
[sa-learn]
env.BayesDir /path/to/bayes/directory/
user mail
(where 'user mail' refers to a user that can read the database).
=head1 MAGIC MARKERS
#%# family=contrib #%# family=contrib
=head1 VERSION
2
=head1 AUTHOR
Paul Saunders L<darac+munin@darac.org.uk>
=cut
#'
case $1 in case $1 in
config) config)
cat <<'EOM' cat <<'EOM'
@ -21,7 +56,7 @@ esac
## Print values ## Print values
BayesDir=${BayesDir:-/var/lib/MailScanner} BayesDir=${BayesDir:-/var/lib/MailScanner}
sa-learn --dbpath $BayesDir --dump magic 2>/dev/null | while read line sa-learn --dbpath $BayesDir/ --dump magic 2>/dev/null | while read line
do do
case "$line" in case "$line" in
*nspam*) *nspam*)

File diff suppressed because it is too large Load diff

67
plugins/other/xfs_frag Executable file
View file

@ -0,0 +1,67 @@
#!/bin/bash
: <<=cut
=head1 NAME
xfs_frag - Munin plugin to monitor the fragmentation level on your XFS filesystems
=head1 APPLICABLE SYSTEMS
Any machine with an XFS file system.
=head1 CONFIGURATION
None, generally, but you may want to run as root and set a timeout.
[xfs_frag]
user root
timeout 90
=head1 MAGIC MARKERS
#%# family=auto contrib
#%# capabilities=
=head1 VERSION
1
=head1 AUTHOR
Paul Saunders L<darac+munin@darac.org.uk>
=cut
declare -a ARRY
shopt -s nocasematch
case $1 in
config)
cat <<'EOF'
graph_title XFS fragmentation
graph_vlabel Percent
graph_category disk
EOF
cat /etc/mtab | awk '{print $2 " " $3}' | while read LINE
do
ARRY=($LINE)
if [[ ${ARRY[1]} =~ xfs ]]; then
FIELDNAME=$(echo ${ARRY[0]} | sed 's/^[^A-Za-z_]/_/; s/[^A-Za-z0-9_]/_/g')
echo "$FIELDNAME.label ${ARRY[0]}"
echo "$FIELDNAME.type GAUGE"
fi
done
exit 0
;;
esac
cat /etc/mtab | awk '{print $2 " " $3 " " $1}' | while read LINE
do
ARRY=($LINE)
if [[ ${ARRY[1]} =~ xfs ]]; then
FIELDNAME=$(echo ${ARRY[0]} | sed 's/^[^A-Za-z_]/_/; s/[^A-Za-z0-9_]/_/g')
FRAG=$(xfs_db -c frag -r ${ARRY[2]} | sed 's/.*fragmentation factor \(.*\)%.*/\1/')
echo $FIELDNAME.value $FRAG
fi
done

View file

@ -45,7 +45,7 @@ Warnings are sent if your estimated allowance drops below 25% of your cap and if
=head1 AUTHOR =head1 AUTHOR
Paul Saunders L<darac@darac.org.uk> Paul Saunders L<darac+munin@darac.org.uk>
=cut =cut
@ -55,13 +55,15 @@ use warnings;
use lib $ENV{'MUNIN_LIBDIR'}; use lib $ENV{'MUNIN_LIBDIR'};
use Munin::Plugin; use Munin::Plugin;
use Data::Dump qw(pp); use Data::Dump qw(pp);
use Time::Local;
my $ret = undef; my $ret = undef;
# Load modules like so # Load modules like so
if ( !eval "require zenus;" ) { if ( !eval "require zenus;" ) {
$ret = $ret =
"Could not load zenus. Get it from http://www.rachaelandtom.info/zenus"; "Could not load zenus. Get it from http://www.rachaelandtom.info/zenus\n";
$ret .= "(BTW, \@INC is: " . join( ', ', @INC ) . ")\n";
} }
my $USER = $ENV{user}; my $USER = $ENV{user};
@ -182,20 +184,26 @@ if ( defined $ARGV[0] and $ARGV[0] eq "config" ) {
my $cap = sprintf( "%.3f", $data->{avail} ); my $cap = sprintf( "%.3f", $data->{avail} );
my $warn = sprintf( "%.3f", $cap * 0.25 ); my $warn = sprintf( "%.3f", $cap * 0.25 );
my $crit = sprintf( "%.3f", $cap * 0.1 ); my $crit = sprintf( "%.3f", $cap * 0.1 );
my $datestr = scalar( localtime($lastread) );
print <<EOF; print <<EOF;
graph_args --base 1000 graph_args --base 1000
graph_vlabel GBytes graph_vlabel GBytes out (-) / in (+)
graph_category Network graph_category Network
graph_title Zen Broadband Usage graph_title Zen Broadband Usage
graph_info Usage of your Zen Broadband account: $data->{name} graph_info Usage of your Zen Broadband account: $data->{name}
download.label Downloaded
download.type GAUGE
download.info Amount of data downloaded (Limit is $cap GB)
download.draw AREA
upload.label Uploaded upload.label Uploaded
upload.type GAUGE upload.type GAUGE
upload.info Amount of data uploaded (No upper limit) upload.info Amount of data uploaded (No upper limit)
upload.draw AREA upload.draw AREA
upload.graph no
upload.colour 00CC00EE
download.label Transfer
download.type GAUGE
download.info Amount of data downloaded (Limit is $cap GB)
download.draw AREA
download.extinfo Last Read was $datestr
download.negative upload
download.colour 00CC00EE
allowance.label Allowance allowance.label Allowance
allowance.type GAUGE allowance.type GAUGE
allowance.info Amount of data you are allowed to download this month allowance.info Amount of data you are allowed to download this month
@ -214,7 +222,7 @@ overrate.info Rate at which you're downloading beyond the sustainable rate
overrate.draw LINE1 overrate.draw LINE1
overrate.min 0 overrate.min 0
overrate.warning 0: overrate.warning 0:
graph_order download upload allowance remaining overrate #graph_order download upload allowance remaining overrate
EOF EOF
save_data($data); save_data($data);