PHPackages                             altrntv/eloquent-filter - PHPackages - PHPackages  [Skip to content](#main-content)[PHPackages](/)[Directory](/)[Categories](/categories)[Trending](/trending)[Leaderboard](/leaderboard)[Changelog](/changelog)[Analyze](/analyze)[Collections](/collections)[Log in](/login)[Sign up](/register)

1. [Directory](/)
2. /
3. [Database &amp; ORM](/categories/database)
4. /
5. altrntv/eloquent-filter

ActiveLibrary[Database &amp; ORM](/categories/database)

altrntv/eloquent-filter
=======================

Eloquent Filter for Laravel Models.

v2.1.1(1w ago)1186↓52.1%[1 issues](https://github.com/altrntv/eloquent-filter/issues)MITPHPPHP ^8.3CI passing

Since Nov 9Pushed 1w agoCompare

[ Source](https://github.com/altrntv/eloquent-filter)[ Packagist](https://packagist.org/packages/altrntv/eloquent-filter)[ Docs](https://github.com/altrntv/eloquent-filter)[ RSS](/packages/altrntv-eloquent-filter/feed)WikiDiscussions main Synced today

READMEChangelog (10)Dependencies (24)Versions (12)Used By (0)

Eloquent Filter
===============

[](#eloquent-filter)

[![Packagist Version](https://camo.githubusercontent.com/9abff6589220dae206b79298a110fc2b15aa4c1d3ae207b0ef6a419110747ad3/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f762f616c74726e74762f656c6f7175656e742d66696c7465723f7374796c653d666c61742d737175617265266c6162656c3d72656c65617365)](https://camo.githubusercontent.com/9abff6589220dae206b79298a110fc2b15aa4c1d3ae207b0ef6a419110747ad3/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f762f616c74726e74762f656c6f7175656e742d66696c7465723f7374796c653d666c61742d737175617265266c6162656c3d72656c65617365)[![GitHub Actions Workflow Status](https://camo.githubusercontent.com/870eae11847034854484b900a40ec643322a8aca0feaf4c8cf22312181c2505d/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f616374696f6e732f776f726b666c6f772f7374617475732f616c74726e74762f656c6f7175656e742d66696c7465722f746573742e796d6c3f6272616e63683d6d61696e267374796c653d666c61742d737175617265266c6162656c3d74657374)](https://camo.githubusercontent.com/870eae11847034854484b900a40ec643322a8aca0feaf4c8cf22312181c2505d/68747470733a2f2f696d672e736869656c64732e696f2f6769746875622f616374696f6e732f776f726b666c6f772f7374617475732f616c74726e74762f656c6f7175656e742d66696c7465722f746573742e796d6c3f6272616e63683d6d61696e267374796c653d666c61742d737175617265266c6162656c3d74657374)[![Packagist Downloads](https://camo.githubusercontent.com/c31324b9bc38ad5c04b5b8cab7d20b103692ca074e9237eec248ed7c67252a57/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f64742f616c74726e74762f656c6f7175656e742d66696c7465723f7374796c653d666c61742d737175617265)](https://camo.githubusercontent.com/c31324b9bc38ad5c04b5b8cab7d20b103692ca074e9237eec248ed7c67252a57/68747470733a2f2f696d672e736869656c64732e696f2f7061636b61676973742f64742f616c74726e74762f656c6f7175656e742d66696c7465723f7374796c653d666c61742d737175617265)

Eloquent Filter provides a clean and expressive way to apply dynamic, request-driven filters to your Eloquent models. It automatically maps incoming request parameters to filter methods, making complex query filtering simple and maintainable.

Table of Contents
-----------------

[](#table-of-contents)

- [Requirements](#requirements)
- [Installation](#installation)
- [Basic Usage Filters](#basic-usage-filters)
    - [Creating a Filter](#creating-a-filter-class)
    - [Controller Example](#controller-example)
    - [Validating Filters](#validating-filters)
    - [Casting Filter Values](#casting-filter-values)
    - [Joining Parameters](#joining-parameters)
- [Basic Usage Sorts](#basic-usage-sorts)
    - [Creating a Sort Class](#creating-a-sort-class)
    - [Request Example](#request-example)
    - [Applying Sort](#applying-sort)
- [Testing](#testing)
- [Contributing](#contributing)
- [Credits](#credits)
- [License](#license)

Requirements
------------

[](#requirements)

This package requires:

- PHP ^8.3
- Laravel 11 / 12 / 13

Installation
------------

[](#installation)

Install the package via Composer:

```
composer require altrntv/eloquent-filter
```

Basic Usage Filters
-------------------

[](#basic-usage-filters)

Extend your model with the `Filterable` trait:

```
use Altrntv\EloquentFilter\Traits\Filterable;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Foundation\Auth\User as Authenticatable;

/**
 * @method static Builder|self filter(array $parameters)
 * @method static Builder|self filterByRequest()
 */
class User extends Authenticatable
{
    use Filterable;
}
```

After adding the trait, your model gains two new query builder methods:

- `filter(array $parameters)` — Applies filters using a key-value array.
- `filterByRequest()` — Automatically applies filters from the current HTTP request, using the key defined in your configuration.

---

### Creating a Filter Class

[](#creating-a-filter-class)

You can create a filter class using the Artisan command:

```
php artisan make:eloquent-filter UserFilter
```

Then, define methods corresponding to each filterable parameter. Each method should accept a value and modify the query builder accordingly.

```
use Altrntv\EloquentFilter\Filters\EloquentFilter;
use Illuminate\Database\Eloquent\Builder;

class UserFilter extends EloquentFilter
{
    public function name(string $value): void
    {
        $this->builder
            ->whereLike('name', "%{$value}%");
    }

    public function age(string $value): void
    {
        $this->builder
            ->where('age', '>=', $value);
    }
}
```

---

### Controller Example

[](#controller-example)

```
use App\Models\User;
use App\Http\Requests\UserIndexRequest;
use Illuminate\Http\JsonResponse;

final class UserController extends Controller
{
    public function index(UserIndexRequest $request): JsonResponse
    {
        $users = User::query()
            ->filterByRequest()
            ->get();

        return $users->toResourceCollection();
    }
}
```

---

### Validating Filters

[](#validating-filters)

It’s recommended to validate incoming filter parameters in your request class:

```
use Illuminate\Foundation\Http\FormRequest;

class UserIndexRequest extends FormRequest
{
    public function rules(): array
    {
        return [
            'filter.name' => ['string', 'max:255'],
            'filter.age' => ['integer', 'min:0', 'max:150'],
        ];
    }
}
```

---

### Casting Filter Values

[](#casting-filter-values)

Eloquent Filter supports the following cast types: `integer`, `string`, `boolean`, and `array`.

To cast a value, define it in the $casts property of your filter:

```
use Altrntv\EloquentFilter\Filters\EloquentFilter;
use Illuminate\Database\Eloquent\Builder;

class UserFilter extends EloquentFilter
{
    protected array $casts = [
        'age' => 'integer',
        'roles' => 'array',
    ];

    public function age(int $value): void
    {
        $this->builder
            ->where('age', '>=', $value);
    }

    public function roles(array $value): void
    {
        $this->builder
            ->whereIn('roles', $value);
    }
}
```

And in your form request:

```
use Illuminate\Foundation\Http\FormRequest;

class UserIndexRequest extends FormRequest
{
    public function rules(): array
    {
        return [
            'filter.name' => ['string', 'max:255'],
            'filter.age' => ['integer', 'min:0', 'max:150'],
            'filter.roles' => ['string', 'regex:/^\d+(,\d+)*$/'],
        ];
    }
}
```

A typical request might look like this:

```
GET /users?filter[name]=John&filter[age]=18&filter[roles]=1,2,4

```

---

### Joining Parameters

[](#joining-parameters)

Sometimes multiple request parameters represent a single logical concept. For example, `vip_at_from` and `vip_at_to` form a date range.

Eloquent Filter allows you to group multiple parameters under a single key using the `$joinParameters` property.

All keys inside the group are:

- **converted to camelCase** (e.g., `vip_at_from` → `vipAtFrom`),
- **passed to your filter method via argument unpacking (`...`)**, so the method’s argument names must match the camelCased keys.

#### Example Filter Class

[](#example-filter-class)

```
use Altrntv\EloquentFilter\Filters\EloquentFilter;
use Illuminate\Database\Eloquent\Builder;

class UserFilter extends EloquentFilter
{
    protected array $joinParameters = [
        'vip_at' => ['vip_at_from', 'vip_at_to'],
    ];

    public function vipAt(string $vipAtFrom, string $vipAtTo): void
    {
        $this->builder
            ->where(function (Builder $query) use ($vipAtFrom, $vipAtTo) {
                $query
                    ->whereDate('vip_from', '=', $vipAtFrom);
            });
    }
}
```

#### Request Example

[](#request-example)

```
GET /users?filter[vip_at_from]=2024-01-01&filter[vip_at_to]=2024-12-31

```

#### Transformed Parameters

[](#transformed-parameters)

```
$this->parameters = [
    'vip_at' => [
        'vipAtFrom' => '2024-01-01',
        'vipAtTo' => '2024-12-31',
    ],
]
```

*This approach is especially useful for handling ranges or multipart filters, keeping your request parameters clean and your filter methods readable.*

Basic Usage Sorts
-----------------

[](#basic-usage-sorts)

Eloquent Filter now supports sorting via the `Sortable` trait and `EloquentSort` classes. This allows you to apply dynamic sorting based on HTTP requests or string parameters.

Extend your model with the `Sortable` trait:

```
use Altrntv\EloquentFilter\Traits\Sortable;
use Illuminate\Database\Eloquent\Builder;
use Illuminate\Foundation\Auth\User as Authenticatable;

/**
 * @method static Builder|self sort(string $parameters)
 * @method static Builder|self sortByRequest()
 */
class User extends Authenticatable
{
    use Sortable;
}
```

After adding the trait, your model gains two query builder methods:

- `sort(string $parameters)` — Apply sorting using a comma-separated string of columns.
- `sortByRequest()` — Automatically applies sorting from the current HTTP request, using the key defined in your configuration.

---

### Creating a Sort Class

[](#creating-a-sort-class)

You can create a sort class using the Artisan command:

```
php artisan make:eloquent-sort UserSort
```

```
use Altrntv\EloquentFilter\Sorts\EloquentSort;
use Illuminate\Database\Eloquent\Builder;

class UserSort extends EloquentSort
{
    public function name(string $direction): void
    {
        $this->builder
            ->orderBy('name', $direction);
    }

    public function age(string $direction): void
    {
        $this->builder
            ->orderBy('age', $direction);
    }
}
```

---

### Request Example

[](#request-example-1)

```
GET /users?sort_by=name,-age

```

- `name` — ascending
- `-age` — descending

The sort string is split by the configured separator (`,` by default), and the direction is inferred from the `-` prefix.

---

### Applying Sort

[](#applying-sort)

In controller:

```
$users = User::query()
    ->sortByRequest()
    ->get();
```

Or using a manual string:

```
$users = User::query()
    ->sort('name,-age')
    ->get();
```

Testing
-------

[](#testing)

```
composer test
```

Contributing
------------

[](#contributing)

Contributions are welcome! If you’d like to improve this package, please fork the repository and open a pull request. Bug fixes, new features, and documentation improvements are all appreciated.

Credits
-------

[](#credits)

- [Pavel Dykin](https://github.com/altrntv)
- [All Contributors](../../contributors)

License
-------

[](#license)

The MIT License (MIT). Please see [License File](LICENSE.md) for more information.

###  Health Score

42

↓

FairBetter than 88% of packages

Maintenance78

Regular maintenance activity

Popularity15

Limited adoption so far

Community6

Small or concentrated contributor base

Maturity57

Maturing project, gaining track record

 Bus Factor1

Top contributor holds 100% of commits — single point of failure

How is this calculated?**Maintenance (25%)** — Last commit recency, latest release date, and issue-to-star ratio. Uses a 2-year decay window.

**Popularity (30%)** — Total and monthly downloads, GitHub stars, and forks. Logarithmic scaling prevents top-heavy scores.

**Community (15%)** — Contributors, dependents, forks, watchers, and maintainers. Measures real ecosystem engagement.

**Maturity (30%)** — Project age, version count, PHP version support, and release stability.

###  Release Activity

Cadence

Every ~25 days

Recently: every ~57 days

Total

10

Last Release

8d ago

Major Versions

v0.0.4 → v1.0.02025-11-10

v1.0.1 → v2.0.02026-05-20

PHP version history (2 changes)v0.0.1PHP ^8.2

v1.0.1PHP ^8.3

### Community

Maintainers

![](https://avatars.githubusercontent.com/u/28820687?v=4)[Paul](/maintainers/altrntv)[@altrntv](https://github.com/altrntv)

---

Top Contributors

[![altrntv](https://avatars.githubusercontent.com/u/28820687?v=4)](https://github.com/altrntv "altrntv (17 commits)")

---

Tags

dynamic-filterdynamic-sorteloquenteloquent-filtereloquent-laraveleloquent-sortlaravellaravel-filterlaravel-filter-urllaravel-query-filterlaravel-query-sortlaravel-sortphpquery-filterquery-sortlaraveleloquentfiltereloquent filterlaravel toolslaravel query filterlaravel filter

###  Code Quality

TestsPest

Code StyleLaravel Pint

### Embed Badge

![Health badge](/badges/altrntv-eloquent-filter/health.svg)

```
[![Health](https://phpackages.com/badges/altrntv-eloquent-filter/health.svg)](https://phpackages.com/packages/altrntv-eloquent-filter)
```

###  Alternatives

[laravel/ai

The official AI SDK for Laravel.

1.0k3.2M195](/packages/laravel-ai)[psalm/plugin-laravel

Psalm plugin for Laravel

3355.3M346](/packages/psalm-plugin-laravel)[api-platform/laravel

API Platform support for Laravel

58171.6k14](/packages/api-platform-laravel)[illuminate/queue

The Illuminate Queue package.

21332.6M1.6k](/packages/illuminate-queue)[mehdi-fathi/eloquent-filter

Eloquent Filter adds custom filters automatically to your Eloquent Models in Laravel.It's easy to use and fully dynamic, just with sending the Query Strings to it.

448199.3k1](/packages/mehdi-fathi-eloquent-filter)[spatie/laravel-health

Monitor the health of a Laravel application

87512.0M165](/packages/spatie-laravel-health)

PHPackages © 2026

[Directory](/)[Categories](/categories)[Trending](/trending)[Changelog](/changelog)[Analyze](/analyze)
