Laravel Eloquent Query Where nested relationship - php

I am new to laravel and i am trying to write a query whereby the selected stock->OrderProduct->product_id is passed to get the relevant result. The query looks like this :
$stock = Stock::where('orderProductid.product_id', $pharmacyEvent->prescription->product_id)
->whereHas('orderProduct.product.prices')
->with(['orderProduct.product.price' => function ($query) use ($paymentMode) {
$query->where('scheme_id', $paymentMode->scheme_id);
}])->first();
$price = $stock->orderProduct->product->price;
This doesnt work as it is bad practise and i rewrote the query like below, which brings me wrong results.
$stock = Stock::whereHas('orderProduct.product.prices')
->with([
'orderProduct.product' => function ($query) {
$query->where('id', $pharmacyEvent->prescription->product_id);
},
'orderProduct.product.price' => function($query) {
$query->where('scheme_id', $paymentMode->scheme_id);
}
])->first();
Any advise on eloquent methods to use when i want to pass a condition based on relationships in a query will be highly appreciated. I am using lavel 5.8

I used whereHas :
$stock = Stock::whereHas('orderProduct.product', function($query) use ($pharmacyEvent) {
$query->where('id', $pharmacyEvent->prescription->product_id);
})
// ->whereHas('orderProduct.product.prices')
->with(['orderProduct.product.price' => function ($query) use ($paymentMode) {
$query->where('scheme_id', $paymentMode->scheme_id);
}])->first();
$price = $stock->orderProduct->product->price;

Related

Eloquent: has() condition against database value

I have a simple relationship between Bottles and InventoryItems:
InventoryItem.php:
public function bottles(): HasMany
{
return $this->hasMany(InventoryItemBottle::class);
}
I'm trying to query for InventoryItem's that have a bottles count of greater then a user entered threshold.
The user's input is saved in a JSONB. Part of the query looks like this and I've commented the problem line:
->when(
$filters['filter'] === 'show_above_max_threshold',
fn (Builder $query): Builder => $query->where(function (Builder $query): Builder {
return $query->whereColumn('info->quantity', '>', 'info->high_level_warning');
})
->orWhere(function (Builder $query): Builder {
return $query->has('bottles', '>', 'info->high_level_warning'); // stuck here
})
)
The has() method should help here, but how do I get the high_level_warning from the database to pass to it? Or is there another method I could use?
You can use the has function.
See if this helps you.
$threshold = 2;
$items = InventoryItem::has('bottles', '>=', $threshold)->get();

Join 2 tables in a Single Eloquent Laravel using multiple where clause

here I'd like to find the solution to simplify my query to get data using eloquent in Laravel.
$room_id = Booking::whereBetween('from', [$request->from, $request->to])
->orWhereBetween('to', [$request->from, $request->to])
->where('from', '<=', $request->from, )
->where('to', '>=', $request->from)
->pluck('room_id');
$rooms = Room::whereNotIn('id', $room_id )->get();
So here I have 2 Eloquent operations to get Rooms which not included in the Booking Table with specified requirements. So far I have no problem with it, but can you guys give me best practice to simplify from what I do? Thank you.
Make sure that 'bookings' relation is written on your Room model.
$rooms = Room::whereDoesntHave('bookings', use($request) function($q){
$q->whereBetween('from', [$request->from, $request->to])
$q->orWhereBetween('to', [$request->from, $request->to])
$q->where('from', '<=', $request->from, )
$q->where('to', '>=', $request->from)
})->get();
Your can refer laravel relationship to add it in model and after that using whereHas to query join table:
https://laravel.com/docs/9.x/eloquent-relationships
Example:
With options
protected $with = [
'product_savour'
];
Relationship
public function product_savour()
{
return $this->hasMany(ProductSavour::class, 'product_id');
}
Query
$productQuery->whereHas('product_savour', function ($query) use ($filters) {
$query->whereHas('savour', function ($query) use ($filters) {
$query->whereHas('type', function ($query) use ($filters) {
$query->whereIn('id', $filters['savour']);
});
});
});

