Combine two eloquent relationships in a single Model and combine their data - laravel

I have multiple eloquent relationships set up through the backend in a laravel application. I need to sort of combine a few of them in a return and I'm not sure how to go about it. I'm considering a hasManyThrough relationship but I feel like since I get the data I need through other relational calls there is probably some way to combine the two. Anyways here are my call in my Quote model.
/**
* The items that belong to the quote.
*/
public function items()
{
return $this->belongsToMany('App\Item')->withPivot('waste', 'subtotal', 'required');
}
/**
* The categories that have been added to a quote.
*/
public function categories()
{
return $this->belongsToMany('App\Category')->withPivot('priority', 'expanded')->with('items');
}
What I'd like to do is somehow combine these two relationships so that categories() returns everythign that it does but it attaches the pivot table from the items method to the eager load items. I don't quite konw if I've explained it properly but I hope so.

Related

Eloquent Relationship on the same model

I am using the User model and want to reference other users on a One to Many relationship.
With two models, this would be done by a Many to Many but this attempt at it is obviously wrong:
public function relatedUsers()
{
return $this->belongsToMany(User::class, 'related_user', 'user_id', 'user_id');
}
Is there a better way I can achieve my goal? I don't need an inverse method.
You can use hasMany() or belongsTo() (according to your need) relation for same model relationship
Define hasMany relationship in User model:
public function relatedUsers() {
return $this->hasMany('User','user_id');
}
Example:
Consider you have one User object
$user = User::where('id',$id)->first();
If you want to access related records
$related_users = $user->relatedUsers; // this will return all related users for particular object

How to define multiple belongsTo in laravel

My table has many foreign key for example prefecture_id, gender_id and status_id.
And I made model for those table.
So I want to define multiple belongsTo method like following for get all data with query builder..
But In fact belongsTo can't use like this.
public function foreign(){
return $this->belongsTo([
'App/Prefecture',
'App/Gender',
'App/Status',
]
}
And if the only way is defining multiple method for belongs to.
How do I get all belongstos data in querybuilder.
Please give me advice.
As far as I am aware, there's not a way to get multiple belongsTo from a single method. What you have to do is make one method for each relationship and when you want to load the relationships you can do the following.
Model
public function prefecture()
{
return $this->belongsTo(\App\Prefecture::class);
}
public function gender()
{
return $this->belongsTo(\App\Gender::class);
}
public function status()
{
return $this->belongsTo(\App\Status::class);
}
Query
// This will get your model with all of the belongs to relationships.
$results = Model::query()->with(['prefecture', 'gender', 'status'])->get();

Laravel getting data from a deep relationship

I have 3 tables:
Users
Baskets
Items
id
id
id
user_id
basket_id
price
I'm trying setup a relationship in eloquent by which I can get all the all the Items and the corresponding Baskets where the price of items is X. I want it so that I can simply use $user->items(x) and get the results.
I'm unsure if this can be done using Relationships alone or will I have to resort to writing custom queries.
Any, and all, help and guidance will be appreciated!
The relationship you are looking for is hasManyThrough
https://laravel.com/docs/7.x/eloquent-relationships#has-many-through
User Modal
public function items()
{
return $this->hasManyThrough(Item::class, Bucket::class);
}
The way you want to use is not possible to achieve I think.
Possible Usage
$user->items()->where('price', x);
of if you define custom scopes
Item Modal
public function scopeWherePrice($query, $value)
{
return $query->where('price', $value);
}
Usage
$user->items()->wherePrice(x);
EDIT
If you really want to write a code like $user->items(x) you can define a method on the User Modal.
Note that this is not a relationship, just another method which fetch the result.
User Modal
public function items($price)
{
return this->items()->where('price', $price)->get();
}
Using hasManyThrough Define the relationship in your models:
User Model
/**
* Get all of the items & baskets for the user.
*/
public function items($price)
{
return $this->hasManyThrough('App\Items', 'App\Baskets')
->with('basket')
->where('price',$price);
}
Basket Model
/**
* Get the Items's Basket.
*/
public function basket()
{
return $this->belongsTo('App\Basket','basket_id');
}
And then call it like this:
$user->items(x);
This will return all user items with their corresponding baskets in a specific price.

Custom hasMany relationship query with select()

Each company on my app can store its own events.
A company and its events are related though the following hasMany relationship:
/**
* The events that belong to the company.
*/
public function events()
{
return $this->hasMany('App\Event');
}
To list a company's events, I use:
Auth::user()->company->events
Since each event stores, a lot of data that I don't need when I query the hasMany, I would like to customize the relationship to only select the id and name columns instead of the whole row.
My hasMany relationship query would be something like
DB::table('events')->where('company_id', Auth::id())->select('id', 'name')->get();
How do I take the collection returned from this result and use it as the query for my hasMany relationship, which will then correctly return a collection of event instances?
Add the filter inside your events method like :
public function events()
{
return $this->hasMany('App\Event')->select('id', 'company_id', 'name');
}
Then call it like:
Auth::user()->company->events
Important update: 'company_id' is necessary for company->events link, otherwise 'events' relationship always returns empty array
How about
Auth::user()->company()->with('events:id,name')->get();
https://laravel.com/docs/5.8/eloquent-relationships#eager-loading
Go to Eager Loading Specific Columns

Eloquent many to many self/meta relationship $this->hasMany($this)

So I am working on a project in Laravel 4, and I am wondering how to do a many to many relationship on a single Model. I think comments should be able to belong to other comments (replies) Or at the very least replies should be able to have many replies.
I think that the way I would build the model would be:
Class Comment extends Eloquent {
public function comments() {
// assuming my comments table has an $id column and a second $comment_id table
// do I even need to specify the column name?
return $this->hasMany('Comment', 'comment_id');
}
public function comment() {
return $this->belongsTo('Comment');
}
}
Where can I look for more documentation about this, or what is the Laravel way to achieve what I am trying to achieve?

Resources