-
Notifications
You must be signed in to change notification settings - Fork 2
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #19 from Icinga/filterable-interface
Introduce interface `Filterable`
- Loading branch information
Showing
4 changed files
with
257 additions
and
0 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,63 @@ | ||
<?php | ||
|
||
namespace ipl\Stdlib\Contract; | ||
|
||
use ipl\Stdlib\Filter; | ||
|
||
interface Filterable | ||
{ | ||
/** | ||
* Get the filter of the query | ||
* | ||
* @return Filter\Chain | ||
*/ | ||
public function getFilter(); | ||
|
||
/** | ||
* Add a filter to the query | ||
* | ||
* Note that this method does not override an already set filter. Instead, multiple calls to this function add | ||
* the specified filter using a {@see Filter\All} chain. | ||
* | ||
* @param Filter\Rule $filter | ||
* | ||
* @return $this | ||
*/ | ||
public function filter(Filter\Rule $filter); | ||
|
||
/** | ||
* Add a filter to the query | ||
* | ||
* Note that this method does not override an already set filter. Instead, multiple calls to this function add | ||
* the specified filter using a {@see Filter\Any} chain. | ||
* | ||
* @param Filter\Rule $filter | ||
* | ||
* @return $this | ||
*/ | ||
public function orFilter(Filter\Rule $filter); | ||
|
||
/** | ||
* Add a filter to the query | ||
* | ||
* Note that this method does not override an already set filter. Instead, multiple calls to this function add | ||
* the specified filter wrapped by a {@see Filter\None} chain and using a {@see Filter\All} chain. | ||
* | ||
* @param Filter\Rule $filter | ||
* | ||
* @return $this | ||
*/ | ||
public function notFilter(Filter\Rule $filter); | ||
|
||
/** | ||
* Add a filter to the query | ||
* | ||
* Note that this method does not override an already set filter. Instead, multiple calls to this function add | ||
* the specified filter wrapped by a {@see Filter\None} chain and using a {@see Filter\Any} chain. | ||
* | ||
* @param Filter\Rule $filter | ||
* | ||
* @return $this | ||
*/ | ||
public function orNotFilter(Filter\Rule $filter); | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,58 @@ | ||
<?php | ||
|
||
namespace ipl\Stdlib; | ||
|
||
trait Filters | ||
{ | ||
/** @var Filter\Chain */ | ||
protected $filter; | ||
|
||
public function getFilter() | ||
{ | ||
return $this->filter ?: Filter::all(); | ||
} | ||
|
||
public function filter(Filter\Rule $filter) | ||
{ | ||
$currentFilter = $this->getFilter(); | ||
if ($currentFilter instanceof Filter\All) { | ||
$this->filter = $currentFilter->add($filter); | ||
} else { | ||
$this->filter = Filter::all($filter); | ||
if (! $currentFilter->isEmpty()) { | ||
$this->filter->insertBefore($currentFilter, $filter); | ||
} | ||
} | ||
|
||
return $this; | ||
} | ||
|
||
public function orFilter(Filter\Rule $filter) | ||
{ | ||
$currentFilter = $this->getFilter(); | ||
if ($currentFilter instanceof Filter\Any) { | ||
$this->filter = $currentFilter->add($filter); | ||
} else { | ||
$this->filter = Filter::any($filter); | ||
if (! $currentFilter->isEmpty()) { | ||
$this->filter->insertBefore($currentFilter, $filter); | ||
} | ||
} | ||
|
||
return $this; | ||
} | ||
|
||
public function notFilter(Filter\Rule $filter) | ||
{ | ||
$this->filter(Filter::none($filter)); | ||
|
||
return $this; | ||
} | ||
|
||
public function orNotFilter(Filter\Rule $filter) | ||
{ | ||
$this->orFilter(Filter::none($filter)); | ||
|
||
return $this; | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,125 @@ | ||
<?php | ||
|
||
namespace ipl\Tests\Stdlib; | ||
|
||
use ipl\Stdlib\Contract\Filterable; | ||
use ipl\Stdlib\Filter; | ||
use ipl\Tests\Stdlib\FiltersTest\FiltersUser; | ||
|
||
class FiltersTest extends \PHPUnit\Framework\TestCase | ||
{ | ||
/** @var Filterable */ | ||
protected $filterable; | ||
|
||
public function setUp() | ||
{ | ||
$this->filterable = new FiltersUser(); | ||
} | ||
|
||
public function testFilterKeepsCurrentHierarchy() | ||
{ | ||
$this->filterable->filter(Filter::equal('', '')); | ||
$this->filterable->filter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::all( | ||
Filter::equal('', ''), | ||
Filter::unequal('', '') | ||
)); | ||
} | ||
|
||
public function testFilterWrapsCurrentHierarchy() | ||
{ | ||
$this->filterable->orFilter(Filter::equal('', '')); | ||
$this->filterable->filter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::all( | ||
Filter::any(Filter::equal('', '')), | ||
Filter::unequal('', '') | ||
)); | ||
} | ||
|
||
public function testOrFilterKeepsCurrentHierarchy() | ||
{ | ||
$this->filterable->orFilter(Filter::equal('', '')); | ||
$this->filterable->orFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::any( | ||
Filter::equal('', ''), | ||
Filter::unequal('', '') | ||
)); | ||
} | ||
|
||
public function testOrFilterWrapsCurrentHierarchy() | ||
{ | ||
$this->filterable->filter(Filter::equal('', '')); | ||
$this->filterable->orFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::any( | ||
Filter::all(Filter::equal('', '')), | ||
Filter::unequal('', '') | ||
)); | ||
} | ||
|
||
public function testNotFilterKeepsCurrentHierarchy() | ||
{ | ||
$this->filterable->notFilter(Filter::equal('', '')); | ||
$this->filterable->notFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::all( | ||
Filter::none(Filter::equal('', '')), | ||
Filter::none(Filter::unequal('', '')) | ||
)); | ||
} | ||
|
||
public function testNotFilterWrapsCurrentHierarchy() | ||
{ | ||
$this->filterable->orFilter(Filter::equal('', '')); | ||
$this->filterable->notFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::all( | ||
Filter::any(Filter::equal('', '')), | ||
Filter::none(Filter::unequal('', '')) | ||
)); | ||
} | ||
|
||
public function testOrNotFilterKeepsCurrentHierarchy() | ||
{ | ||
$this->filterable->orNotFilter(Filter::equal('', '')); | ||
$this->filterable->orNotFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::any( | ||
Filter::none(Filter::equal('', '')), | ||
Filter::none(Filter::unequal('', '')) | ||
)); | ||
} | ||
|
||
public function testOrNotFilterWrapsCurrentHierarchy() | ||
{ | ||
$this->filterable->filter(Filter::equal('', '')); | ||
$this->filterable->orNotFilter(Filter::unequal('', '')); | ||
|
||
$this->assertSameFilterHierarchy(Filter::any( | ||
Filter::all(Filter::equal('', '')), | ||
Filter::none(Filter::unequal('', '')) | ||
)); | ||
} | ||
|
||
protected function assertSameFilterHierarchy(Filter\Chain $expected) | ||
{ | ||
$actual = $this->filterable->getFilter(); | ||
|
||
$checkHierarchy = function ($expected, $actual) use (&$checkHierarchy) { | ||
$expectedArray = iterator_to_array($expected); | ||
$actualArray = iterator_to_array($actual); | ||
foreach ($expectedArray as $key => $rule) { | ||
$this->assertTrue(isset($actualArray[$key])); | ||
$this->assertInstanceOf(get_class($rule), $actualArray[$key]); | ||
if ($rule instanceof Filter\Chain) { | ||
$checkHierarchy($rule, $actualArray[$key]); | ||
} | ||
} | ||
}; | ||
|
||
$checkHierarchy($expected, $actual); | ||
} | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,11 @@ | ||
<?php | ||
|
||
namespace ipl\Tests\Stdlib\FiltersTest; | ||
|
||
use ipl\Stdlib\Contract\Filterable; | ||
use ipl\Stdlib\Filters; | ||
|
||
class FiltersUser implements Filterable | ||
{ | ||
use Filters; | ||
} |