From 23ec092ed1120adf41cd82756df74c9d485aa618 Mon Sep 17 00:00:00 2001 From: Alex Vanderbist Date: Mon, 5 Jul 2021 16:16:37 +0200 Subject: [PATCH 01/11] Add support for cursor pagination --- src/Concerns/AppendsAttributesToResults.php | 8 ++++++ src/QueryBuilder.php | 3 ++- tests/AppendTest.php | 28 ++++++++++++++++++++- 3 files changed, 37 insertions(+), 2 deletions(-) diff --git a/src/Concerns/AppendsAttributesToResults.php b/src/Concerns/AppendsAttributesToResults.php index daa1d8e8..09314e42 100644 --- a/src/Concerns/AppendsAttributesToResults.php +++ b/src/Concerns/AppendsAttributesToResults.php @@ -3,6 +3,7 @@ namespace Spatie\QueryBuilder\Concerns; use Illuminate\Database\Eloquent\Model; +use Illuminate\Pagination\Cursor; use Illuminate\Support\Collection; use Spatie\QueryBuilder\Exceptions\InvalidAppendQuery; @@ -29,6 +30,13 @@ protected function addAppendsToResults(Collection $results) }); } + protected function addAppendsToCursor( $results) + { + return $results->each(function (Model $result) { + return $result->append($this->request->appends()->toArray()); + }); + } + protected function ensureAllAppendsExist() { $appends = $this->request->appends(); diff --git a/src/QueryBuilder.php b/src/QueryBuilder.php index 6c25d4d3..e3a5e7dc 100755 --- a/src/QueryBuilder.php +++ b/src/QueryBuilder.php @@ -3,6 +3,7 @@ namespace Spatie\QueryBuilder; use ArrayAccess; +use Illuminate\Contracts\Pagination\CursorPaginator; use Illuminate\Database\Eloquent\Builder as EloquentBuilder; use Illuminate\Database\Eloquent\Model; use Illuminate\Database\Eloquent\Relations\Relation; @@ -125,7 +126,7 @@ public function __call($name, $arguments) $this->addAppendsToResults($result); } - if ($result instanceof LengthAwarePaginator || $result instanceof Paginator) { + if ($result instanceof LengthAwarePaginator || $result instanceof Paginator || $result instanceof CursorPaginator) { $this->addAppendsToResults(collect($result->items())); } diff --git a/tests/AppendTest.php b/tests/AppendTest.php index ff0fc17b..a24ac529 100644 --- a/tests/AppendTest.php +++ b/tests/AppendTest.php @@ -73,6 +73,28 @@ public function it_can_append_paginates() $this->assertPaginateAttributeLoaded($models, 'FullName'); } + /** @test */ + public function it_can_append_simple_paginates() + { + $models = $this + ->createQueryFromAppendRequest('FullName') + ->allowedAppends('FullName') + ->simplePaginate(); + + $this->assertPaginateAttributeLoaded($models, 'FullName'); + } + + /** @test */ + public function it_can_append_cursor_paginates() + { + $models = $this + ->createQueryFromAppendRequest('FullName') + ->allowedAppends('FullName') + ->cursorPaginate(); + + $this->assertPaginateAttributeLoaded($models, 'FullName'); + } + /** @test */ public function it_guards_against_invalid_appends() { @@ -150,7 +172,11 @@ protected function assertCollectionAttributeLoaded(Collection $collection, strin $this->assertFalse($hasModelWithoutAttributeLoaded, "The `{$attribute}` attribute was expected but not loaded."); } - protected function assertPaginateAttributeLoaded(LengthAwarePaginator $collection, string $attribute) + /** + * @param \Illuminate\Pagination\LengthAwarePaginator|\Illuminate\Contracts\Pagination\Paginator $collection + * @param string $attribute + */ + protected function assertPaginateAttributeLoaded($collection, string $attribute) { $hasModelWithoutAttributeLoaded = $collection ->contains(function (Model $model) use ($attribute) { From cbe5336665106251e4efe911ef824e69bd1e64f6 Mon Sep 17 00:00:00 2001 From: Alex Vanderbist Date: Mon, 5 Jul 2021 16:17:09 +0200 Subject: [PATCH 02/11] Update changelog --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 2c0ae319..e8d6a0ba 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,10 @@ All notable changes to `laravel-query-builder` will be documented in this file +## 3.5.0 - 2021-07-05 + +- add support for cursor pagination + ## 3.4.3 - 2021-07-05 - fix unexpected lowercase appends (#637) From 4e5257be24139836dc092f618d7c73bcb1c00302 Mon Sep 17 00:00:00 2001 From: AlexVanderbist Date: Mon, 5 Jul 2021 14:17:44 +0000 Subject: [PATCH 03/11] Fix styling --- src/Concerns/AppendsAttributesToResults.php | 3 +-- tests/AppendTest.php | 1 - 2 files changed, 1 insertion(+), 3 deletions(-) diff --git a/src/Concerns/AppendsAttributesToResults.php b/src/Concerns/AppendsAttributesToResults.php index 09314e42..0fddd216 100644 --- a/src/Concerns/AppendsAttributesToResults.php +++ b/src/Concerns/AppendsAttributesToResults.php @@ -3,7 +3,6 @@ namespace Spatie\QueryBuilder\Concerns; use Illuminate\Database\Eloquent\Model; -use Illuminate\Pagination\Cursor; use Illuminate\Support\Collection; use Spatie\QueryBuilder\Exceptions\InvalidAppendQuery; @@ -30,7 +29,7 @@ protected function addAppendsToResults(Collection $results) }); } - protected function addAppendsToCursor( $results) + protected function addAppendsToCursor($results) { return $results->each(function (Model $result) { return $result->append($this->request->appends()->toArray()); diff --git a/tests/AppendTest.php b/tests/AppendTest.php index a24ac529..c97607ec 100644 --- a/tests/AppendTest.php +++ b/tests/AppendTest.php @@ -4,7 +4,6 @@ use Illuminate\Database\Eloquent\Model; use Illuminate\Http\Request; -use Illuminate\Pagination\LengthAwarePaginator; use Illuminate\Support\Collection; use Spatie\QueryBuilder\Exceptions\InvalidAppendQuery; use Spatie\QueryBuilder\QueryBuilder; From 880e8641fbde48fa0343f80698dbb8c6e243d7d1 Mon Sep 17 00:00:00 2001 From: Pham Thao <34786441+vanthao03596@users.noreply.github.com> Date: Mon, 6 Sep 2021 14:58:11 +0700 Subject: [PATCH 04/11] Add support callback sort (#654) * Add support sort callback * Add sort callback test --- src/AllowedSort.php | 6 +++ src/Sorts/SortsCallback.php | 25 ++++++++++++ tests/SortsCallbackTest.php | 77 +++++++++++++++++++++++++++++++++++++ 3 files changed, 108 insertions(+) create mode 100644 src/Sorts/SortsCallback.php create mode 100644 tests/SortsCallbackTest.php diff --git a/src/AllowedSort.php b/src/AllowedSort.php index b702eb0b..8d78081f 100644 --- a/src/AllowedSort.php +++ b/src/AllowedSort.php @@ -5,6 +5,7 @@ use Spatie\QueryBuilder\Enums\SortDirection; use Spatie\QueryBuilder\Exceptions\InvalidDirection; use Spatie\QueryBuilder\Sorts\Sort; +use Spatie\QueryBuilder\Sorts\SortsCallback; use Spatie\QueryBuilder\Sorts\SortsField; class AllowedSort @@ -54,6 +55,11 @@ public static function custom(string $name, Sort $sortClass, ?string $internalNa return new static($name, $sortClass, $internalName); } + public static function callback(string $name, $callback, ?string $internalName = null): self + { + return new static($name, new SortsCallback($callback), $internalName); + } + public function getName(): string { return $this->name; diff --git a/src/Sorts/SortsCallback.php b/src/Sorts/SortsCallback.php new file mode 100644 index 00000000..e7fe8e73 --- /dev/null +++ b/src/Sorts/SortsCallback.php @@ -0,0 +1,25 @@ +callback = $callback; + } + + /** {@inheritdoc} */ + public function __invoke(Builder $query, bool $descending, string $property) + { + return call_user_func($this->callback, $query, $descending, $property); + } +} diff --git a/tests/SortsCallbackTest.php b/tests/SortsCallbackTest.php new file mode 100644 index 00000000..3c3d4b29 --- /dev/null +++ b/tests/SortsCallbackTest.php @@ -0,0 +1,77 @@ +models = factory(TestModel::class, 5)->create(); + } + + /** @test */ + public function it_should_sort_by_closure() + { + $sortedModels = $this + ->createQueryFromSortRequest('callback') + ->allowedSorts(AllowedSort::callback('callback', function (Builder $query, $descending) { + $query->orderBy('name', $descending ? 'DESC' : 'ASC'); + })) + ->get(); + + $this->assertQueryExecuted('select * from `test_models` order by `name` asc'); + $this->assertSortedAscending($sortedModels, 'name'); + } + + /** @test */ + public function it_should_sort_by_array_callback() + { + $sortedModels = $this + ->createQueryFromSortRequest('callback') + ->allowedSorts(AllowedSort::callback('callback', [$this, 'sortCallback'])) + ->get(); + + $this->assertQueryExecuted('select * from `test_models` order by `name` asc'); + $this->assertSortedAscending($sortedModels, 'name'); + } + + public function sortCallback(Builder $query, $descending) + { + $query->orderBy('name', $descending ? 'DESC' : 'ASC'); + } + + protected function createQueryFromSortRequest(string $sort): QueryBuilder + { + $request = new Request([ + 'sort' => $sort, + ]); + + return QueryBuilder::for(TestModel::class, $request); + } + + protected function assertQueryExecuted(string $query) + { + $queries = array_map(function ($queryLogItem) { + return $queryLogItem['query']; + }, DB::getQueryLog()); + + $this->assertContains($query, $queries); + } +} From 2d98bf2959eaa2d42ae433da9894ef91f9ad6b48 Mon Sep 17 00:00:00 2001 From: AlexVanderbist Date: Mon, 6 Sep 2021 08:02:54 +0000 Subject: [PATCH 05/11] Fix styling --- tests/SortsCallbackTest.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/tests/SortsCallbackTest.php b/tests/SortsCallbackTest.php index 3c3d4b29..ae7f9ad6 100644 --- a/tests/SortsCallbackTest.php +++ b/tests/SortsCallbackTest.php @@ -3,12 +3,12 @@ namespace Spatie\QueryBuilder\Tests; use Illuminate\Database\Eloquent\Builder; +use Illuminate\Http\Request; use Illuminate\Support\Facades\DB; use Spatie\QueryBuilder\AllowedSort; use Spatie\QueryBuilder\QueryBuilder; use Spatie\QueryBuilder\Tests\Concerns\AssertsCollectionSorting; use Spatie\QueryBuilder\Tests\TestClasses\Models\TestModel; -use Illuminate\Http\Request; class SortsCallbackTest extends TestCase { From 03d8e1307dcb58b16fcc9c4947633fc60ae74802 Mon Sep 17 00:00:00 2001 From: Alex Vanderbist Date: Mon, 6 Sep 2021 10:03:03 +0200 Subject: [PATCH 06/11] Update changelogf --- CHANGELOG.md | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index e8d6a0ba..cd62de49 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -2,6 +2,10 @@ All notable changes to `laravel-query-builder` will be documented in this file +## 3.6.0 - 2021-09-06 + +- add callback sorts (#654) + ## 3.5.0 - 2021-07-05 - add support for cursor pagination From 8bb9ae37876079a78a5635b682658d38c3e27e2e Mon Sep 17 00:00:00 2001 From: Graham Campbell Date: Wed, 17 Nov 2021 15:35:20 +0000 Subject: [PATCH 07/11] Fixed typo preventing the installation of the laravel/framework 7.30.5 security release --- composer.json | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/composer.json b/composer.json index 4d7c37d5..b676271a 100644 --- a/composer.json +++ b/composer.json @@ -22,8 +22,8 @@ "require": { "php": "^7.3|^8.0", "illuminate/database": "^6.20.13|^7.30.4|^8.22.2", - "illuminate/http": "^6.20.13|7.30.4|^8.22.2", - "illuminate/support": "^6.20.13|7.30.4|^8.22.2" + "illuminate/http": "^6.20.13|^7.30.4|^8.22.2", + "illuminate/support": "^6.20.13|^7.30.4|^8.22.2" }, "require-dev": { "ext-json": "*", From 5db8a1e889cec1061c5bd322ea83b0769c5decc3 Mon Sep 17 00:00:00 2001 From: ankurk91 Date: Sun, 9 Jan 2022 18:57:24 +0530 Subject: [PATCH 08/11] fix: php 8.1 support --- src/QueryBuilder.php | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-) diff --git a/src/QueryBuilder.php b/src/QueryBuilder.php index e3a5e7dc..3b019346 100755 --- a/src/QueryBuilder.php +++ b/src/QueryBuilder.php @@ -153,22 +153,22 @@ public function __set($name, $value) $this->subject->{$name} = $value; } - public function offsetExists($offset) + public function offsetExists($offset): bool { return isset($this->subject[$offset]); } - public function offsetGet($offset) + public function offsetGet($offset): mixed { return $this->subject[$offset]; } - public function offsetSet($offset, $value) + public function offsetSet($offset, $value): void { $this->subject[$offset] = $value; } - public function offsetUnset($offset) + public function offsetUnset($offset): void { unset($this->subject[$offset]); } From c2680c5a11b4eb3c16e367f12bffef5aca9d6adb Mon Sep 17 00:00:00 2001 From: Freek Van der Herten Date: Fri, 14 Jan 2022 12:31:42 +0100 Subject: [PATCH 09/11] Update _index.md --- docs/_index.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/_index.md b/docs/_index.md index 3e88c8f7..c2ae5699 100644 --- a/docs/_index.md +++ b/docs/_index.md @@ -2,5 +2,5 @@ title: v3 slogan: Easily build Eloquent queries from API requests. githubUrl: https://github.com/spatie/laravel-query-builder -branch: master +branch: v3 --- From 0e03b34073d0641462cba92a3eeee6caf8fea1c9 Mon Sep 17 00:00:00 2001 From: James Bhatta Date: Thu, 14 Jul 2022 10:39:25 +0545 Subject: [PATCH 10/11] Add version number to installation command in V3 --- docs/installation-setup.md | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/docs/installation-setup.md b/docs/installation-setup.md index ae8f98fb..af998bc6 100644 --- a/docs/installation-setup.md +++ b/docs/installation-setup.md @@ -6,7 +6,7 @@ weight: 4 You can install the package via composer: ```bash -composer require spatie/laravel-query-builder +composer require spatie/laravel-query-builder "^3.0" ``` The package will automatically register its service provider. From f51c5bd587947962f1c85cdc0a011304c9e5753c Mon Sep 17 00:00:00 2001 From: Pawel Bieszczad Date: Mon, 29 Aug 2022 15:48:00 -0400 Subject: [PATCH 11/11] PHP 8.1 Support Backport for https://github.com/spatie/laravel-query-builder/pull/742 & https://github.com/spatie/laravel-query-builder/pull/702 --- src/QueryBuilderRequest.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/src/QueryBuilderRequest.php b/src/QueryBuilderRequest.php index 059d0a4a..6a5d8adb 100644 --- a/src/QueryBuilderRequest.php +++ b/src/QueryBuilderRequest.php @@ -38,7 +38,7 @@ public function includes(): Collection $includeParts = $this->getRequestData($includeParameterName); - if (! is_array($includeParts)) { + if (is_string($includeParts)) { $includeParts = explode(static::getIncludesArrayValueDelimiter(), $this->getRequestData($includeParameterName)); } @@ -53,7 +53,7 @@ public function appends(): Collection $appendParts = $this->getRequestData($appendParameterName); - if (! is_array($appendParts)) { + if (! is_array($appendParts) && ! is_null($appendParts)) { $appendParts = explode(static::getAppendsArrayValueDelimiter(), $appendParts); }