Reputation: 3197
I have a series of tables related like so;
trainers -> hasMany -> programs
programs -> hasMany -> weeks
weeks -> hasMany -> days
days -> hasMany -> sessions
sessions -> hasMany -> phases
phases -> hasMany -> excersises
the relationships in the opposite direction are all has one accept for excersises to phases which is also hasMany with a pivot table
getting relationships one deep like this per the documentation works fine obviously
$programs = $this->program->orderBy('trainerId', 'asc')->take(1)->with('weeks.days')->get();
I need to be able to retrieve the contents of an entire program and I thought that I could eager load each nested relationship something like this
$programs = $this->program->orderBy('trainerId', 'asc')->take(1)->with('weeks.days', 'weeks.days.sessions')->get();
or
$programs = $this->program->orderBy('trainerId', 'asc')->take(1)->with('weeks.days.sessions')->get();
but both return a FatalErrorException
Call to undefined method Illuminate\Support\Facades\Session::newQuery()
whats the correct way to do this?
Upvotes: 3
Views: 3756
Reputation: 3197
So I found the problem and it might help someone else to know the answer. this thread gave me the aha moment laravel forums
I have a model called Session, laravel uses that name elsewhere in the framework, duh, so when it tries to call my model it is actually calling the other session class from somewhere deep in the framework. some of the solutions i found suggest namespaces but I dont think that will work for me because the relationship declaration simply passes a string with the class name to the framework. I think this means that the calling of the class happens elsewhere and I would need to put the namespace /use there correct me if I am wrong please.
either way changing the session class to Sessionss and changing the relationships to suit has resolved my issue.
i hope this helps someone else not waste 36 hours trying to figure this out :p
Upvotes: 1
Reputation: 12169
From your question, I can see you have nested relationship like the following.
programs -> hasMany -> weeks
-----------------------------weeks -> hasMany -> days
----------------------------------------------------days -> hasMany -> sessions
It is very hard to know what data should load for days
if we do not know the weeks
. Similarly for the sessions
as well. So, we have to load the weeks
data first then days
, then sessions
.
From Laravel documentation, we can see, Eager loading using the following approach:
select * from books
select * from authors where id in (1, 2, 3, 4, 5, ...)
Laravel loading author
data based on books
data.
http://laravel.com/docs/eloquent#eager-loading
Try to load weeks
first
$programs = $this->program->orderBy('trainerId', 'asc')
->take(1)
->with('weeks', 'weeks.days', 'weeks.days.sessions')
->get();
or:
Lazy Eager Loading:
$programs = $this->program->orderBy('trainerId', 'asc')->take(1)->get();
$programs->load('weeks', 'weeks.days', 'weeks.days.sessions');
Upvotes: 3