filtering the model based on a relationship laravel

So my code is
$categories=Category::where('user_id', $store->id)->whereHas('childrenCategories', function($q) use ($id){
$q->where('user_id', $id);
})->orwhereHas('products', function($q) use ($id) {
$q->where('auth_id', $id);
})->with('products', 'childrenCategories')->latest()->get();
I want to get all children categories with and products with given id but this code doesn't seem to work. As children categories with user_id other than id are also being returned. Sorry, I am relatively new to Laravel. And I thought this would be a good platform to ask. Also, I can share the relationships if you want me to.
I solved this with the following. Thanks, #lagbox for your time.
$categories = Category::with(['childrenCategories' =>
$childrenClosure = function ($query) use ($id) {$query->where('user_id', $id);}, 'products'
=> $productsClosure = function ($query) use ($id) {$query->where('auth_id', $id);}])
->where('user_id', $store->id)
->where(function ($query) use ($childrenClosure, $productsClosure) {$query->whereHas('childrenCategories', $childrenClosure)
->orWhereHas('products', $productsClosure);})
->latest()
->get();

how to use WHERE clause and WITH in Laravel

I'm working on a small project using laravel and i would like to know how can i use WHERE clause for apartment this is my code
$buildings = Building::with('apartment')->get();
i have already tried :
$buildings = Building::with('apartment')->where('name','=',5)->get();
but it applies for Building not for apartment.
how can i apply WHERE clause for apartment ?
You can apply a Closure to with(...) if you pass in an array using the following syntax:
Model::with(['relation_name' => function ($query) { ... }])
In your case, what you're looking for is:
$buildings = Building::with(['apartment' => function ($apartments) {
$apartments->where('name', 5); // if you don't pass an operator, it's assumed to be '='.
}])->get();
You can also write it like this using PHP 7.4 shorthand closures.
$buildings = Building::with(['apartment' => fn($apartments) => $apartments->where('name', 5)])->get();
https://laravel.com/docs/7.x/eloquent-relationships#constraining-eager-loads
Try this
$buildings = App\Building::with(['apartment' => function ($query) {
$query->where('name', 5); .
}])->get();

Laravel eloquent, joining tables and make filter queries

I am trying to write queries to filtering tables, but it's looks like something is not right.
$keyword = "chapel";
$city = $request->get("city");
$price = $request->get("price");
First checking the plans table empty or not. Then start to write filtering queries.
$datas = Place::whereHas("plans")
->groupBy("address","place_name")
->when($keyword, function($query, $keyword) {
return $query->where("place_name", "LIKE", "%$keyword%");
})
->when($city, function($query, $city) {
return $query->where("city", "LIKE", "%$city%");
})
The queries working till basic_info table. But when I when search $keyword in basic_info table then then error pops and says
Call to undefined relationship [basic_infos] on model > [App\Model\Place].
//basic info table
->when($keyword, function($query) use ($keyword){
$query->with(["basic_infos" => function($query, $keyword){
return $query->where("basic_info.wedding_style", "LIKE", "%$keyword%");
}]);
})
//plan table
->when($price, function($query) use ($price){
$query->with(["basic_infos" => function($query, $price){
return $query->where("plans.plan_price", "<=", $price);
}]);
})
->paginate(20);
return $datas;
But actually it's defined. Here is the models
Place Model
public function basicInfos()
{
return $this->hasMany("App\Model\BasicInfo");
}
BasicInfo Model
public function place()
{
return $this->belongsTo("App\Model\Place");
}
But in query inside ->when function, when I use ->with it seems, there is a problem happening. I guess, I am using it at wrong time or else... Same thing surely will happen to plan table's query too.. What is the right way to do it?
You have two problems:
You need to use your function name instead of table name for relationship.
If you want to use another params except $query, use use.
->when($keyword, function($query) use ($keyword){
$query->with(["basicInfos" => function($query) use ($keyword){
return $query->where("wedding_style", "LIKE", "%$keyword%");
}]);
})

Categories