Eloquenturl: A Laravel Package to Simplify or Eliminate Query Building for URL Parameters
Tags: laravel, package, query
Published: 2022-01-27 17:50:37

Eloquenturl is a Laravel package that **simplifies** and **eliminates** building of complex, cluttered and unreusable queries for filters, search, sort, scopes, pagination and more.

The name "Eloquenturl", pronounced "Eloquenterl" was derived from the term "Eloquent URL". Meaning, Laravel's Eloquent models can be queried with only URL parameters.

For example, you have a route `/articles`, and wish to support filtering the index results with URL parameters, `/articles?search=apple&order_by=author&scope[published]=true&scope[featured]=true`, **without Eloquenturl**, your resource controller would be something like this:

```php
<?php

namespace App\Http\Controllers;

use App\Models\Article;
use Illuminate\Http\Request;

class ArticlesController extends Controller
{
    public function index(Request $request)
    {
        // Initialise query
        $articles_query = Article::with('category');

        // Build the filters query

        // Filter articles by search term
        if ($request->filled('search')) {
            $articles_query->where('title', 'like', '%'.$request->search.'%')
                ->orWhereHas('category', function($query) use ($request) {
                    $query->where('name', 'like', '%'.$request->search.'%');
                });
        }
        
        // Filter articles by category
        if($request->filled('category')){
            // Validate the ordering parameters
            if (in_array(strtolower($request->category), $categories->pluck('slug')->toArray())) {
                $articles_query->whereHas('category', function($query) use ($request) {
                    $query->where('slug', $request->category);
                });
            }
        }

        // Filter articles by user/author's username
        if($request->filled('username')){
            $articles_query->whereHas('user', function($query) use ($request) {
                $query->where('username', $request->username);
            });
        }

        // Ugh, notice that for every field you wish to filter by,
        // you'll write code for that just like above.

        // Order articles
        if ($request->filled('order_by')) {
            // Validate the ordering parameters
            if (in_array(strtolower($request->order_by), ['title', 'published_at'])) {
                $order_by = strtolower($request->order_by);
                $order = $request->filled('order') && in_array($request->order, ['asc', 'desc']) ? strtolower($request->order) : 'asc';
                $articles_query->orderBy($order_by, $order);
            }
        } else {
            // Set default ordering
            $articles_query->orderBy('published_at', 'desc');
        }

        // Execute the query
        $articles = $articles_query->paginate();

        return view('articles.index',compact('articles'));
    }
}
```

To be fare, the code above is already well written. But,

With `Eloquenturl`, we can make it simple, yet more powerful:

```php
<?php

namespace App\Http\Controllers;

use App\Http\Controllers\Controller;
use App\Models\Article;
use Doncadavona\Eloquenturl\Eloquenturl;
use Illuminate\Http\Request;

class ArticlesController extends Controller
{
    public function index(Request $request)
    {
        // Simply pass the model and the request.
        $articles = Eloquenturl::eloquenturled(Article::class, $request);

        return view('articles.index', compact('articles'));
    }
}
```

Please take a look at the [Github Repository](https://github.com/doncadavona/eloquenturl) for installation, usage guides and more details:

[https://github.com/doncadavona/eloquenturl](https://github.com/doncadavona/eloquenturl)

## Credits

Eloquenturl is developed by [Don Cadavona](https://doncadavona.com) with love.