bakhadyrovf / easy-filter
此包允许您使用自己的方法过滤查询。
Requires
- php: >=8.0
README
这是一个通过用户自定义方法过滤查询的包。
依赖项
- PHP >= 8.0
- Laravel >= 9.0
安装
composer require bakhadyrovf/easy-filter
Laravel使用包自动发现,因此不需要您手动添加ServiceProvider。
使用发布命令将包配置复制到本地配置。
php artisan vendor:publish --tag=easy-filter-config
用法
重要
默认情况下,过滤器的命名空间为App\Filters
,每个过滤器类在创建之前都期望您已经有一个遵循以下命名空间标准的强类型Eloquent模型
首先,您必须创建一个过滤器类
php artisan make:filter ArticleFilter
此命令将在您项目的app/Filters
文件夹中创建ArticleFilter
类。
此命令还将把Filterable
特质添加到您的Eloquent Model
。
您可以在配置文件中更改基本文件夹的名称(命名空间
也会相应更改)
<?php return [ /** * Base folder's name in app directory. * Default: Filters */ 'base-folder' => 'Filters' ];
此外,您还可以使用子文件夹生成过滤器类
php artisan make:filter Dashboard/ArticleFilter
过滤器类将位于app/Filters/Dashboard
文件夹。
新创建的类将如下所示
<?php namespace App\Filters\ArticleFilter; use Bakhadyrovf\EasyFilter\QueryFilter; class ArticleFilter extends QueryFilter { }
如果您的Model
或Filter
的命名空间与上述不匹配,您可以使用--model
选项:例如,我们有一个命名空间为App\Models\Article
的模型,我们希望创建一个命名空间为App\Filters\Dashboard\ArticleFilter
的过滤器类
php artisan make:filter Dashboard/ArticleFilter --model=App\\Models\\Article
为了使不与模型命名空间匹配的过滤器,您必须在您的App\Models\Article
类中添加方法
<?php namespace App\Models\Admin; use Bakhadyrovf\EasyFilter\Traits\Filterable; use Illuminate\Database\Eloquent\Factories\HasFactory; use Illuminate\Database\Eloquent\Model; use App\Filters\Dashboard\ArticleFilter; class Discount extends Model { use HasFactory, Filterable; public function provideFilter() { return ArticleFilter::class; } }
此方法将指向特定的过滤器类。
现在,您可以在过滤器类中编写自己的方法。让我们添加第一个方法并尝试过滤我们的查询。在app/Filters/ArticleFilter
class ArticleFilter extends QueryFilter { public function title(Builder $builder, $value) { return $builder->where('title', 'LIKE', $value . '%'); } }
方法参数
- $builder - Illuminate\Database\Eloquent\Builder
- $value - 从请求中获取的值
您可以使用您Eloquent Model
上的filter()
方法尝试过滤查询。这是基本的Eloquent Scope,因此您可以像通常一样使用它。在app\Http\Controllers\ArticleController
use App\Models\Article; use Illuminate\Http\Request; class ArticleController extends Controller { public function index(Request $request) { $articles = Article::filter() ->orderByDesc('id') ->get(); return $articles; } }
所有负责过滤的参数都必须在查询中
example.com/articles?title=some-title
如果您的参数是蛇形命名,您不需要创建相同命名的参数的方法,因为它不匹配php标准。包本身会将参数转换为驼峰式命名。
例如,如果您的参数是first_name
example.com/articles?first_name=some-value
方法将如下所示
Class ArticleFilter extends QueryFilter { public function firstName(Builder $builder, $value) { return $builder->where('first_name', 'LIKE', $value . '%'); } }
多个值
如果您的参数可以接受多个值,您可以使用括号
example.com/articles?category_ids=[1,2,3,4,5]
通常,这些值将在方法的第二个参数中
Class ArticleFilter extends QueryFilter { public function categoryIds(Builder $builder, $values) { return $builder->whereHas('categories', function ($query) use ($values) { return $query->whereIn('id', $values); }); } }
忽略参数
例如,如果您想忽略post_ids
参数的过滤
https://example.com/users?name=Firuzbek&post_ids=[1,10,25]
您可以将方法名称或查询参数的异常数组作为filter()
方法的参数提供
use App\Models\User; use Illuminate\Http\Request; class UserController extends Controller { public function index(Request $request) { $users = User::active() ->filter(['postIds']) // Or post_ids ->orderByDesc('created_at') ->get(); return $users; } }
多个过滤器
如果您有一个模型的多个过滤器类,您可以提供特定的过滤器类作为第二个参数。即使您在模型上有一个provideFilter()
方法,也会使用此过滤器类
use App\Models\Post; use App\Filters\Dashboard\PostFilter; use Illuminate\Http\Request; class UserController extends Controller { public function index(Request $request) { $posts = Post::active() ->filter(['sort_by'], PostFilter::class) ->orderByDesc('created_at') ->get(); return $posts; } }