I have the some tables: Orders, Products, ProductsImages.
I try to get all orders:
$orders = Orders::with("Products")->with("images")->get();
So relationship is:
Orders.product_id = Products.id
Products.id = ProductsImages.product_id
I want to connect these tables in one request
through Order model.
You want to use many-to-many relation between orders and products and one-to-many relation between products and productsImages
Just setup these relationships as described in documentation and load data using nested eager loading:
Orders::with('products.productsImages')->get();
Related
I would like to begin with the messy things I have done with the database architecture.
I have put the fields title, description, donation_amount, in the users table which should have been in a different table. But now if I change this, I would have to change a lot of things.
The ManyToMany relation is already setup between these tables in laravel. I tried to join tables that query builder as well.
There are different roles in the application. We will talk specifically about Donor When a Donor registers in the Application. It selects multiple categories and sub_categories which stores in selections table.
Now when a donor logs in to the application. It should only get the records based on the categories selected.
Now I am confused how can I retrieve the users based on the logged in users selected categories and sub_categories.
I have tried joining the tables which works well but it is getting all the results against the joined tables.
DB::table("users")->select('users.*')->from('categories')
->join('selections','categories.id', '=', 'selections.category_id')
->join('users', 'users.id','=', 'selections.user_id')
->join('sub_categories','sub_categories.id', '=', 'selections.sub_category_id')
->where('users.status','approved')->paginate(6);
Relations in the model Category
public function users() {
return $this->belongsToMany(User::class,'selections');
}
Relations in the model User
public function categories() {
return $this->belongsToMany(Category::class,'selections');
}
If there is a way of doing this calling eloquent relationships. I would love the help else It would be evenly nicer to get the job done with the joins I have already implemented.
Use has-many-through relationship.
https://laravel.com/docs/9.x/eloquent-relationships#has-many-through
In other way you can query like this :
DB::table("users")->select('users.*')
->whereIn('users.id',function($query) use ($specific_category_id){
$query->select(''user_id')->from('selections')->where('category_id',$specific_category_id)
})
->where('users.status','approved')->paginate(6);
I have a model Category with a belongs to many relationship with itself:
Category has many categories in subcategories
Category belongs to one category in supercategory
When I query all categories I get the correct results:
strapi.services.category.find()
When I query all subcategories I also get the correct results:
strapi.services.category.find({ supercategory_null: false })
But when I query just supercategories it doesn't return any categories:
strapi.services.category.find({ supercategory_null: true })
Question
How can I query just the categories that have no supercategory relationship?
This should work
strapi.services.category.find({ supercategory_null: true },['category']);
Defination:
find(params, populate)
populate (array): you have to mention data you want populate e.g ["author", "author.name", "comment", "comment.content"]
The solution I found is to use knex instead of the strapi api:
// Assuming your table name is `category`
const knex = strapi.connections.default;
const categories = await knex(`category`).select(`*`).where(`supercategory`, null);
I have a question about Laravel Eloquent Relations.
I have the following table situation:
Table guests:
id
name
...
Table landing_pages:
id
name
...
A guest can have several landing pages. And a landing page will have multiple guests.
So I thought, I can use a many-to-many relationship there and I created a new table
Table guests_landing_pages:
id
guest_id
landing_page_id
...
I would be able to use this the following way:
In guest Model I can do this, to create the many-to-many relationship:
public function landing_pages()
{
return $this->belongsToMany(\App\Models\LandingPage\LandingPage::class, 'guests_landing_pages','landing_page_id','guest_id');
}
... and the other way round in landing_page model.
But actually the table guests_landing_pages contains more data than just the guest_id and landing_page_id relation.
There are several other fields in it:
Table guests_landing_pages:
id
guest_id
landing_page_id
identifier_token
max_persons
answer
...
My question is now, how can I realize this best. If I would use the many-to-many relation as described above, I will not be able to access the fields in the intermediate table, won't I?
Or will the best solution to this to create a GuestLandingPages model with all the fields and create hasMany relations to/in both?
Laravel Eloquent has features for retrieving intermediate columns.
public function landing_pages()
{
return $this->belongsToMany(\App\Models\LandingPage\LandingPage::class, 'guests_landing_pages','landing_page_id','guest_id')
->withPivot('max_persons', 'answers');
}
I have a model Asset with documents() { $this->hasMany(Document::class); } through a table data_asset_document. I extend Asset into multiple models, one of which is Equipment. In my seeder for Equipment, I attempt to create a Document bound to the Equipment record:
$asset = Equipment::create([...]);
$document = Document::create([
'name' => "$type Purchase Order",
'tracking_number' => app('incrementer')->current()
]);
$asset->documents()->save($document);
Eloquent produces this query:
update `data_document` set `equipment_id` = 1, `data_document`.`updated_at` = 2019-09-20 14:39:48 where `id` = 1
This is obviously incorrect, since data_document does not have an equipment_id column (Documents "belong to" several models besides Asset). How do I rewrite Asset::documents so that produces the correct mapping, even in its extensions? Or do I need to save my Document through a means other than Asset::documents?
Since your extended asset model is called Equipment, Laravel expects your foreign key to be called equipment_id. You will need to specify the actual foreign key of asset_id in your relationship.
https://laravel.com/docs/6.x/eloquent-relationships#one-to-many
hasMany
documents() {
$this->hasMany(Document::class, 'asset_id');
}
The problem is, I'm not convinced your relationship is really hasMany since you mention what looks like a pivot table data_asset_document as being involved. Many-to-many relationships, like mentioned in your title, would use the belongsToMany method.
https://laravel.com/docs/6.x/eloquent-relationships#many-to-many
https://laravel.com/docs/6.x/eloquent-relationships#has-many-through
in my Laravel project i get this database structure:
Products
Id
Name
Orders
Id
Total
Order_Product
Product_id (nullable)
Order_Id
Details
In my Order model I make belongsToMany retaltionship with Product model:
public function products() {
return $this->belongsToMany(Product::class)->withPivot('Details');
}
The Problem is when I try to get the Order Products Collection
$order->products();
I don't get rows with nullable product_id, Any solution please ? Thank you.
Laravel support "Null Object Pattern" since version 5.5 which allows you to define a default model that will be returned if the given relationship is null.
Try using the following code:
public function products() {
return $this->belongsToMany(Product::class)->withDefault()->withPivot('Details');
}
Most likely, you don't get "nullable" products because you have a relation Order->Products. When you call $order->products(), eloquent tries to get all Product entities that are connected to your Order via product_id field. So, if field is empty, then you can't get Product because there is no connection.
One of the solutions is:
create another entity like OrderLine(Order_Product table); add methods like $orderLine->details() and relation to Product like $orderLine->product()
add relation to OrderLine inside Order - $order->line() or $order->info() etc. -> Order hasMany OrderLine
then use $order->line() to get an order's details and products (if exists)
p.s. I've compiled it in my head so it might need some code adjustments.
Good luck