Weave Code
Code Weaver
Helps Laravel developers discover, compare, and choose open-source packages. See popularity, security, maintainers, and scores at a glance to make better decisions.
Feedback
Share your thoughts, report bugs, or suggest improvements.
Subject
Message

Filterable Laravel Package

ysm/filterable

View on GitHub
Deep Wiki
Context7

Getting Started

Minimal Setup

  1. Installation:

    composer require ysm/filterable
    

    Publish the config (optional):

    php artisan vendor:publish --provider="Ysm\Filterable\FilterableServiceProvider"
    
  2. Basic Usage: Apply the trait to your Eloquent model:

    use Ysm\Filterable\Filterable;
    
    class User extends Model
    {
        use Filterable;
    }
    
  3. First Filter Request: Define a filterable field in your model:

    protected $filterable = ['name', 'email'];
    

    Use in a controller:

    $users = User::filter(request()->all())->get();
    
  4. Key Files:

    • config/filterable.php (for global settings)
    • app/Models/YourModel.php (trait application)
    • routes/web.php (API/route integration)

Implementation Patterns

Common Workflows

  1. Basic Filtering:

    // Controller
    $results = Model::filter(request()->query)->get();
    
  2. API Integration:

    // Route
    Route::get('/api/users', [UserController::class, 'index']);
    
    // Controller
    public function index()
    {
        return response()->json(
            User::filter(request()->all())->paginate()
        );
    }
    
  3. Dynamic Filtering:

    // Model
    protected $filterable = [
        'name' => ['type' => 'like'],
        'status' => ['type' => 'in', 'values' => ['active', 'inactive']],
    ];
    
    // Request
    User::filter(['name' => 'John', 'status' => 'active']);
    
  4. Combining with Scopes:

    // Model
    public function scopeActive($query)
    {
        return $query->where('active', true);
    }
    
    // Usage
    User::active()->filter(request()->all())->get();
    
  5. Custom Filter Logic:

    // Model
    protected $customFilters = [
        'age_range' => function ($query, $value) {
            [$min, $max] = explode('-', $value);
            return $query->whereBetween('age', [$min, $max]);
        }
    ];
    
    // Request
    User::filter(['age_range' => '25-40']);
    
  6. Validation Integration:

    // Form Request
    public function rules()
    {
        return [
            'name' => 'sometimes|string',
            'email' => 'sometimes|email',
        ];
    }
    
    // Controller
    $validated = $this->validate(request()->all());
    User::filter($validated)->get();
    

Gotchas and Tips

Common Pitfalls

  1. Case Sensitivity:

    • Default behavior is case-sensitive for exact matches. Use type: 'like' for case-insensitive searches.
    • Example:
      protected $filterable = ['name' => ['type' => 'like']];
      
  2. Date Handling:

    • Dates must be in a format the database can parse (e.g., Y-m-d). Use Carbon instances or ISO strings.
    • Example:
      User::filter(['created_at' => '2023-01-01']);
      
  3. Relationship Filters:

    • Nested relationships (e.g., user.posts.title) require explicit handling. Use with() and custom filters:
      protected $customFilters = [
          'post_title' => function ($query, $value) {
              return $query->whereHas('posts', fn($q) => $q->where('title', 'like', "%{$value}%"));
          }
      ];
      
  4. Performance:

    • Avoid filtering on large text fields or unindexed columns. Add database indexes for frequent filters:
      Schema::table('users', function (Blueprint $table) {
          $table->index('email');
          $table->index('name');
      });
      
  5. Mass Assignment:

    • Filterable fields are not automatically whitelisted for mass assignment. Explicitly add them to $fillable if needed:
      protected $fillable = ['name', 'email'];
      

Debugging Tips

  1. Log Filter Queries: Enable query logging in config/filterable.php:

    'debug' => env('FILTERABLE_DEBUG', false),
    

    Check Laravel logs for generated SQL.

  2. Validate Input: Use dd(request()->all()) to inspect incoming filter parameters before applying them.

  3. Test Edge Cases:

    • Empty strings (''), null, and invalid values can break queries. Handle them in custom filters:
      protected $customFilters = [
          'status' => function ($query, $value) {
              if ($value === '') return $query;
              return $query->where('status', $value);
          }
      ];
      

Extension Points

  1. Custom Filter Types: Extend the package by adding new filter types in app/Providers/FilterableServiceProvider.php:

    use Ysm\Filterable\Filters\Filter;
    
    class CustomFilter extends Filter
    {
        public function apply($query, $value)
        {
            // Custom logic
        }
    }
    

    Register it in the service provider:

    $this->app->bind('filter.custom', function () {
        return new CustomFilter();
    });
    
  2. Override Default Behavior: Publish and modify the config to change global defaults (e.g., default operator, allowed types).

  3. Integration with Search: Combine with Laravel Scout or Algolia for full-text search:

    User::filter(request()->all())
        ->when(request('search'), fn($q) => $q->scoutSearch(request('search')))
        ->get();
    
  4. Localization: For multilingual apps, add locale-aware filters:

    protected $customFilters = [
        'name' => function ($query, $value) {
            return $query->where('name', 'like', "%{$value}%")
                        ->orWhere('name_translations', 'like', "%{$value}%");
        }
    ];
    
Weaver

How can I help you explore Laravel packages today?

Conversation history is not saved when not logged in.
Prompt
Add packages to context
No packages found.
terminal42/code-quality-tools
codifyo/ts-generator-bundle
andydefer/laravel-cluster
testo/fiber
mintobit/jobqueue
a4sex/maintenance-bundle
a4sex/entity-date-update
a4sex/client-identifier
a4sex/base-utilites
a4sex/key-value-storage
a4sex/micro-status
chilldev/dependency-injection-extra
datinglibre/datinglibre-app-api
biberltd/corebundle
bricre/symfony-bundle-test
biberltd/logbundle
dominium/http-adapter-bundle
dominium/google-analytics
a4sex/auto-clean-entity
christhompsontldr/laravel-inky