Home » Php » Laravel 5.3 – Multiple pagination on a single page not working

Laravel 5.3 – Multiple pagination on a single page not working

Posted by: admin October 29, 2017 Leave a comment

Questions:

I am displaying paginated results that I get from Algolia. I have two queries in my controller that I paginate. This is how I send the data from the controller to the view:

public function index(Request $request)
{
    if(!$request->q && !$request->page){
      return redirect('/');
    }

    $videos = Video::search($request->q)->paginate(1);
    $videosCollection = $videos->getCollection();

    return fractal()
      ->collection($videosCollection)
      ->parseIncludes(['player'])
      ->transformWith(new VideoTransformer)
      ->paginateWith(new IlluminatePaginatorAdapter($videos))
      ->toArray();
}

So then when I search for example for 'rene' the result is displayed on url http://videoapp.app/search?q=rene
And the data that I get looks like this:

{
  data: [
    {
      id: 46,
      description: null,
      views: 0,
      created_at: "1 month ago",
      player: {
        data: {
          id: 34,
          image: "15889ca47e557c12240142_1013305815416003_5199651181367705874_n.jpg",
          first_name: "Bruno",
          last_name: "Hendricks"
    }
  }
}
],
meta: {
  pagination: {
    total: 2,
    count: 1,
    per_page: 1,
    current_page: 1,
    total_pages: 2,
    links: {
      next: "http://videoapp.app/search?query=rene&page=2"
      }
    }
  }
}

But the pagination link that is being created for the next page is "http://videoapp.app/search?query=rene&page=2" and if I click on it the metadata is changed and I get the results for the whole table and not just for the result of my first query that was 'rene' in this example. If I on the other hand type the url in the browser http://videoapp.app/search?q=rene&page=2 then it works like it should be.
How I can change those generated links so that it works as it should be?

I have also tried with another example from SO, which again didn’t work for me:

Controller:

    if(!$request->q && !$request->page){
      return redirect('/');
    }

    $players = Player::search($request->q)
                ->paginate(1);

    $videos = Video::search($request->q)
                ->paginate(1);
    $videos->setPageName('videos');

View

{{ $videos->appends(array_except(Request::only('q'), 'page'))->links() }}

and

{{ $players->appends(array_except(Request::only('q'), 'videos'))->links() }}

I have also tried the suggestion from the answers:

public function index(Request $request)
{
    $q = $request->q;
    $videosPage = $request->vpage;
    $playersPage = $request->ppage;

    if (! $request->q) {
        return redirect('/');
    }

    $players = Player::search($q)
        ->paginate(1, 'ppage')
        ->appends(['q' => $q, 'vpage' => $videosPage]);
    $videos = Video::search($q)
        ->paginate(1, 'vpage')
        ->appends(['q' => $q, 'ppage' => $playersPage]);

    return view('search.index', [
        'players' => $players,
        'videos'  => $videos,
    ]);
}

But that also didn’t work, when I would click on a link for players it would go back to video results for example. Can’t seem to find any solution for this problem?

Answers:

The problem is you need 3 separate query string values (“q” for search term, and the page number of each paginator), and the default pagination links clear them, leaving only the one corresponding to the current paginator.

I would try this:

public function index(Request $request)
{
    $q = $request->q;
    $videosPage = $request->vpage;
    $playersPage = $request->ppage;

    if (! $request->q) {
        return redirect('/');
    }

    $players = Player::search($q)
        ->paginate(1, 'ppage')
        ->appends(['q' => $q, 'vpage' => $videosPage]);
    $videos = Video::search($q)
        ->paginate(1, 'vpage')
        ->appends(['q' => $q, 'ppage' => $playersPage]);

    return view('search.index', [
        'players' => $players,
        'videos'  => $videos,
    ]);
}

This way, each paginator has its own page name, and keeps the other one and the search term in the query string.

Questions:
Answers:
if (!$request->q) {
    return redirect('/');
}

This is causing your problem, when you press the paginate link it will replace ?q=something to ?page=2 which will cause your function to redirect.

Use something else ex:

if(!request->q && !request->page){
    return redirect('/');
}

Questions:
Answers:

Divide the window for players or for videos
with <– – Iframe — – > or <— frameset –> Use different method into your controller and output will appear on same window.