diff --git a/HISTORY.md b/HISTORY.md index 60b1b62..8b1eb5d 100644 --- a/HISTORY.md +++ b/HISTORY.md @@ -6,6 +6,8 @@ your knownlinks file. * Added support for peer-AS stats/graphs (sFlow only). * Add -n option to asstats.pl and set showpeeras=true in config.inc to enable. +* Top N AS intervals are now configurable (see config.inc and README), and separate top stats files can be used per interval (enables e.g. proper weekly/monthly stats). +* Added Terabyte formatting. ## 1.5 diff --git a/README.md b/README.md index fc34611..0686085 100644 --- a/README.md +++ b/README.md @@ -30,8 +30,9 @@ scripts. Prerequisites ------------- -- Perl 5.10 -- RRDtool 1.2 (with Perl "RRDs" library) +- Perl 5.10 or newer +- RRDtool 1.3 or newer (with Perl "RRDs" library) +- File::Find::Rule module (CPAN) - if using sFlow: the Net::sFlow module (CPAN) - web server with PHP 5 - one or more routers than can generate NetFlow v8/v9 AS aggregation records @@ -260,14 +261,30 @@ Installation - Add a cronjob to run the following command every hour: - `rrd-extractstats.pl /path/to/rrd/dir /path/to/knownlinks \ - /path/to/asstats_day.txt` + `rrd-extractstats.pl /path/to/rrd/dir /path/to/knownlinks /path/to/asstats_day.txt` That script will go through all RRD files and collect per-link summary stats for each AS, sort them by total traffic (descending), and write them to a text file. The "top N AS" page uses this to determine which ASes to show. + If you want an additional interval for the top N AS (e.g. top N AS in the + last 30 days), add another cronjob with the desired interval in hours as + the last argument (and another output file of course). Example: + + `rrd-extractstats.pl /path/to/rrd/dir /path/to/knownlinks /path/to/asstats_month.txt 720` + + Add the interval to the top_intervals array in config.inc (see the example) so that + it will appear in the web interface. + + Repeat for further intervals if necessary. + + It is not recommended to run more than one rrd-extractstats.pl cronjobs at the same + time for disk I/O reasons – add some variation in the start minute setting + so that the jobs can run separately. + For longer intervals than one day, the cronjob frequency can be adjusted as + well (e.g. for monthly output, it is sufficient to run the cronjob once a day). + - Copy the contents of the "www" directory to somewhere within your web server's document root and change file paths in config.inc as necessary. diff --git a/bin/rrd-extractstats.pl b/bin/rrd-extractstats.pl index b8613ee..b10d1b7 100755 --- a/bin/rrd-extractstats.pl +++ b/bin/rrd-extractstats.pl @@ -10,13 +10,18 @@ use RRDs; use File::Find; use File::Find::Rule; -if ($#ARGV != 2) { - die("Usage: $0 outfile\n"); +if ($#ARGV < 2) { + die("Usage: $0 outfile [interval-hours]\n"); } my $rrdpath = $ARGV[0]; my $knownlinksfile = $ARGV[1]; my $statsfile = $ARGV[2]; +my $interval = 86400; + +if ($ARGV[3]) { + $interval = $ARGV[3] * 3600; +} my %knownlinks; @@ -37,7 +42,7 @@ foreach my $rrdfile (@rrdfiles) { if ($rrdfile =~ /\/(\d+).rrd$/) { my $as = $1; - $astraffic->{$as} = gettraffic($as, time - 86400, time); + $astraffic->{$as} = gettraffic($as, time - $interval, time); $i++; if ($i % 100 == 0) { print "$i... "; diff --git a/www/config.inc b/www/config.inc index cb622c9..76d4134 100644 --- a/www/config.inc +++ b/www/config.inc @@ -37,5 +37,21 @@ $customlinks = array( 'euro-IX' => 'https://www.euro-ix.net/tools/asn_search?query=%as%' ); +/* Custom time intervals for top N AS */ +/* +$top_intervals[] = array( + 'hours' => 7*24, + 'statsfile' => '/data/as-stats/asstats_week.txt', + 'label' => '1 week', + //'statslabel' => '1 week' // overrides display of "... in the last ..." - use if 'hours' parameter does not correspond with statsfile interval +); +$top_intervals[] = array( + 'hours' => 30*24, + 'statsfile' => '/data/as-stats/asstats_month.txt', + 'label' => '30 days', + //'statslabel' => '30 days' // overrides display of "... in the last ..." - use if 'hours' parameter does not correspond with statsfile interval +); +*/ + /* END - no closing php tag needed here (prevents problems with stray whitespace) */ diff --git a/www/config_defaults.inc b/www/config_defaults.inc index e59a8ea..dce9e43 100644 --- a/www/config_defaults.inc +++ b/www/config_defaults.inc @@ -21,3 +21,23 @@ $asset_graph_height = 200; /* Defaults for other settings, introduced in recent versions */ $vertical_label = true; # vertical IN/OUT label in graph $brighten_negative = true; # brighten the "negative" part of graphs +$showpeeras = false; + +/* Time intervals for top N AS */ +$top_intervals = array( + array( + 'hours' => 24, + 'label' => '24 hours', + 'statslabel' => '24 hours' + ), + array( + 'hours' => 4, + 'label' => '4 hours', + 'statslabel' => '24 hours' + ), + array( + 'hours' => 12, + 'label' => '12 hours', + 'statslabel' => '24 hours' + ) +); diff --git a/www/func.inc b/www/func.inc index b5b4aad..796639c 100644 --- a/www/func.inc +++ b/www/func.inc @@ -95,15 +95,7 @@ function getknownlinks() { return $knownlinks; } -function getasstats_top($ntop, $peer = 0) { - if($peer == 0){ - global $daystatsfile; - $statfile = $daystatsfile; - }else{ - global $daypeerstatsfile; - $statfile = $daypeerstatsfile; - } - +function getasstats_top($ntop, $statfile) { /* first step: walk the data for all ASes to determine the top 5 for the given link */ $fd = fopen($statfile, "r"); if (!$fd) @@ -148,7 +140,9 @@ function getasstats_top($ntop, $peer = 0) { } function format_bytes($bytes) { - if ($bytes >= 1073741824) + if ($bytes >= 1099511627776) + return sprintf("%.2f TB", $bytes / 1099511627776); + else if ($bytes >= 1073741824) return sprintf("%.2f GB", $bytes / 1073741824); else if ($bytes >= 1048576) return sprintf("%.2f MB", $bytes / 1048576); diff --git a/www/headermenu.inc b/www/headermenu.inc index 901321d..db1829c 100644 --- a/www/headermenu.inc +++ b/www/headermenu.inc @@ -1,35 +1,22 @@ Top AS | Top AS | Top AS: "; +foreach ($top_intervals as $interval) { + echo '' . $interval['label'] . ' | '; +} if($showpeeras == true){ if ($dpagename == "peerusage"): - ?>Top Peer AS | Peer 24 hours | Top AS Peer | Peer 24 hours | 4 Hour | 4 Hour | 12 Hour | 12 Hour | View an AS | 200) $ntop = 200; -$topas = getasstats_top($ntop, $peerusage); +if ($peerusage) + $statsfile = $daypeerstatsfile; +else { + $statsfile = $daystatsfile; + + /* find more appropriate file for this interval */ + foreach ($top_intervals as $interval) { + if ($interval['hours'] == @$_GET['numhours']) { + if (@$interval['statsfile']) + $statsfile = $interval['statsfile']; + if (@$interval['label']) + $label = $interval['label']; + if (@$interval['statslabel']) + $statslabel = $interval['statslabel']; + } + } +} +$topas = getasstats_top($ntop, $statsfile); if (@$_GET['numhours']) { $start = time() - $_GET['numhours']*3600; $end = time(); + if (!$label) + $label = htmlspecialchars($_GET['numhours']) . " hours"; } else { $start = ""; $end = ""; + if (!$label) + $label = "24 hours"; } +if (!$statslabel) + $statslabel = $label; + ?> @@ -32,7 +56,7 @@ if (@$_GET['numhours']) { - Top <?php echo $ntop; ?> AS<?php if($peerusage) echo " peer"; ?> + Top <?php echo $ntop; ?> AS<?php if($peerusage) echo " peer"; ?> (<?=$label?>) @@ -46,7 +70,7 @@ Number of AS: -
Top AS
+
Top AS ()
@@ -67,10 +91,10 @@ $class = (($i % 2) == 0) ? "even" : "odd"; AS:
IPv4: ~ in / - out in the last 24 hours
+ out in the last
IPv6: ~ in / - out in the last 24 hours
+ out in the last