Skip to content

Commit be96c4a

Browse files
committed
Use 'conflictsWith' in Filterer
1 parent 1834bd1 commit be96c4a

2 files changed

Lines changed: 96 additions & 0 deletions

File tree

src/Filterer.php

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -123,12 +123,15 @@ public function execute(array $input) : FilterResponse
123123
$leftOverInput = array_diff_key($input, $this->specification);
124124

125125
$errors = [];
126+
$conflicts = [];
126127
foreach ($inputToFilter as $field => $input) {
127128
$filters = $this->specification[$field];
128129
self::assertFiltersIsAnArray($filters, $field);
129130
$customError = self::validateCustomError($filters, $field);
130131
unset($filters[FilterOptions::IS_REQUIRED]);//doesn't matter if required since we have this one
131132
unset($filters[FilterOptions::DEFAULT_VALUE]);//doesn't matter if there is a default since we have a value
133+
$conflicts = self::extractConflicts($filters, $field, $conflicts);
134+
132135
foreach ($filters as $filter) {
133136
self::assertFilterIsNotArray($filter, $field);
134137

@@ -165,6 +168,7 @@ public function execute(array $input) : FilterResponse
165168
}
166169

167170
$errors = self::handleAllowUnknowns($this->allowUnknowns, $leftOverInput, $errors);
171+
$errors = self::handleConflicts($inputToFilter, $conflicts, $errors);
168172

169173
return new FilterResponse($inputToFilter, $errors, $leftOverInput);
170174
}
@@ -179,6 +183,40 @@ public function getAliases() : array
179183
return $this->filterAliases ?? self::$registeredFilterAliases;
180184
}
181185

186+
private static function extractConflicts(array &$filters, string $field, array $conflicts) : array
187+
{
188+
$conflictsWith = $filters[FilterOptions::CONFLICTS_WITH] ?? null;
189+
unset($filters[FilterOptions::CONFLICTS_WITH]);
190+
if ($conflictsWith === null) {
191+
return $conflicts;
192+
}
193+
194+
if (!is_array($conflictsWith)) {
195+
$conflictsWith = [$conflictsWith];
196+
}
197+
198+
$conflicts[$field] = $conflictsWith;
199+
200+
return $conflicts;
201+
}
202+
203+
private static function handleConflicts(array $inputToFilter, array $conflicts, array $errors)
204+
{
205+
foreach (array_keys($inputToFilter) as $field) {
206+
if (!array_key_exists($field, $conflicts)) {
207+
continue;
208+
}
209+
210+
foreach ($conflicts[$field] as $conflictsWith) {
211+
if (array_key_exists($conflictsWith, $inputToFilter)) {
212+
$errors[] = "Field '{$field}' cannot be given if field '{$conflictsWith}' is present.";
213+
}
214+
}
215+
}
216+
217+
return $errors;
218+
}
219+
182220
/**
183221
* @return array
184222
*

tests/FiltererTest.php

Lines changed: 58 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -238,6 +238,64 @@ public function provideValidFilterData() : array
238238
'options' => [],
239239
'result' => [true, ['field' => 'a string with newlines and extra spaces'], null, []],
240240
],
241+
'conflicts with single' => [
242+
'spec' => [
243+
'fieldOne' => [FilterOptions::CONFLICTS_WITH => 'fieldThree', ['string']],
244+
'fieldTwo' => [['string']],
245+
'fieldThree' => [FilterOptions::CONFLICTS_WITH => 'fieldOne', ['string']],
246+
],
247+
'input' => [
248+
'fieldOne' => 'abc',
249+
'fieldTwo' => '123',
250+
'fieldThree' => 'xyz',
251+
],
252+
'options' => [],
253+
'result' => [
254+
false,
255+
null,
256+
"Field 'fieldOne' cannot be given if field 'fieldThree' is present.\n"
257+
. "Field 'fieldThree' cannot be given if field 'fieldOne' is present.",
258+
[],
259+
],
260+
],
261+
'conflicts with multiple' => [
262+
'spec' => [
263+
'fieldOne' => [FilterOptions::CONFLICTS_WITH => ['fieldTwo', 'fieldThree'], ['string']],
264+
'fieldTwo' => [['string']],
265+
'fieldThree' => [['string']],
266+
],
267+
'input' => [
268+
'fieldOne' => 'abc',
269+
'fieldTwo' => '123',
270+
],
271+
'options' => [],
272+
'result' => [
273+
false,
274+
null,
275+
"Field 'fieldOne' cannot be given if field 'fieldTwo' is present.",
276+
[],
277+
],
278+
],
279+
'conflicts with not present' => [
280+
'spec' => [
281+
'fieldOne' => [FilterOptions::CONFLICTS_WITH => 'fieldThree', ['string']],
282+
'fieldTwo' => [['string']],
283+
],
284+
'input' => [
285+
'fieldOne' => 'abc',
286+
'fieldTwo' => '123',
287+
],
288+
'options' => [],
289+
'result' => [
290+
true,
291+
[
292+
'fieldOne' => 'abc',
293+
'fieldTwo' => '123',
294+
],
295+
null,
296+
[],
297+
],
298+
],
241299
];
242300
}
243301

0 commit comments

Comments
 (0)