Zachary Dale
Zachary Dale

Reputation: 749

Search with one parameter from search form that can take multiple parameter Laravel

I have created a search form that can has 3 parameter to search into db and return result. All parameter or say form fields in form are drop downs.

Form code:

{!!Form::open(['route' => 'search','class' => 'form-inline pull-left', 'id' => 'search-form', 'method' => 'GET', 'role' => 'search'])!!}
    <select class=" form-control" name="country">
       <option> Select Country</option>
       @foreach($countries as $country)
       <option value="{{$country->name}}">{{ucfirst($country->name)}}</option>
       @endforeach
    </select>
    <select class=" form-control" name="category">
       <option value="">Select Activity</option>
       @foreach($categories as $category)
       <option value="{{$category->name}}">{{ucfirst($category->name)}}</option>
       @endforeach
    </select>
    <select class=" form-control" name="days">
       <option value="">Select Duration (Days)</option>
       <option value="1|5">1-5</option>
       <option value="10|15">10-15</option>
       <option value="20|30">20-30</option>
       <option value="30|60">30-Above</option>
    </select>
 {{ Form::submit('Search', ['class' => 'btn btn-primary btn-lg','id' => 'search'] )}}

  {!! Form::close() !!}

My method in controller to search only with one parameter:

    public function search(Request $request)
{
    $days = $request->days;
    $days_explode = explode('|', $days);

    if (isset($request->country) && !isset($request->category) && !isset($request->days)) {

        $query= Tour::whereHas('country', function($r) use($request) {
            $r->where('name','=', $request->country);
        })
        ->paginate(8);

        return view('public.tour.list')->withResults($query);
    }
    else{
    $query= Tour::whereHas('country', function($r) use($request) {
            $r->where('countries.name','=', $request->country);
        })
        ->whereHas('category', function($s) use($request) {
            $s->where('categories.name','=', $request->category);
        }) 
        ->whereHas('country', function($r) use($request) {
            $r->where('countries.name','=', $request->country);
        })
        ->whereBetween('days', [$days_explode[0], $days_explode[1]])   
        ->paginate(8);
    return view('public.tour.list')->withResults($query);
    }

I'm trying to make my form flexible. It should return result whether 1,2 or 3 parameter is passed to it. With this above code the form returns results if all 3 parameter is passed to it. And gives error Undefined offset: 1 if only one parameter is passed to it.

Upvotes: 1

Views: 62

Answers (1)

Alexey Mezenin
Alexey Mezenin

Reputation: 163978

You can check every parameter first and then decide to add it to the query or not. Do something like this:

$query = Tour::where(function($q) use($request) {
    if (!empty($request->country)) {
        $q->whereHas('country', function($r) use($request) {
            $r->where('countries.name', $request->country);
        });
    }

    if (!empty($request->category)) {
        $q->whereHas('category', function($r) use($request) {
            $r->where('categories.name', $request->category);
        });
    }
})
->whereBetween('days', [$days_explode[0], $days_explode[1]])
->paginate(8);

Or you could do this:

$query = Tour::query();

if (!empty($request->country)) {
    $query = $query->whereHas('country', function($r) use($request) {
        $r->where('countries.name', $request->country);
    });
}

if (!empty($request->category)) {
    $query = $query->whereHas('category', function($s) use($request) {
        $s->where('categories.name', $request->category);
    });
}

$query = $query->whereBetween('days', [$days_explode[0], $days_explode[1]])
               ->paginate(8);

Upvotes: 1

Related Questions