Skip to content

Commit 6cfa25a

Browse files
authored
Merge branch 'master' into 263-fix-model-test-state-to-support-custom-eloquent-casts-over-json-columns
2 parents 38c1dbd + c9fdad9 commit 6cfa25a

10 files changed

Lines changed: 186 additions & 73 deletions

File tree

src/Testing/TableTestState.php

Lines changed: 6 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -64,7 +64,12 @@ protected function getChanges(): array
6464
$deletedRecords[] = $originItem;
6565
} else {
6666
$updatedItem = $updatedData->get($updatedItemIndex);
67-
$changes = array_diff_assoc($updatedItem, $originItem);
67+
68+
$changes = array_filter(
69+
array: $updatedItem,
70+
callback: fn ($value, $key) => !array_key_exists($key, $originItem) || $value !== $originItem[$key],
71+
mode: ARRAY_FILTER_USE_BOTH,
72+
);
6873

6974
if (!empty($changes)) {
7075
$updatedRecords[] = array_merge([$this->uniqueKey => $originItem[$this->uniqueKey]], $changes);

src/Traits/EntityControlTrait.php

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,7 @@ public function force($value = true): self
4848
return $this;
4949
}
5050

51-
public function setModel($modelClass): self
51+
protected function setModel($modelClass): self
5252
{
5353
$this->model = new $modelClass();
5454

@@ -255,7 +255,7 @@ public function count($where = []): int
255255
return $result;
256256
}
257257

258-
public function get(array $where = []): Collection
258+
public function get(int|string|array $where = []): Collection
259259
{
260260
$result = $this->getQuery($where)->get();
261261

src/Traits/SearchTrait.php

Lines changed: 8 additions & 42 deletions
Original file line numberDiff line numberDiff line change
@@ -40,7 +40,7 @@ protected function setAdditionalReservedFilters(...$filterNames)
4040
array_push($this->reservedFilters, ...$filterNames);
4141
}
4242

43-
public function paginate(): LengthAwarePaginator
43+
protected function paginate(): LengthAwarePaginator
4444
{
4545
$defaultPerPage = config('defaults.items_per_page');
4646
$perPage = Arr::get($this->filter, 'per_page', $defaultPerPage);
@@ -138,10 +138,10 @@ public function searchQuery(array $filter = []): self
138138
$this->filterLess($field, true, $fieldName);
139139
} elseif (Str::endsWith($fieldName, '_from')) {
140140
$field = Str::replace('_from', '', $fieldName);
141-
$this->filterFrom($field, false, $fieldName);
141+
$this->filterGreater($field, false, $fieldName);
142142
} elseif (Str::endsWith($fieldName, '_to')) {
143143
$field = Str::replace('_to', '', $fieldName);
144-
$this->filterTo($field, false, $fieldName);
144+
$this->filterLess($field, false, $fieldName);
145145
} elseif (Str::endsWith($fieldName, '_in_list')) {
146146
$field = Str::replace('_in_list', '', $fieldName);
147147
$this->filterByList($field, $fieldName);
@@ -169,7 +169,7 @@ public function getSearchResults(): LengthAwarePaginator
169169
return $this->wrapPaginatedData($data);
170170
}
171171

172-
public function wrapPaginatedData(Collection $data): LengthAwarePaginator
172+
protected function wrapPaginatedData(Collection $data): LengthAwarePaginator
173173
{
174174
$total = $data->count();
175175

@@ -183,7 +183,7 @@ public function wrapPaginatedData(Collection $data): LengthAwarePaginator
183183
return $this->getModifiedPaginator($paginator);
184184
}
185185

186-
public function getModifiedPaginator(LengthAwarePaginator $paginator): LengthAwarePaginator
186+
protected function getModifiedPaginator(LengthAwarePaginator $paginator): LengthAwarePaginator
187187
{
188188
$collection = $paginator->getCollection();
189189

@@ -215,30 +215,6 @@ protected function getDesc(bool $isDesc): string
215215
return ($isDesc) ? 'DESC' : 'ASC';
216216
}
217217

218-
/** @deprecated use filterGreater instead */
219-
public function filterMoreThan(string $field, $value): self
220-
{
221-
return $this->filterValue($field, '>', $value);
222-
}
223-
224-
/** @deprecated use filterLess instead */
225-
public function filterLessThan(string $field, $value): self
226-
{
227-
return $this->filterValue($field, '<', $value);
228-
}
229-
230-
/** @deprecated use filterGreater instead */
231-
public function filterMoreOrEqualThan(string $field, $value): self
232-
{
233-
return $this->filterValue($field, '>=', $value);
234-
}
235-
236-
/** @deprecated use filterLess instead */
237-
public function filterLessOrEqualThan(string $field, $value): self
238-
{
239-
return $this->filterValue($field, '<=', $value);
240-
}
241-
242218
public function filterValue(string $field, string $sign, $value): self
243219
{
244220
if (!empty($value)) {
@@ -274,7 +250,7 @@ public function withCount(array|string $relations): self
274250

275251
protected function getQuerySearchCallback(string $field, string $mask): Closure
276252
{
277-
return function ($query) use ($field, $mask) {
253+
return function (Query $query) use ($field, $mask) {
278254
$databaseDriver = config('database.default');
279255
$value = ($databaseDriver === 'pgsql')
280256
? pg_escape_string($this->filter['query'])
@@ -284,16 +260,12 @@ protected function getQuerySearchCallback(string $field, string $mask): Closure
284260
? 'ilike'
285261
: 'like';
286262

263+
$field = $query->qualifyColumn($field);
264+
287265
$query->orWhere($field, $operator, DB::raw($value));
288266
};
289267
}
290268

291-
/** @deprecated use filterGreater instead */
292-
public function filterFrom(string $field, bool $isStrict = true, ?string $filterName = null): self
293-
{
294-
return $this->filterGreater($field, $isStrict, $filterName);
295-
}
296-
297269
public function filterGreater(string $field, bool $isStrict = true, ?string $filterName = null): self
298270
{
299271
$filterName = empty($filterName) ? 'from' : $filterName;
@@ -306,12 +278,6 @@ public function filterGreater(string $field, bool $isStrict = true, ?string $fil
306278
return $this;
307279
}
308280

309-
/** @deprecated use filterLess instead */
310-
public function filterTo(string $field, bool $isStrict = true, ?string $filterName = null): self
311-
{
312-
return $this->filterLess($field, $isStrict, $filterName);
313-
}
314-
315281
public function filterLess(string $field, bool $isStrict = true, ?string $filterName = null): self
316282
{
317283
$filterName = (empty($filterName)) ? 'to' : $filterName;

tests/EntityControlTraitTest.php

Lines changed: 32 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -652,7 +652,7 @@ public function testCount()
652652
$this->assertSettablePropertiesReset(self::$testRepositoryClass);
653653
}
654654

655-
public function testGet()
655+
public function testGet(): void
656656
{
657657
$this->mockGet(self::$selectResult);
658658

@@ -667,7 +667,37 @@ public function testGet()
667667
$this->assertSettablePropertiesReset(self::$testRepositoryClass);
668668
}
669669

670-
public function testGetEmptyResult()
670+
public function testGetByIntPrimaryKey(): void
671+
{
672+
$this->mockGet(self::$selectResult);
673+
674+
self::$testRepositoryClass
675+
->withTrashed()
676+
->onlyTrashed()
677+
->force()
678+
->with('relation')
679+
->withCount('relation')
680+
->get(1);
681+
682+
$this->assertSettablePropertiesReset(self::$testRepositoryClass);
683+
}
684+
685+
public function testGetByStringPrimaryKey(): void
686+
{
687+
$this->mockGet(self::$selectResult, ['test_id_1']);
688+
689+
self::$testRepositoryClass
690+
->withTrashed()
691+
->onlyTrashed()
692+
->force()
693+
->with('relation')
694+
->withCount('relation')
695+
->get('test_id_1');
696+
697+
$this->assertSettablePropertiesReset(self::$testRepositoryClass);
698+
}
699+
700+
public function testGetEmptyResult(): void
671701
{
672702
$this->mockSelectById(
673703
'select "test_models".*, (select count(*) from "relation_models" '

tests/SearchTraitTest.php

Lines changed: 20 additions & 7 deletions
Original file line numberDiff line numberDiff line change
@@ -274,24 +274,37 @@ public function testSearchQueryWithListFilters()
274274
->getSearchResults();
275275
}
276276

277-
public function testSearchQueryWithFiltersFunctions()
277+
public function testSearchQueryWithChainedFilters()
278278
{
279279
$this->shouldSettablePropertiesBeResetProperty->setValue($this->testRepositoryClass, false);
280280

281281
$this->mockGetSearchResultWithFilters(self::$selectResult);
282282

283+
$this->callEncapsulatedMethod(
284+
$this->testRepositoryClass,
285+
'setAdditionalReservedFilters',
286+
'date_greater',
287+
'date_less',
288+
'updated_at_greater',
289+
'updated_at_less',
290+
);
291+
283292
$this->testRepositoryClass
284293
->searchQuery([
285294
'user_id_in_list' => [1, 2],
286295
'user_id_not_in_list' => [3, 4],
287296
'name' => 'text_name',
297+
'date_greater' => Carbon::now(),
298+
'date_less' => Carbon::now(),
299+
'updated_at_greater' => Carbon::now(),
300+
'updated_at_less' => Carbon::now(),
288301
])
289-
->filterMoreOrEqualThan('date', Carbon::now())
290-
->filterLessOrEqualThan('date', Carbon::now())
291-
->filterMoreOrEqualThan('created_at', Carbon::now())
292-
->filterLessOrEqualThan('created_at', Carbon::now())
293-
->filterMoreThan('updated_at', Carbon::now())
294-
->filterLessThan('updated_at', Carbon::now())
302+
->filterGreater('date', false, 'date_greater')
303+
->filterLess('date', false, 'date_less')
304+
->filterValue('created_at', '>=', Carbon::now())
305+
->filterValue('created_at', '<=', Carbon::now())
306+
->filterGreater('updated_at', true, 'updated_at_greater')
307+
->filterLess('updated_at', true, 'updated_at_less')
295308
->getSearchResults();
296309
}
297310
}

tests/TableTestStateTest.php

Lines changed: 16 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -102,4 +102,20 @@ public function testAssertChangesWithCustomPrimaryKey()
102102

103103
$modelTestState->assertChangesEqualsFixture('assertion_fixture_primary_key_set');
104104
}
105+
106+
public function testAssertChangesDetectsFalsyToNullTransitions()
107+
{
108+
$initialDatasetMock = collect($this->getJsonFixture('falsy_to_null_transitions/initial_dataset'));
109+
$changedDatasetMock = collect($this->getJsonFixture('falsy_to_null_transitions/changed_dataset'));
110+
111+
$this->mockGettingDatasetForChanges($changedDatasetMock, $initialDatasetMock, 'test_models', 'name');
112+
113+
$modelTestState = new TableTestState(
114+
tableName: 'test_models',
115+
jsonFields: ['json_field', 'castable_field'],
116+
uniqueKey: 'name',
117+
);
118+
119+
$modelTestState->assertChangesEqualsFixture('assertion_fixture_falsy_to_null_transitions');
120+
}
105121
}
Lines changed: 18 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,18 @@
1+
{
2+
"updated": [
3+
{
4+
"name": "name1",
5+
"some_flag": false,
6+
"some_numeric_value": 0,
7+
"some_string_value": ""
8+
},
9+
{
10+
"name": "name2",
11+
"some_flag": true,
12+
"some_numeric_value": 0,
13+
"some_string_value": "value"
14+
}
15+
],
16+
"created": [],
17+
"deleted": []
18+
}
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
[
2+
{
3+
"name": "name1",
4+
"some_flag": false,
5+
"some_numeric_value": 0.0,
6+
"some_string_value": "",
7+
"json_field": "{\"field1\": \"updated_value\", \"field2\": [2, 3], \"field3\": {\"one\": 1, \"two\": 2}}",
8+
"castable_field": "{\"field1\": \"value\", \"field2\": [2, 3], \"field3\": {\"one\": 1, \"two\": 2}}",
9+
"created_at": "2018-10-10 10:10:10",
10+
"updated_at": "2018-10-10 10:10:10"
11+
},
12+
{
13+
"name": "name2",
14+
"some_flag": true,
15+
"some_numeric_value": 0,
16+
"some_string_value": "value",
17+
"json_field": "{\"field1\": \"added_value\"}",
18+
"castable_field": "{\"one\": \"first value\", \"two\": \"second value\"}",
19+
"created_at": "2018-10-10 10:10:10",
20+
"updated_at": "2018-10-10 10:10:10"
21+
},
22+
{
23+
"name": "name3",
24+
"some_flag": null,
25+
"some_numeric_value": null,
26+
"some_string_value": null,
27+
"castable_field": "{}",
28+
"json_field": "{}",
29+
"created_at": "2018-10-10 10:10:10",
30+
"updated_at": "2018-10-10 10:10:10"
31+
}
32+
]
Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
[
2+
{
3+
"name": "name1",
4+
"some_flag": null,
5+
"some_numeric_value": null,
6+
"some_string_value": null,
7+
"json_field": "{\"field1\": \"updated_value\", \"field2\": [2, 3], \"field3\": {\"one\": 1, \"two\": 2}}",
8+
"castable_field": "{\"field1\": \"value\", \"field2\": [2, 3], \"field3\": {\"one\": 1, \"two\": 2}}",
9+
"created_at": "2018-10-10 10:10:10",
10+
"updated_at": "2018-10-10 10:10:10"
11+
},
12+
{
13+
"name": "name2",
14+
"some_flag": null,
15+
"some_numeric_value": null,
16+
"some_string_value": null,
17+
"json_field": "{\"field1\": \"added_value\"}",
18+
"castable_field": "{\"one\": \"first value\", \"two\": \"second value\"}",
19+
"created_at": "2018-10-10 10:10:10",
20+
"updated_at": "2018-10-10 10:10:10"
21+
},
22+
{
23+
"name": "name3",
24+
"some_flag": null,
25+
"some_numeric_value": null,
26+
"some_string_value": null,
27+
"castable_field": "{}",
28+
"json_field": "{}",
29+
"created_at": "2018-10-10 10:10:10",
30+
"updated_at": "2018-10-10 10:10:10"
31+
}
32+
]

0 commit comments

Comments
 (0)