Reputation: 6612
I have a Contact
named model like this :
class Contact extends Model
{
public $timestamps = false;
protected $primaryKey = 'contact_id';
protected $fillable = [
'tel', 'fax', 'email', 'mob', 'address'
];
public function contactable ()
{
return $this->morphTo();
}
}
The above model can belong to some other model, for example House
model like this:
class House extends Model
{
protected $primaryKey = 'house_id';
public function contact ()
{
return $this->morphMany('App\Contact', 'contactable');
}
}
Each of House
can only have one related Contact
, but since Contact
model can be related to other models, I have to define polymorphic relationships.
Now when I want to get a related Contact
model of a specific House
model, that is, return an array of Contact
(that only have one element) while I want to get it as an simple object model; for example:
public function edit (\App\House $house)
{
$house = $house->load('contact');
return $house;
return view('admin/pages/house/house-edit', compact('house'));
}
The result is something like this:
{
"house_id": 6,
"title": "testا",
"header": "0f74e9aa891bcc6fb84aa744721d9692.jpg",
"type": "sara",
"creator": 1,
"created_at": "2016-07-26 15:19:31",
"updated_at": "2016-07-26 15:19:31",
"contact": [
{
"contact_id": 1,
"tel": "1",
"fax": "2",
"email": "3",
"mob": null,
"contactable_id": 6,
"contactable_type": "App\\House"
}
]
}
I try to use first()
method on a relation:
public function contact ()
{
return $this->morphMany('App\Contact', 'contactable')->first();
}
But I'm getting this error:
Call to undefined method Illuminate\Database\Query\Builder::addEagerConstraints()
What's the solution to this problem?
Upvotes: 0
Views: 2435
Reputation: 519
You can use morphOne relationship
public function contact ()
{
return $this->morphOne('App\Contact', 'contactable');
}
Upvotes: -1
Reputation: 3226
There is a way to solve this without having to create two functions.
An example could be:
// House.php
public function contact()
{
return Contact
::where('contactable_id', $this->id)
->where('contactable_type', 'App\\House')
->first();
}
Maybe you will have to change some names.
Hope this helps :)
Edit
The solution above can only be called like so:
$house->contact()
If you wish to use it the 'normal' way ($house->contact->first()
) you should remove ->first()
at the end of the chain.
Upvotes: 1
Reputation: 9749
I've been checking to see if someone can give an answer but since no one is, I have a very wild guess that this has some chance of working:
public function contactRelation()
{
return $this->morphMany('App\Contact', 'contactable');
}
public function contact()
{
$this->load('contactRelation');
return $this->contactRelation->first();
}
Basically what I think is you can't call the first() method on the morph relation, so maybe if you make the morph first and then try to call first on the result it might work.
Note that you no longer need $house = $house->load('contact');
in your controller, just try to access the relation like this: $house->contact();
.
Upvotes: 1