One-to-many then eager load an array with Laravel Eloquent ORM

11,839

It looks like you don't even need a nested eager load, you just need to modify the query that with returns, so:

$posts = Post::with('comments')->where('user_id', '=', 1)->get();

You can daisy chain most of the methods in the Eloquent system, generally they're just returning a Fluent query object.

(I haven't tested it but I'm fairly certain that'll work. Also, you can't do it on ::all() because that calls ->get() for you. You have to dig in the source code to find this, I don't think the Eloquent documentation mentions that's what it's doing.)

Also the Eager Loading Documentation covers nested eager loading, so you could load all users, with their posts, with the comments:

You may even eager load nested relationships. For example, let's assume our Author model has a "contacts" relationship. We can eager load both of the relationships from our Book model like so:

$books = Book::with(array('author', 'author.contacts'))->get();
Share:
11,839
drew schmaltz
Author by

drew schmaltz

Updated on July 19, 2022

Comments

  • drew schmaltz
    drew schmaltz almost 2 years

    With Laravel and the eloquent ORM, I want to create an array or object of all posts and corresponding comments that belong to a specific user (the logged in one). The result will then be used with Response::eloquent(); to return JSON.

    Basically in pseudo-code:

    All Posts by user ::with('comments').
    

    or

    Posts by Auth::user()->id ::with('comments').
    

    I have my database setup per the usual with a user's table, comments table and posts table. The comments table has a post_id and the posts table has a user_id.

    The long way of doing this without Laravel would be something like:

    SELECT * FROM posts WHERE user_id = 'user_id'
    foreach($result as $post) {
        SELECT * FROM comments WHERE posts_id =  $post->id
        foreach($query as $comment) {
            $result[$i]->comments[$n] = $comment
        }
    }
    

    But I want to accomplish it with Laravel's Eloquent ORM.

  • drew schmaltz
    drew schmaltz over 11 years
    You have to have a Comment class defined and BINGO! Simple as what you described.
  • andrewtweber
    andrewtweber about 10 years
    The eager loading of nested relationships (author.contacts) is what I've been struggling with. Thanks!
  • scipilot
    scipilot about 10 years
  • Goldentoa11
    Goldentoa11 about 10 years
    In response to Post::with('comments')->where('user_id', '=', 1)->get(), a more readable solution would be Auth::user()->posts()->with('comments')->get()
  • Goldentoa11
    Goldentoa11 about 10 years
    Or, if it's not pertaining to Auth::user(), you could use User::find($id) in it's place.
  • Kevin Op den Kamp
    Kevin Op den Kamp over 9 years
    note: ['author', 'author.contacts'] is ambiguous, simply using with('author.contacts') will suffice.
  • furcicm
    furcicm over 6 years