sql >> Database teknologi >  >> RDS >> Mysql

Oprettelse af en filtrerbar liste ved hjælp af Laravel- og Eloquent-forespørgsler

Når du begynder at anvende betingelser på dine forespørgsler, skal du være opmærksom på følgende funktion:newQuery() . Denne funktion giver dig mulighed for at starte en ny forespørgselsbygger og kæde dine filtre/ordrebys til den.

Eksempel på skema:

Kolonner i Produkt tabel:

id | name | price | date_received

Kolonner i product_tag tabel:

id | tag_id | product_id

Kolonne i tag tabel:

id | name

Forhold:

  • Mange produkter har mange tags

Jeg vil ikke opsætte de veltalende modeller, men bemærk, at produktmodellen har et tag() funktion med en hasManyThrough() forhold

En filterklasse er blevet konfigureret med hovedformålet at anvende dine filtre og bestille bys. Bemærk:Klassen kan abstraheres endnu længere.

Din filterklasse:

class ProductFilter {

    /**
    * Fluent query builder
    * @var mixed $queryBuilder
    */
    private $queryBuilder;

    /**
    * Http Request
    * @var \Illuminate\Http\Request $request
    */
    protected $request;

    /**
    * Filters collection
    * @var array $filters
    */
    private $filters = [];

    /**
    * Order Bys Collection
    * @var array $orderBys
    */
    private $orderBys = [];

    /**
    * Class constructor
    *
    * @param array $input
    */
    public function __construct(\Illuminate\Http\Request $request, &$queryBuilder)
    {
        //Initialize Query Builder
        $this->queryBuilder = $queryBuilder;
        //Get input
        $this->request = $request;

        //Register Filters
        $this->registerFilters();

        //Register Order Bys
        $this->registerOrderBys();
    }

    /**
     * Register Filters in the function below
     * Each filter is in the form of an array
     */

    private function registerFilters()
    {
        $this->filters['product_name'] = ['name'=>'Name',
                                                'value' => $this->request->get('filter_product_name'),
                                                'enabled' => $this->request->has('filter_product_name'),
                                                'function' => 'filterProductName'
                                            ];

        $this->filters['tag'] = ['name'=>'End Date',
                                            'value' => $this->request->get('filter_tag'),
                                            'enabled' => $this->request->has('filter_tag'),
                                            'function' => 'filterTag'
                                        ];
    }

    /**
    * Check if any filters are active
    * Useful to show/hide filter bar
    * 
    * @return bool
    */
    public function isFiltersActive()
    {
        return (boolean)count(
            array_filter($this->filters,function($v){
                return $v['enabled'] === true;
            })
        );        
    }

    /**
    * Register Order Bys in the function below
    * Each order by is in the form of an array
    *
    */
    private function registerOrderBys()
    {
        $this->orderBys['name'] = [
                                    'name' => 'Order By Name',
                                    'value' => $this->request->get('order_by_product_name','ASC'),
                                    'enabled' => $this->request->has('order_by_product_name'),
                                    'function' => 'orderByProductName'
                                  ];
    }

    /**
    * Check if any order bys are active
    * Useful to show/hide order by bar
    * 
    * @return bool
    */
    public function isOrderBysActive()
    {
        return (boolean)count(
            array_filter($this->orderBys,function($v){
                return $v['enabled'] === true;
            })
        );        
    }    

    /**
     * Apply Filters
     * Loop through each filter, check if they are enabled. If they are, apply filter to query builder
     */

    public function applyFilters()
    {
        foreach($this->filters as $filter_name => $filter_array)
        {
            if($filter_array['enabled'] &&
                array_key_exists('function',$filter_array) &&
                method_exists($this,$filter_array['function']))
            {
                $this->{$filter_array['function']}($filter_array);
            }
        }

        return $this;
    }

    /**
     * Apply Order Bys
     * Loop through each order by, check if they are enabled. If they are, apply order by to query builder
     */

    public function applyFilters()
    {
        foreach($this->orderBys as $order_by_name => $order_by_array)
        {
            if($order_by_array['enabled'] &&
                array_key_exists('function',$order_by_array) &&
                method_exists($this,$order_by_array['function']))
            {
                $this->{$order_by_array['function']}($order_by_array);
            }
        }

        return $this;
    }    

    /*
     * Filter Functions: START
     */

    /**
    * Filter by Product Name
    *
    * @param array $filterArray
    */
    private function filterProductName($filterArray)
    {
        $this->queryBuilder
            ->where('name','=',$filterArray['value']);
    }

    /**
    * Filter by Product Tag
    *
    * @param array $filterArray
    */
    private function filterTag($filterArray)
    {
        $this->queryBuilder
        ->whereHas('tag',function($query) use ($filterArray){
            return $query->where('name','=',$filterArray['value']);
        }); 
    }

    /*
     * Filter Functions: END
     */


    /*
    * Order By Functions: START
    */

    /**
    * Order By Name
    * @param array $orderByArray
    */
    private function orderByName($orderByArray)
    {
        $this->queryBuilder
        ->orderBy('name', $orderByArray['value']);
    }

    /*
    * Order By Functions: END
    */    
}

Sådan bruges:

//In my controller function

public function getListOfProducts(\Illuminate\Http\Request $request)
{
    //Init Product Query
    $productQuery = \App\Models\Product()::newQuery();

    //Apply all filters and order bys
    $productFilter = app('ProductFilter',[$request,$productQuery])->applyFilters()->applyOrderBys();

    //Fetch Product Result
    $productResult = $productQuery->get();
}



  1. Håndtering af frysning i PostgreSQL

  2. Materialiserede visninger med MySQL

  3. Postgres now() tidsstemplet ændres ikke, når scriptet virker

  4. Kaldes onUpgrade-metoden nogensinde?