mirror of
https://github.com/Cacti/cacti.git
synced 2026-10-27 23:27:44 +09:00
68 lines
3.2 KiB
PHP
68 lines
3.2 KiB
PHP
<?php
|
|
declare(strict_types = 1);
|
|
// Copyright (C) 2004-2026 The Cacti Group. GPL-2.0-or-later.
|
|
// Regression coverage for Cacti issue #8426.
|
|
|
|
require_once __DIR__ . '/../../../../lib/spikekill.php';
|
|
|
|
test('windowed deviation uses the same reference samples for its mean and deviation', function (mixed $minimum, mixed $maximum) {
|
|
$repair = (new ReflectionClass(spikekill::class))->newInstanceWithoutConstructor();
|
|
$repair->method = SPIKE_METHOD_STDDEV;
|
|
$repair->out_start = 150;
|
|
$repair->out_end = 250;
|
|
$repair->stddev = 2;
|
|
|
|
foreach (['ds_min' => [$minimum], 'ds_max' => [$maximum]] as $name => $value) {
|
|
(new ReflectionProperty(spikekill::class, $name))->setValue($repair, $value);
|
|
}
|
|
$statistics = [[['sumofsamples' => 1020, 'numsamples' => 3]]];
|
|
$samples = [[[100 => '10', 200 => '1000', 225 => 'NaN', 300 => '10', 400 => 'NaN']]];
|
|
(new ReflectionMethod(spikekill::class, 'calculateOverallStatistics'))->invokeArgs($repair, [&$statistics, &$samples]);
|
|
expect($statistics[0][0]['average'])->toEqual(10)
|
|
->and($statistics[0][0]['stddev'])->toEqual(0)
|
|
->and($statistics[0][0]['min_cutoff'])->toEqual(10)
|
|
->and($statistics[0][0]['max_cutoff'])->toEqual(10)
|
|
->and($statistics[0][0]['stddev_killed'])->toBe(1);
|
|
})->with([[0, 10000], ['NaN', 'NaN']]);
|
|
|
|
test('absolute repair carries the last valid value separately for each data source', function () {
|
|
$repair = (new ReflectionClass(spikekill::class))->newInstanceWithoutConstructor();
|
|
$repair->method = SPIKE_METHOD_ABSOLUTE;
|
|
$repair->avgnan = 'last';
|
|
$repair->absmax = 100;
|
|
$repair->out_start = 150;
|
|
$repair->out_end = 350;
|
|
$output = [
|
|
'<row><timestamp>100</timestamp><v>10</v><v>0</v></row>',
|
|
'<row><timestamp>200</timestamp><v>1000</v><v>500</v></row>',
|
|
'<row><timestamp>300</timestamp><v>20</v><v>5</v></row>',
|
|
'<row><timestamp>325</timestamp><v>NaN</v><v>NaN</v></row>',
|
|
'<row><timestamp>400</timestamp><v>2000</v><v>500</v></row>',
|
|
];
|
|
$statistics = [];
|
|
$repaired = (new ReflectionMethod(spikekill::class, 'updateXML'))->invokeArgs($repair, [&$output, &$statistics]);
|
|
$xml = simplexml_load_string('<database>' . implode('', $repaired) . '</database>');
|
|
expect((string) $xml->row[1]->v[0])->toBe(' 10')
|
|
->and((string) $xml->row[1]->v[1])->toBe(' 0')
|
|
->and((string) $xml->row[2]->v[0])->toBe(' 20')
|
|
->and((string) $xml->row[3]->v[0])->toBe(' NaN')
|
|
->and((string) $xml->row[4]->v[0])->toBe(' 2000');
|
|
});
|
|
|
|
test('deviation correction preserves unknown samples', function () {
|
|
$repair = (new ReflectionClass(spikekill::class))->newInstanceWithoutConstructor();
|
|
$repair->method = SPIKE_METHOD_STDDEV;
|
|
$repair->avgnan = 'last';
|
|
$repair->numspike = 10;
|
|
$output = [
|
|
'<row><timestamp>100</timestamp><v>10</v></row>',
|
|
'<row><timestamp>200</timestamp><v>NaN</v></row>',
|
|
'<row><timestamp>300</timestamp><v>1000</v></row>',
|
|
];
|
|
$statistics = [[['min_cutoff' => 5, 'max_cutoff' => 15]]];
|
|
$repaired = (new ReflectionMethod(spikekill::class, 'updateXML'))->invokeArgs($repair, [&$output, &$statistics]);
|
|
$xml = simplexml_load_string('<database>' . implode('', $repaired) . '</database>');
|
|
expect((string) $xml->row[1]->v)->toBe(' NaN')
|
|
->and((string) $xml->row[2]->v)->toBe(' 10');
|
|
});
|