Вызов неопределенного метода Illuminate \ Database \ Eloquent \ Builder :: search () с использованием laravel scout и tntsearch - PullRequest
0 голосов
/ 30 октября 2019

В моем приложении larave-vue я хочу иметь возможность фильтровать по поисковому запросу, используя laravel scout tntsearch, наряду с этим я также выполняю дополнительную фильтрацию, сортировку или предложения where в моем контроллере. Я не могу заставить оба работать правильно в моем приложении.

В моем контроллере у меня есть это:

$posts = Post::filter($filters)->search($request->input('query'))->paginate(0);
            $posts->load(['postcategory.section','author']);

            if($posts->isEmpty())
            {
                return response()->json([
                    'message' => 'No results found',
                ],500);    
            }

            return response()->json([
                'message' => 'Results found',
                'posts' => $posts,
            ]);

Это дает мне следующую ошибку:

Call to undefined method Illuminate\Database\Eloquent\Builder::search()

По какой-то причине это не работает, я попытался изменить порядок фильтра, поиска и разбивки на страницы, но я все еще получаю ошибки.

Если вам интересно, как работает мой метод фильтрации, это в основном область действия

Вы можете прочитать подробное описание здесь:

https://medium.com/@mykeels/writing-clean-composable-eloquent-filters-edd242c82cc8

См. Ниже мой QueryFilters и Filterable trait

<?php
namespace App\Filters;

use Illuminate\Database\Eloquent\Builder;
use Illuminate\Http\Request;

class QueryFilters
{
    protected $request;
    protected $builder;

    public function __construct(Request $request)
    {
        $this->request = $request;
    }

    public function title($term)
    {
        $lowerCaseTerm = strtolower($term);
        return $this->builder->where('title', 'LIKE', "%$lowerCaseTerm%");
    }

    public function postCategory($term)
    {

        return $this->builder->whereHas('postcategory', function ($query) use ($term){
            $query->where('id', $term);
        });
    }

    public function sort($term)
    {
        $sortArray = explode(",", $term);

        for($i = 0; $i <= $sortArray.length; $i++)
        {
            $sortBy = substr_replace($sortArray[i], "", -1);

            $sortChar = substr($sortArray[i], -1);

            $sortOrder = $sortChar == '+' ? 'ASC' : 'DESC';  

            $this->bulider->orderBy($sortBy, $sortOrder);
        }

        return $this->builder;
    }

    public function apply(Builder $builder)
    {
        $this->builder = $builder;
        foreach ($this->filters() as $name => $value)
        {
            //if method doesn't exists continue out of the loop 
            if ( ! method_exists($this, $name))
            {
                continue;
            }
            //method exists so check if it has a value payload so call the method with arguments
            if (strlen($value)) 
            {
                $this->$name($value);
            } 
            //it doesn't have a payload so call the method without arguments
            else 
            {
                $this->$name();
            }
        }
        return $this->builder;
    }

    public function filters()
    {
        //returns associative array of request body key value pairs
        return $this->request->all();
    }

}

ИФильтруемая черта

<?php
namespace App\Filters;

use Illuminate\Database\Eloquent\Builder;

trait Filterable
{
    public function scopeFilter($query, QueryFilters $filters)
    {
        return $filters->apply($query);
    }
}

1 Ответ

0 голосов
/ 30 октября 2019

Метод search () не предназначен для добавления к существующему запросу. Вот метод, который добавляется в вашу модель с помощью функции поиска

public static function search($query = '', $callback = null)
{
    return app(Builder::class, [
        'model' => new static,
        'query' => $query,
        'callback' => $callback,
        'softDelete'=> static::usesSoftDelete() && config('scout.soft_delete', false),
    ]);
}

Функция статическая, она не 'не принимает построитель запросов в качестве параметра и возвращает нового построителя, несмотря ни на что. Таким образом, вы не можете связать Поиск по запросу, но вы можете НАЧАТЬ с поиска и затем применить свои фильтры

Так что вместо этого

$posts = Post::filter($filters)->search($request->input('query'))->paginate(0);

Попробуйте это

$posts = Post::search($request->input('query'))->filter($filters)->paginate(0);
...