From dc94e36c2f8379b41ee61fae983dc6341c8a81ec Mon Sep 17 00:00:00 2001 From: Yonas Habteab Date: Mon, 15 Nov 2021 15:00:33 +0100 Subject: [PATCH 1/5] Introduce `HasNotValue` Filter rule --- src/Filter/HasNotValue.php | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 src/Filter/HasNotValue.php diff --git a/src/Filter/HasNotValue.php b/src/Filter/HasNotValue.php new file mode 100644 index 0000000..e256e1e --- /dev/null +++ b/src/Filter/HasNotValue.php @@ -0,0 +1,8 @@ + Date: Mon, 15 Nov 2021 15:01:07 +0100 Subject: [PATCH 2/5] Introduce `HasValue` Filter rule --- src/Filter/HasValue.php | 8 ++++++++ 1 file changed, 8 insertions(+) create mode 100644 src/Filter/HasValue.php diff --git a/src/Filter/HasValue.php b/src/Filter/HasValue.php new file mode 100644 index 0000000..a809faf --- /dev/null +++ b/src/Filter/HasValue.php @@ -0,0 +1,8 @@ + Date: Mon, 15 Nov 2021 15:01:54 +0100 Subject: [PATCH 3/5] `Filter`: Implement `hasValue()` & `matchHasValue()` helper methods --- src/Filter.php | 43 +++++++++++++++++++++++++++++++++++++++++++ 1 file changed, 43 insertions(+) diff --git a/src/Filter.php b/src/Filter.php index 402400c..edf4e6d 100644 --- a/src/Filter.php +++ b/src/Filter.php @@ -11,6 +11,8 @@ use ipl\Stdlib\Filter\Equal; use ipl\Stdlib\Filter\GreaterThan; use ipl\Stdlib\Filter\GreaterThanOrEqual; +use ipl\Stdlib\Filter\HasNotValue; +use ipl\Stdlib\Filter\HasValue; use ipl\Stdlib\Filter\LessThan; use ipl\Stdlib\Filter\LessThanOrEqual; use ipl\Stdlib\Filter\None; @@ -143,6 +145,45 @@ protected function matchNone(None $rules, $row) return true; } + /** + * Create a rule that applies rows with a column having any values, i.e. matches + * all rows where this column has been set + * + * Value is optional, as it is not used anyway when executing the query, rather + * it is only being populated in the FilterEditor. + * + * @param string $column + * @param string|null $value + * + * @return HasValue + */ + public static function hasValue($column, $value = '') + { + return new HasValue($column, $value); + } + + /** + * Get whether the given rule's column contains any values + * + * @param HasValue|HasNotValue $rule + * @param object $row + * + * @return bool + */ + protected function matchHasValue($rule, $row) + { + if (! $rule instanceof HasValue && ! $rule instanceof HasNotValue) { + throw new InvalidArgumentException(sprintf( + 'Rule must be of type %s or %s, got %s instead', + HasValue::class, + HasNotValue::class, + get_php_type($rule) + )); + } + + return ! empty($this->extractValue($rule->getColumn(), $row)); + } + /** * Create a rule that matches rows with a column that **equals** the given value * @@ -408,6 +449,8 @@ protected function performMatch(Rule $rule, $row) return $this->matchNone($rule, $row); case $rule instanceof Unequal: return $this->matchUnequal($rule, $row); + case $rule instanceof HasValue: + return $this->matchHasValue($rule, $row); default: throw new InvalidArgumentException(sprintf( 'Unable to match filter. Rule type %s is unknown', From a5d4a796037de9ea798d4b08879e38c4b9c762df Mon Sep 17 00:00:00 2001 From: Yonas Habteab Date: Mon, 15 Nov 2021 16:42:54 +0100 Subject: [PATCH 4/5] Filter: Implement `hasNotValue()` & `matchHasnotValue()` methods --- src/Filter.php | 32 ++++++++++++++++++++++++++++++++ 1 file changed, 32 insertions(+) diff --git a/src/Filter.php b/src/Filter.php index edf4e6d..e3c7ce7 100644 --- a/src/Filter.php +++ b/src/Filter.php @@ -184,6 +184,36 @@ protected function matchHasValue($rule, $row) return ! empty($this->extractValue($rule->getColumn(), $row)); } + /** + * Create a rule that applies rows where a column has no values, i.e. to all + * rows where this column hasn't been set. + * + * Value is optional, as it is not used anyway when executing the query, rather + * it is only being populated in the FilterEditor. + * + * @param string $column + * @param string|null $value + * + * @return HasNotValue + */ + public static function hasNotValue($column, $value = '') + { + return new HasNotValue($column, $value); + } + + /** + * Get whether the given rule's column is null|doesn't contain any values + * + * @param HasNotValue $rule + * @param object $row + * + * @return bool + */ + public function matchHasNotValue(HasNotValue $rule, $row) + { + return ! $this->matchHasValue($rule, $row); + } + /** * Create a rule that matches rows with a column that **equals** the given value * @@ -451,6 +481,8 @@ protected function performMatch(Rule $rule, $row) return $this->matchUnequal($rule, $row); case $rule instanceof HasValue: return $this->matchHasValue($rule, $row); + case $rule instanceof HasNotValue: + return $this->matchHasNotValue($rule, $row); default: throw new InvalidArgumentException(sprintf( 'Unable to match filter. Rule type %s is unknown', From 4b01b51a3a69ac6e7ce074b866b2f40cade0eac0 Mon Sep 17 00:00:00 2001 From: Yonas Habteab Date: Mon, 15 Nov 2021 16:44:19 +0100 Subject: [PATCH 5/5] FilterTest: Add HasValue & HasNotValue test cases --- tests/FilterTest.php | 37 ++++++++++++++++++++++++++++++++++--- 1 file changed, 34 insertions(+), 3 deletions(-) diff --git a/tests/FilterTest.php b/tests/FilterTest.php index b26b3fc..d960db7 100644 --- a/tests/FilterTest.php +++ b/tests/FilterTest.php @@ -12,21 +12,24 @@ class FilterTest extends TestCase 'problem' => '1', 'service' => 'ping', 'state' => 2, - 'handled' => '1' + 'handled' => '1', + 'host_id' => 1 ], [ 'host' => 'localhost', 'problem' => '1', 'service' => 'www.icinga.com', 'state' => 0, - 'handled' => '0' + 'handled' => '0', + 'host_id' => null ], [ 'host' => 'localhost', 'problem' => '1', 'service' => 'www.icinga.com', 'state' => 1, - 'handled' => '0' + 'handled' => '0', + 'host_id' => 1 ] ]; @@ -183,6 +186,34 @@ public function testUnequalMatchesMultiValuedColumns() ])); } + public function testHasValueMatches() + { + $hasValue = Filter::hasValue('host_id'); + + $this->assertTrue(Filter::match($hasValue, $this->row(0))); + } + + public function testHasValueMismatches() + { + $hasValue = Filter::hasValue('host_id'); + + $this->assertFalse(Filter::match($hasValue, $this->row(1))); + } + + public function testHasNotValueMatches() + { + $hasNotValue = Filter::hasNotValue('host_id'); + + $this->assertTrue(Filter::match($hasNotValue, $this->row(1))); + } + + public function testHasNotValueMismatches() + { + $hasNotValue = Filter::hasNotValue('host_id'); + + $this->assertFalse(Filter::match($hasNotValue, $this->row(0))); + } + public function testGreaterThanMatches() { $greaterThan = Filter::greaterThan('state', 1);