Skip to content

Commit 4a96dc4

Browse files
authored
Merge pull request #743 from teohhanhui/abstractfilter-filterproperty
Add AbstractFilter::filterProperty
2 parents d4b5312 + 3bfb342 commit 4a96dc4

File tree

7 files changed

+435
-466
lines changed

7 files changed

+435
-466
lines changed

src/Bridge/Doctrine/Orm/Filter/AbstractFilter.php

Lines changed: 31 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,6 +21,7 @@
2121
use Psr\Log\LoggerInterface;
2222
use Psr\Log\NullLogger;
2323
use Symfony\Component\HttpFoundation\Request;
24+
use Symfony\Component\HttpFoundation\RequestStack;
2425

2526
/**
2627
* {@inheritdoc}
@@ -33,16 +34,45 @@
3334
abstract class AbstractFilter implements FilterInterface
3435
{
3536
protected $managerRegistry;
37+
protected $requestStack;
3638
protected $logger;
3739
protected $properties;
3840

39-
public function __construct(ManagerRegistry $managerRegistry, LoggerInterface $logger = null, array $properties = null)
41+
public function __construct(ManagerRegistry $managerRegistry, RequestStack $requestStack, LoggerInterface $logger = null, array $properties = null)
4042
{
4143
$this->managerRegistry = $managerRegistry;
44+
$this->requestStack = $requestStack;
4245
$this->logger = $logger ?? new NullLogger();
4346
$this->properties = $properties;
4447
}
4548

49+
/**
50+
* {@inheritdoc}
51+
*/
52+
public function apply(QueryBuilder $queryBuilder, QueryNameGeneratorInterface $queryNameGenerator, string $resourceClass, string $operationName = null)
53+
{
54+
$request = $this->requestStack->getCurrentRequest();
55+
if (null === $request) {
56+
return;
57+
}
58+
59+
foreach ($this->extractProperties($request) as $property => $value) {
60+
$this->filterProperty($property, $value, $queryBuilder, $queryNameGenerator, $resourceClass, $operationName);
61+
}
62+
}
63+
64+
/**
65+
* Passes a property through the filter.
66+
*
67+
* @param string $property
68+
* @param mixed $value
69+
* @param QueryBuilder $queryBuilder
70+
* @param QueryNameGeneratorInterface $queryNameGenerator
71+
* @param string $resourceClass
72+
* @param string|null $operationName
73+
*/
74+
abstract protected function filterProperty(string $property, $value, QueryBuilder $queryBuilder, QueryNameGeneratorInterface $queryNameGenerator, string $resourceClass, string $operationName = null);
75+
4676
/**
4777
* Gets class metadata for the given resource.
4878
*

src/Bridge/Doctrine/Orm/Filter/BooleanFilter.php

Lines changed: 51 additions & 64 deletions
Original file line numberDiff line numberDiff line change
@@ -22,76 +22,20 @@
2222
/**
2323
* Filters the collection by boolean values.
2424
*
25+
* Filters collection on equality of boolean properties. The value is specified
26+
* as one of ( "true" | "false" | "1" | "0" ) in the query.
27+
*
28+
* For each property passed, if the resource does not have such property or if
29+
* the value is not one of ( "true" | "false" | "1" | "0" ) the property is ignored.
30+
*
2531
* @author Amrouche Hamza <[email protected]>
2632
* @author Teoh Han Hui <[email protected]>
2733
*/
2834
class BooleanFilter extends AbstractFilter
2935
{
30-
private $requestStack;
31-
3236
public function __construct(ManagerRegistry $managerRegistry, RequestStack $requestStack, LoggerInterface $logger = null, array $properties = null)
3337
{
34-
parent::__construct($managerRegistry, $logger, $properties);
35-
36-
$this->requestStack = $requestStack;
37-
}
38-
39-
/**
40-
* {@inheritdoc}
41-
*
42-
* Filters collection on equality of boolean properties. The value is specified as one of
43-
* ( "true" | "false" | "1" | "0" ) in the query.
44-
*
45-
* For each property passed, if the resource does not have such property or if the value is not one of
46-
* ( "true" | "false" | "1" | "0" ) the property is ignored.
47-
*/
48-
public function apply(QueryBuilder $queryBuilder, QueryNameGeneratorInterface $queryNameGenerator, string $resourceClass, string $operationName = null)
49-
{
50-
$request = $this->requestStack->getCurrentRequest();
51-
if (null === $request) {
52-
return;
53-
}
54-
55-
$properties = $this->extractProperties($request);
56-
57-
foreach ($properties as $property => $value) {
58-
if (
59-
!$this->isPropertyEnabled($property) ||
60-
!$this->isPropertyMapped($property, $resourceClass) ||
61-
!$this->isBooleanField($property, $resourceClass)
62-
) {
63-
continue;
64-
}
65-
66-
if (in_array($value, ['true', '1'], true)) {
67-
$value = true;
68-
} elseif (in_array($value, ['false', '0'], true)) {
69-
$value = false;
70-
} else {
71-
$this->logger->notice('Invalid filter ignored', [
72-
'exception' => new InvalidArgumentException(sprintf('Invalid boolean value for "%s" property, expected one of ( "%s" )', $property, implode('" | "', [
73-
'true',
74-
'false',
75-
'1',
76-
'0',
77-
]))),
78-
]);
79-
80-
continue;
81-
}
82-
83-
$alias = 'o';
84-
$field = $property;
85-
86-
if ($this->isPropertyNested($property)) {
87-
list($alias, $field) = $this->addJoinsForNestedProperty($property, $alias, $queryBuilder, $queryNameGenerator);
88-
}
89-
$valueParameter = $queryNameGenerator->generateParameterName($field);
90-
91-
$queryBuilder
92-
->andWhere(sprintf('%s.%s = :%s', $alias, $field, $valueParameter))
93-
->setParameter($valueParameter, $value);
94-
}
38+
parent::__construct($managerRegistry, $requestStack, $logger, $properties);
9539
}
9640

9741
/**
@@ -121,6 +65,49 @@ public function getDescription(string $resourceClass) : array
12165
return $description;
12266
}
12367

68+
/**
69+
* {@inheritdoc}
70+
*/
71+
protected function filterProperty(string $property, $value, QueryBuilder $queryBuilder, QueryNameGeneratorInterface $queryNameGenerator, string $resourceClass, string $operationName = null)
72+
{
73+
if (
74+
!$this->isPropertyEnabled($property) ||
75+
!$this->isPropertyMapped($property, $resourceClass) ||
76+
!$this->isBooleanField($property, $resourceClass)
77+
) {
78+
return;
79+
}
80+
81+
if (in_array($value, ['true', '1'], true)) {
82+
$value = true;
83+
} elseif (in_array($value, ['false', '0'], true)) {
84+
$value = false;
85+
} else {
86+
$this->logger->notice('Invalid filter ignored', [
87+
'exception' => new InvalidArgumentException(sprintf('Invalid boolean value for "%s" property, expected one of ( "%s" )', $property, implode('" | "', [
88+
'true',
89+
'false',
90+
'1',
91+
'0',
92+
]))),
93+
]);
94+
95+
return;
96+
}
97+
98+
$alias = 'o';
99+
$field = $property;
100+
101+
if ($this->isPropertyNested($property)) {
102+
list($alias, $field) = $this->addJoinsForNestedProperty($property, $alias, $queryBuilder, $queryNameGenerator);
103+
}
104+
$valueParameter = $queryNameGenerator->generateParameterName($field);
105+
106+
$queryBuilder
107+
->andWhere(sprintf('%s.%s = :%s', $alias, $field, $valueParameter))
108+
->setParameter($valueParameter, $value);
109+
}
110+
124111
/**
125112
* Determines whether the given property refers to a boolean field.
126113
*
@@ -129,7 +116,7 @@ public function getDescription(string $resourceClass) : array
129116
*
130117
* @return bool
131118
*/
132-
private function isBooleanField(string $property, string $resourceClass) : bool
119+
protected function isBooleanField(string $property, string $resourceClass) : bool
133120
{
134121
$propertyParts = $this->splitPropertyParts($property);
135122
$metadata = $this->getNestedMetadata($resourceClass, $propertyParts['associations']);

0 commit comments

Comments
 (0)