diff --git a/modules/statistics/lib/Aggregator.php b/modules/statistics/lib/Aggregator.php index 4ba6e362ea0166ef2ae03e66b765fafef935132d..345b446385b102d33e90d701c2bd0ef2eab8b5b0 100644 --- a/modules/statistics/lib/Aggregator.php +++ b/modules/statistics/lib/Aggregator.php @@ -58,10 +58,11 @@ class sspmod_statistics_Aggregator { $i = 0; // Parse through log file, line by line foreach ($logfile AS $logline) { - $i++; + // Continue if STAT is not found on line. if (!preg_match('/STAT/', $logline)) continue; - + $i++; + // Parse log, and extract epoch time and rest of content. $epoch = $logparser->parseEpoch($logline); $content = $logparser->parseContent($logline); @@ -72,7 +73,7 @@ class sspmod_statistics_Aggregator { echo('Log line: ' . $logline . "\n"); echo('Date parse [' . substr($logline, 0, $this->statconfig->getValue('datelength', 15)) . '] to [' . date(DATE_RFC822, $epoch) . ']' . "\n"); print_r($content); - if ($i > 2) exit; + if ($i >= 13) exit; } diff --git a/modules/statistics/lib/Graph/GoogleCharts.php b/modules/statistics/lib/Graph/GoogleCharts.php index f11231597c257fdfdeafb0981ee81f22a1932311..787843a8cab0b2cec3b63a50b24a74561d19c045 100644 --- a/modules/statistics/lib/Graph/GoogleCharts.php +++ b/modules/statistics/lib/Graph/GoogleCharts.php @@ -28,10 +28,33 @@ class sspmod_statistics_Graph_GoogleCharts { } # t:10.0,58.0,95.0 - private function encodedata($data) { - return 't:' . join(',', $data); + private function encodedata($datasets) { + $setstr = array(); + foreach ($datasets AS $dataset) { + $setstr[] = join(',', $dataset); + } + return 't:' . join('|', $setstr); } + + + /** + * Return colors between multiple graphs... + */ + private function getFillArea($datasets) { + if (count($datasets) < 2) return ''; + + $colors = array('eeeeee', 'cccccc', 'aaaaaa', '99eecc'); + $num = count($datasets) ; + $colstr = array(); + for ($i = 0; $i < $num; $i++) { + $colstr[] = 'b' . ',' . $colors[$i] . ',' . ($i) . ',' . ($i+1) . ',0'; + } + return '&chm=' . join('|', $colstr); + } + + + /** * Generate a Google Charts URL which points to a generated image. * More documentation on Google Charts here: @@ -39,19 +62,23 @@ class sspmod_statistics_Graph_GoogleCharts { * * @param $axis Axis * @param $axpis Axis positions - * @param $values Dataset values + * @param $datasets Datasets values * @param $max Max value. Will be the topmost value on the Y-axis. */ - public function show($axis, $axispos, $values, $max) { + public function show($axis, $axispos, $datasets, $max) { - $nv = count($values); $url = 'http://chart.apis.google.com/chart?' . // Dimension of graph. Default is 800x350 'chs=' . $this->x . 'x' . $this->y . // Dateset values. - '&chd=' . $this->encodedata($values) . + '&chd=' . $this->encodedata($datasets) . + + // Fill area... + $this->getFillArea($datasets) . + + // chart type is linechart '&cht=lc' . '&chxt=x,y' . '&chxl=0:|' . $this->encodeaxis($axis) . # . $'|1:||top' . @@ -59,7 +86,7 @@ class sspmod_statistics_Graph_GoogleCharts { # '&chxp=0,0.3,0.4' . '&chxr=0,0,1|1,0,' . $max . # '&chm=R,CCCCCC,0,0.25,0.5' . - '&chg=' . (2400/(count($values)-1)) . ',20,3,3'; // lines + '&chg=' . (2400/(count($datasets[0])-1)) . ',20,3,3'; // lines return $url; } diff --git a/modules/statistics/templates/statistics-tpl.php b/modules/statistics/templates/statistics-tpl.php index 9fa4a51f1e2dde6f47ff92b8ef06beb2f75ac3c3..caf06c1edf3ae32cc30d35055e3e0d7adc7cde3b 100644 --- a/modules/statistics/templates/statistics-tpl.php +++ b/modules/statistics/templates/statistics-tpl.php @@ -50,8 +50,15 @@ $this->includeAtTemplateBase('includes/header.php'); echo('<h1>'. $this->data['available.rules'][$this->data['selected.rule']]['name'] . '</h1>'); echo('<p>' . $this->data['available.rules'][$this->data['selected.rule']]['descr'] . '</p>'); -echo '<div class="selecttime" style="border: 1px solid #ccc; background: #eee; margin: 5px 0px; padding: .5em">'; -echo '<div style="display: inline">'; + + + +// Report settings +echo '<table class="selecttime" style="width: 100%; border: 1px solid #ccc; background: #eee; margin: 1px 0px; padding: 0px">'; +echo('<tr><td style="width: 50px; padding: 0px"><img style="margin: 0px" src="' . SimpleSAML_Module::getModuleURL("statistics/resources/report.png") . '" alt="Report settings" /></td>'); + +// Select report +echo '<td>'; echo '<form style="display: inline"><select onChange="submit();" name="rule">'; foreach ($this->data['available.rules'] AS $key => $rule) { if ($key === $this->data['selected.rule']) { @@ -61,12 +68,45 @@ foreach ($this->data['available.rules'] AS $key => $rule) { } } echo '</select></form>'; -echo '</div>'; +echo '</td>'; + + +// Select delimiter +echo '<td style="text-align: right">'; +echo '<form style="display: inline">'; +echo '<input type="hidden" name="rule" value="' . $this->data['selected.rule'] . '" />'; +echo '<input type="hidden" name="time" value="' . $this->data['selected.time'] . '" />'; +echo '<select onChange="submit();" name="d">'; +foreach ($this->data['availdelimiters'] AS $key => $delim) { + if ($key == '_') { + echo '<option value="_">Total</option>'; + } elseif ($delim == $_REQUEST['d']) { + echo '<option selected="selected" value="' . $delim . '">' . $delim . '</option>'; + } else { + echo '<option value="' . $delim . '">' . $delim . '</option>'; + } +} +echo '</select></form>'; +echo '</td>'; + +echo '</table>'; + +// End report settings -echo '<div style="display: inline">'; +// Select time and date +echo '<table class="selecttime" style="width: 100%; border: 1px solid #ccc; background: #eee; margin: 1px 0px; padding: 0px">'; +echo('<tr><td style="width: 50px; padding: 0px"><img style="margin: 0px" src="' . SimpleSAML_Module::getModuleURL("statistics/resources/calendar.png") . '" alt="Select date and time" /></td>'); + +if (isset($this->data['available.times.prev'])) { + echo('<td style=""><a href="showstats.php?rule=' . $this->data['selected.rule']. '&time=' . $this->data['available.times.prev'] . '">« Previous</a></td>'); +} else { + echo('<td style="color: #ccc">« Previous</td>'); +} + +echo '<td style="text-align: center">'; echo '<form style="display: inline">'; echo '<input type="hidden" name="rule" value="' . $this->data['selected.rule'] . '" />'; echo '<select onChange="submit();" name="time">'; @@ -78,30 +118,23 @@ foreach ($this->data['available.times'] AS $key => $timedescr) { } } echo '</select></form>'; -echo '</div>'; +echo '</td>'; + +if (isset($this->data['available.times.next'])) { + echo('<td style="text-align: right; padding-right: 4px"><a href="showstats.php?rule=' . $this->data['selected.rule']. '&time=' . $this->data['available.times.next'] . '">Next »</a></td>'); +} else { + echo('<td style="color: #ccc; text-align: right; padding-right: 4px">Next »</td>'); +} + + + + +echo '</tr></table>'; -echo '<div style="display: inline">'; -echo '<form style="display: inline">'; -echo '<input type="hidden" name="rule" value="' . $this->data['selected.rule'] . '" />'; -echo '<input type="hidden" name="time" value="' . $this->data['selected.time'] . '" />'; -echo '<select onChange="submit();" name="d">'; -foreach ($this->data['availdelimiters'] AS $key => $delim) { - if ($key == '_') { - echo '<option value="_">Total</option>'; - } elseif ($delim == $_REQUEST['d']) { - echo '<option selected="selected" value="' . $delim . '">' . $delim . '</option>'; - } else { - echo '<option value="' . $delim . '">' . $delim . '</option>'; - } -} -echo '</select></form>'; -echo '</div>'; -echo '<div style="clear: both; height: 0px"></div>'; -echo '</div>'; echo '<div id="tabdiv"><ul class="tabset_tabs"> diff --git a/modules/statistics/www/resources/calendar.png b/modules/statistics/www/resources/calendar.png new file mode 100644 index 0000000000000000000000000000000000000000..91ff723ee03e74bdc82f947e5300565ff7155dc7 Binary files /dev/null and b/modules/statistics/www/resources/calendar.png differ diff --git a/modules/statistics/www/resources/report.png b/modules/statistics/www/resources/report.png new file mode 100644 index 0000000000000000000000000000000000000000..3afe8a2b956c8ce4fdd3c2cb99b8c12c58204e51 Binary files /dev/null and b/modules/statistics/www/resources/report.png differ diff --git a/modules/statistics/www/showstats.php b/modules/statistics/www/showstats.php index c41de5dad7e72222f3b048b4d7f66cd3c20d9dca..0cc4c90963cffcc2e96e2fafe80296e1be51e3fc 100644 --- a/modules/statistics/www/showstats.php +++ b/modules/statistics/www/showstats.php @@ -63,6 +63,18 @@ if (array_key_exists('time', $_GET)) { } } +// Extract previous and next time slots... +$available_times_prev = NULL; $available_times_next = NULL; +$timeslots = array_keys($available_times); +$timeslotindex = array_flip($timeslots); + +if ($timeslotindex[$fileslot] > 0) + $available_times_prev = $timeslots[$timeslotindex[$fileslot]-1]; +if ($timeslotindex[$fileslot] < (count($timeslotindex)-1) ) + $available_times_next = $timeslots[$timeslotindex[$fileslot]+1]; + + + // Get file and extract results. $resultFileName = $statdir . $rule . '-' . $fileslot . '.stat'; if (!file_exists($resultFileName)) @@ -74,10 +86,6 @@ $results = unserialize($resultfile); if (empty($results)) throw new Exception('Aggregated statistics in file [' . $resultFileName . '] was empty.'); -$dataset = array(); -$axis = array(); -$axispos = array(); -$max = 15; /* @@ -99,13 +107,20 @@ if (isset($_REQUEST['d'])) { $maxvalue = 0; $maxvaluetime = 0; $debugdata = array(); + + +$maxdelimiter = $delimiter; +if (array_key_exists('graph.total', $statrules[$rule]) && $statrules[$rule]['graph.total'] === TRUE) { + $maxdelimiter = '_'; +} + foreach($results AS $slot => &$res) { - if (!array_key_exists($delimiter, $res)) $res[$delimiter] = 0; - if ($res[$delimiter] > $maxvalue) { + if (!array_key_exists($maxdelimiter, $res)) $res[$maxdelimiter] = 0; + if ($res[$maxdelimiter] > $maxvalue) { $maxvaluetime = $datehandler->prettyDateSlot($slot, $slotsize, $dateformat_intra); } - $maxvalue = max($res[$delimiter],$maxvalue); - $debugdata[] = array($datehandler->prettyDateSlot($slot, $slotsize, $dateformat_intra), $res[$delimiter] ); + $maxvalue = max($res[$maxdelimiter],$maxvalue); + $debugdata[] = array($datehandler->prettyDateSlot($slot, $slotsize, $dateformat_intra), $res[$maxdelimiter] ); } $max = sspmod_statistics_Graph_GoogleCharts::roof($maxvalue); @@ -133,41 +148,76 @@ $summaryDataset = array_reverse($summaryDataset, TRUE); #echo '<pre>'; print_r($summaryDataset); exit; -/* - * Walk through dataset to get percent values from max into dataset[]. - */ + + + + +$datasets = array(); +$axis = array(); +$axispos = array(); +#$max = 25; $availdelimiters = array(); $xentries = count($results); $lastslot = 0; $i = 0; -foreach($results AS $slot => $res) { - $dataset[] = number_format(100*$res[$delimiter] / $max, 2); - foreach(array_keys($res) AS $nd) $availdelimiters[$nd] = 1; +/* + * Walk through dataset to get percent values from max into dataset[]. + */ +function getPercentValues($results, $delimiter) { + + #echo('<pre>'); print_r($results); exit; + + global $slot, $slotsize, $dateformat_intra, $axis, $axispos, $availdelimiters, $max, $datehandler, $axislabelint, $i, $xentries; + + $dataset = array(); + foreach($results AS $slot => $res) { + #echo ('<p>new value: ' . number_format(100*$res[$delimiter] / $max, 2)); + if (array_key_exists($delimiter, $res)) { + $dataset[] = number_format(100*$res[$delimiter] / $max, 2); + } else { + $dataset[] = '0'; + } + foreach(array_keys($res) AS $nd) $availdelimiters[$nd] = 1; + + // check if there should be an axis here... + if ( $slot % $axislabelint == 0) { + $axis[] = $datehandler->prettyDateSlot($slot, $slotsize, $dateformat_intra); + $axispos[] = (($i)/($xentries-1)); + #echo 'set axis on [' . $slot . ']'; + } + $lastslot = $slot; + $i++; + } + + return $dataset; +} - // check if there should be an axis here... - if ( $slot % $axislabelint == 0) { - $axis[] = $datehandler->prettyDateSlot($slot, $slotsize, $dateformat_intra); - $axispos[] = (($i)/($xentries-1)); - - #echo 'set axis on [' . $slot . ']'; + +$datasets[] = getPercentValues($results, '_'); +if ($delimiter !== '_') { + if (array_key_exists('graph.total', $statrules[$rule]) && $statrules[$rule]['graph.total'] === TRUE) { + $datasets[] = getPercentValues($results, $delimiter); } - $lastslot = $slot; - $i++; } + #echo 'set axis on lastslot [' . $lastslot . ']'; $axis[] = $datehandler->prettyDateSlot($lastslot+1, $slotsize, $dateformat_intra); #print_r($axis); + + $dimx = $statconfig->getValue('dimension.x', 800); $dimy = $statconfig->getValue('dimension.y', 350); $grapher = new sspmod_statistics_Graph_GoogleCharts($dimx, $dimy); $t = new SimpleSAML_XHTML_Template($config, 'statistics:statistics-tpl.php'); $t->data['header'] = 'stat'; -$t->data['imgurl'] = $grapher->show($axis, $axispos, $dataset, $max); +$t->data['imgurl'] = $grapher->show($axis, $axispos, $datasets, $max); $t->data['available.rules'] = $available_rules; $t->data['available.times'] = $available_times; +$t->data['available.times.prev'] = $available_times_prev; +$t->data['available.times.next'] = $available_times_next; $t->data['selected.rule']= $rule; $t->data['selected.time'] = $fileslot; $t->data['debugdata'] = $debugdata;