Laravel previous and next records

浪尽此生 提交于 2019-11-27 20:05:18

问题


I am trying to create a page where I can see all the people in my database and create edits on them. I made a form where I fill in the data from the database of certain fields.

I would like to navigate trough them by a Next and Previous button.

For generating the next step I have to take the ID larger than the current one to load the next profile.

For generating the previous step I have to take the ID smaller than the current one to load the previous profile.

My route:

Route::get('users/{id}','UserController@show');

Controller:

public function show($id)
    {

        $input = User::find($id);

        // If a user clicks next this one should be executed.
        $input = User::where('id', '>', $id)->firstOrFail();



        echo '<pre>';

        dd($input);

        echo '</pre>';

        return View::make('hello')->with('input', $input);
    }

View: The buttons:

<a href="{{ URL::to( 'users/' . $input->id ) }}">Next</a>

What is the best approach to get the current ID and increment it?


回答1:


Below are your updated controller and view files derived from @ridecar2 link,

Controller:

public function show($id)
{

    // get the current user
    $user = User::find($id);

    // get previous user id
    $previous = User::where('id', '<', $user->id)->max('id');

    // get next user id
    $next = User::where('id', '>', $user->id)->min('id');

    return View::make('users.show')->with('previous', $previous)->with('next', $next);
}

View:

<a href="{{ URL::to( 'users/' . $previous ) }}">Previous</a>
<a href="{{ URL::to( 'users/' . $next ) }}">Next</a>



回答2:


// in your model file
public function next(){
    // get next user
    return User::where('id', '>', $this->id)->orderBy('id','asc')->first();

}
public  function previous(){
    // get previous  user
    return User::where('id', '<', $this->id)->orderBy('id','desc')->first();

}
// in your controller file
$user = User::find(5); 
// a clean object that can be used anywhere
$user->next();
$user->previous();



回答3:


Here's a link I found that should help: http://maxoffsky.com/code-blog/laravel-quick-tip-get-previous-next-records/

It looks like for next you want to use: $next = User::where('id', '>', $id)->min('id'); and have the view as: <a href="{{ URL::to( 'users/' . $next->id ) }}">Next</a>

Also don't forget to pass $next to the view.




回答4:


Simplest approach

// User.php
public static function findNext($id)
{
    return static::where('id', '>', $id)->first();
}

// UserController.php
$nextUser = User::findNext($id);

// view
<a href="{{ URL::to( 'users/' . $nextUser->id ) }}">Next</a>

Lazy approach :

// view
<a href="{{ URL::to( 'users/' . $input->id . '/next') }}">Next</a>

// routes.php (should be optimized, this is just to show the idea)
Route::get('users/{user}/next', function($id) {
    $nextUser = User::findNext($id);
    return Redirect::to('user/' . $id);
});



回答5:


I understand the approach being taken here by user2581096 but I am not sure it is efficient (by any standards). We are calling the database 3 times for really no good reason. I suggest an alternative that will be way more efficient and scalable.

Do not pass the previous and next IDs to the view. This eliminates 2 unnecessary database calls.

Create the following routes:

users/{id}/next

users/{id}/previous

These routes should be used in the href attributes of the anchor tags

Add methods in the controller to handle each of the new routes you have created. For example:

 public  function getPrevious(){
        // get previous  user
        $user = User::where('id', '<', $this->id)->orderBy('id','desc')->first();
        return $this->show($user->id);
    }

This function will only be called when you actually click on the button. Therefore, the database call is only made when you need to actually look up the user.




回答6:


in-case you want to retrieve the prev/next records along with their data, you can try

$id   = 7; // for example

$prev = DB::table('posts')->where('id', '<', $id)->orderBy('id','desc')->limit(1);
$next = DB::table('posts')->where('id', '>', $id)->limit(1);

$res = DB::table('posts')
        ->where('id', '=', $id)
        ->unionAll($prev)
        ->unionAll($next)
        ->get();

// now $res is an array of 3 objects
// main, prev, next
dd($res);

1- the query builder is usually much faster than eloquent.

2- with union we are now only hitting the db once instead of 3.




回答7:


i developed the code.

it work all times, even if we don't have any next or prev post

public function nextPost($table, $id)
{
    $next = DB::table($table)->where('id', '>', $id)->orderBy('id','asc')->first();
    if(!$next)
        $next = DB::table($table)->orderBy('id','asc')->first();

    return $next;
}

public function prevPost($table, $id)
{
    $prev = DB::table($table)->where('id', '<', $id)->orderBy('id','desc')->first();
    if(!$prev)
        $prev = DB::table($table)->orderBy('id','desc')->first();
    return $prev;
}


来源:https://stackoverflow.com/questions/21909706/laravel-previous-and-next-records

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!