';
return
} else {
opendir (GROUPDIR, $groupdir) ||
die "Fatal: can't open groupdir $groupdir: $!";
my @groups = sort (grep { -f "$groupdir/$_" && /^\w+/ } readdir (GROUPDIR));
closedir GROUPDIR;
print header (
-type => "text/html",
-expires => "+10m"
);
print '
';
print "$title ";
print '
';
print '
';
print '
';
print '
systory ';
print ' Click on a host name from the table on the right to view all statistics for all time spans or Check one or more hosts and/or one or more groups, one or more statistics, and one or more time spans.
';
#### here goes the form elements
print '
';
return
};
}; ## END print_page_top
###############################################################################
sub determine_hosts {
if (param('group') =~ /^all$/i) {
param(-name => 'host', -value => 'all');
};
unless (param('host') || param('group')) {
param(-name => 'host', -value => 'all');
param(-name => 'group', -value => 'all');
$group = "all";
};
if (param('host')) {
foreach (param('host')) {
if ($_ =~ /^all$/i) {
opendir (DATADIR, $datadir) ||
die "Can't open datadir $datadir: $!";
@hosts = sort (grep { -d "$datadir/$_" && /^\w+/ } readdir (DATADIR));
closedir DATADIR;
} elsif (-d "$datadir/$_" && $_ =~ /(^\w.+$)/) {
push (@hosts, $1)
} else {
note ("Invalid host $_ specified.");
};
};
} elsif (param('group') && param('group') =~ /(^\w+.*)/) {
$group = "$1";
if (-f "$groupdir/$group") {
open (GROUPFILE, "$groupdir/$group") ||
die "Can't read group file $groupdir/$group: $!";
while () {
next if /^$/;
chomp;
if (-d "$datadir/$_") {
push (@hosts, $_);
} else {
note ("No data available for host $_ in group $group.");
};
};
close GROUPFILE;
} else {
note ("Invalid group $group specified.");
};
my @hosts_sorted = sort {$::a cmp $::b} @hosts;
@hosts = @hosts_sorted;
};
}; ## END determine_hosts
###############################################################################
sub generate_index {
print <
Host
OS
Model
CPUs
RAM (MB)
Uptime
Last Update
END
my $hostindex = "0";
my $rowcolor;
foreach (@hosts) {
open(SUMMARY, "$datadir/$_/summary") ||
do { note "no summary found for host $_" ; next };
my $age = sprintf ("%d", time() - (sub { $_[9] } -> (stat SUMMARY)));
$age = ($age > 86399) ? "" . sprintf ("%d", $age / 86400) . " d " :
($age > 3549) ? "" . sprintf ("%d", $age / 3600) . " h " :
($age > 601) ? "" . sprintf ("%d", $age / 600) . " m " :
($age > 300) ? "" . sprintf ("%d", $age ) . " s " :
$age . " s";
my ($host, $os, $model, $proc_info, $ram, $uptime) = split (/\|/, ());
$hostindex++;
if ($hostindex % 2) {
$rowcolor = "#FFFFFF"
} else {
$rowcolor = "#EFEEED"
};
print "\n";
print ' ';
print "" . $host . "
$os
$model
$proc_info
$ram
$uptime
$age \n";
close SUMMARY;
};
print " \n";
print "
\n";
} ## END generate_index
###############################################################################
sub determine_stats {
unless (param('stat')) {
param(-name => 'stat', -value => 'all')
};
foreach (param('stat')) {
if ($_ =~ /^all$/i) {
foreach (keys (%stats)) {
push (@stats, $stats{$_});
};
} elsif (exists ($stats{"\L$_"}) && $_ =~ /^(\w+)$/) {
push (@stats, $stats{"\L$1"})
} else {
note ("Invalid stat $_ specified.");
};
};
} ## END determine_stats
###############################################################################
sub determine_spans {
unless (param('span')) {
param(-name => 'span', -value => 'all')
};
foreach (param('span')) {
if ($_ =~ /^all$/i) {
foreach (keys (%spans)) {
push (@spans, $spans{$_});
};
} elsif (exists ($spans{"\L$_"}) && $_ =~ /^(\w+)$/) {
push (@spans, $spans{"\L$_"})
} else {
note ("Invalid span $_ specified.");
};
};
my @spans_sorted = sort {$::a <=> $::b} @spans;
@spans = @spans_sorted;
} ## END determine_spans
###############################################################################
sub generate_graphs {
print '';
my @graph_common_args = (
"--lazy",
"--no-minor",
"--lower-limit", "0",
"--color", "BACK#FFFFFF",
"--color", "CANVAS#FFFFFF",
"--color", "MGRID#666666",
"--color", "SHADEA#FFFFFF",
"--color", "SHADEB#FFFFFF"
);
my $gsize;
if (param('gsize') =~ /^sm/i) {
push (@graph_common_args, "--width", "400", "--height", "100");
$gsize = "small";
} elsif (param('gsize') =~ /^la/i) {
push (@graph_common_args, "--width", "800", "--height", "200");
$gsize = "large";
} else {
push (@graph_common_args, "--width", "600", "--height", "150");
$gsize = "medium";
};
my @graph_args;
foreach my $host (@hosts) {
print " \n";
print "$host ";
print "top ";
foreach my $span (@spans) {
print "";
print "$spans_pretty{$span} \n";
print "\n";
foreach my $stat (@stats) {
print "\n";
@graph_args = @graph_common_args;
if ($stat eq 'CPU') {
push (@graph_args,
"--upper-limit", "100",
"--end", "now-5min",
"--start", "now-$span",
"--title", "$host: CPU Usage ($spans_pretty{$span})",
"--vertical-label", "% Busy",
"--imginfo",
" ",
"DEF:A=$datadir/$host/CPU.rrd:user_p:AVERAGE",
"DEF:B=$datadir/$host/CPU.rrd:system_p:AVERAGE",
"CDEF:C=A,B,+",
"CDEF:NODATA=A,UN,INF,UNKN,IF",
"AREA:NODATA#EFEEED"
);
if ($gsize eq "small") {
push (@graph_args,
"AREA:A#000066:% User ",
"STACK:B#009900:% System ",
"LINE1:C#FFFFFF:Total "
);
} else {
push (@graph_args,
"AREA:A#000066:% User ",
"GPRINT:A:LAST:\nCur\\: %3.2lf",
"GPRINT:A:AVERAGE:Avg\\: %3.2lf",
"GPRINT:A:MIN:Min\\: %3.2lf",
"GPRINT:A:MAX:Max\\: %3.2lf\\n",
"STACK:B#009900:% System ",
"GPRINT:B:LAST:Cur\\: %3.2lf",
"GPRINT:B:AVERAGE:Avg\\: %3.2lf",
"GPRINT:B:MIN:Min\\: %3.2lf",
"GPRINT:B:MAX:Max\\: %3.2lf\\n",
"LINE1:C#FFFFFF:Total ",
"GPRINT:C:LAST:Cur\\: %3.2lf",
"GPRINT:C:AVERAGE:Avg\\: %3.2lf",
"GPRINT:C:MIN:Min\\: %3.2lf",
"GPRINT:C:MAX:Max\\: %3.2lf"
);
};
} elsif ($stat eq 'LOAD') {
push (@graph_args,
"--upper-limit", "10",
"--end", "now-5min",
"--start", "now-$span",
"--title", "$host: Load Average ($spans_pretty{$span})",
"--vertical-label", "Load Average",
"--imginfo",
" ",
"DEF:A=$datadir/$host/LOAD.rrd:load_01:AVERAGE",
"DEF:B=$datadir/$host/LOAD.rrd:load_05:AVERAGE",
"DEF:C=$datadir/$host/LOAD.rrd:load_15:AVERAGE",
"CDEF:NODATA=A,UN,INF,UNKN,IF",
"AREA:NODATA#EFEEED",
);
if ($gsize eq "small") {
push (@graph_args,
"LINE1:A#000066:1 Minute ",
"LINE2:B#009900:5 Minute ",
"LINE3:C#FF0000:15 Minute"
);
} else {
push (@graph_args,
"LINE1:A#000066:1 Minute ",
"GPRINT:A:LAST:\nCur\\: %3.2lf",
"GPRINT:A:AVERAGE:Avg\\: %3.2lf",
"GPRINT:A:MIN:Min\\: %3.2lf",
"GPRINT:A:MAX:Max\\: %3.2lf\\n",
"LINE2:B#009900:5 Minute ",
"GPRINT:B:LAST:Cur\\: %3.2lf",
"GPRINT:B:AVERAGE:Avg\\: %3.2lf",
"GPRINT:B:MIN:Min\\: %3.2lf",
"GPRINT:B:MAX:Max\\: %3.2lf\\n",
"LINE3:C#FF0000:15 Minute",
"GPRINT:C:LAST:Cur\\: %3.2lf",
"GPRINT:C:AVERAGE:Avg\\: %3.2lf",
"GPRINT:C:MIN:Min\\: %3.2lf",
"GPRINT:C:MAX:Max\\: %3.2lf"
);
};
} elsif ($stat eq 'SWAP') {
push (@graph_args,
"--upper-limit", "100",
"--end", "now-5min",
"--start", "now-$span",
"--title", "$host: Paging Usage ($spans_pretty{$span})",
"--vertical-label", "% Swap Used",
"--imginfo",
" ",
"DEF:A=$datadir/$host/SWAP.rrd:swap_p:AVERAGE",
"CDEF:NODATA=A,UN,INF,UNKN,IF",
"AREA:NODATA#EFEEED",
);
if ($gsize eq "small") {
push (@graph_args,
"AREA:A#000066:% Swap Used"
);
} else {
push (@graph_args,
"AREA:A#000066:% Swap Used",
"GPRINT:A:LAST:\nCur\\: %3.2lf",
"GPRINT:A:AVERAGE:Avg\\: %3.2lf",
"GPRINT:A:MIN:Min\\: %3.2lf",
"GPRINT:A:MAX:Max\\: %3.2lf"
);
};
};
my $filename = "graphs/$host.$stat.$span.$gsize.png";
my ($imgtag, $xsize, $ysize) = RRDs::graph ($filename, @graph_args);
my $rrderror = RRDs::error;
if ($rrderror) {
print "RRD Error: $rrderror
\n";
} else {
printf (" %s ", @$imgtag);
};
print "\n";
};
print '';
print "\n";
};
print " ";
print "\n";
};
print "
";
}; ## END generate_graphs
###############################################################################
sub print_page_bottom {
print '