CamKem's avatar
Level 10

How to paginate eloquent related model data

Hello, I am trying to paginate the results for some data that shown in one of my views.

My route look like this

Route::get('posts/{post:slug}', function (Post $post) {
    $post->load(['comments' => fn($query) => $query->latest()]);
    return view('post', [
        'post' => $post
    ]);

});

This is my method on my model class

    public function comments()
    {
        return $this->hasMany(Comment::class)->paginate(10);
        //->orderBy('created_at','desc');
    }

This is the section of my view that deals with showing the data.

        <h2 class="font-bold text-2xl">Comments</h2>
        @foreach ($post->comments as $comment)
            <div class="border border-gray-300 rounded-md p-4">
                <div>
                    <a href="/comment/{{ $comment->slug }}" class="hover:underline"><h1>{{ $comment->title }}</h1></a>
                    <br>
                    {{ $comment->body }}
                    <br>
                        <?php
                        $commentdiff = Carbon::parse($comment->created_at)->diffForHumans(null, true, true, 2);
                        ?>
                    {{ $comment->created_at }} / {{ $commentdiff }} ago
                </div>
            </div>
            <br>
        @endforeach
        <div class="border border-gray-300 rounded-md p-4">
            {{ $post->comments->links() }}
        </div>

I am not sure where to put the pagination so that it passes the links through to the view, it seems if I add it into the method for the relationship in the model class (as shown above) that something goes wrong. I get the following error.

Method Illuminate\Database\Eloquent\Collection::addEagerConstraints does not exist.

If I take the paginate(10) out of the model and add it to the eager lazy load of the comments in the route, I get the following error.

Method Illuminate\Database\Eloquent\Collection::links does not exist.

Please help as I am stuck where to go from here....

0 likes
3 replies
Sinnbeck's avatar
Sinnbeck
Best Answer
Level 102

Split it up

Route::get('posts/{post:slug}', function (Post $post) {
    $comments = $post->comments()->latest()->paginate(10);
    return view('post', [
        'post' => $post, 
        'comments' => $comments 
    ]);

});

And just use $comments directly in the view

CamKem's avatar
Level 10

@Sinnbeck Yet again, thank you sir! (will ensure no re-opening of old threads)

Please or to participate in this conversation.