Add where clause to relations table in laravel - php

I have a question. This query gets me the needed data and that includes the related table delivery
$RS = $this->instance->user()->with(['driver.trailer', 'driver.truck', 'driver.delivery']);
I researched this topic, and I think part below should do the trick, but I don't know how to combine the two together.
//add WHERE clause to driver.delivery:
->whereBetween('created_at', [
Carbon\Carbon::parse('last monday')->startOfDay(),
Carbon\Carbon::parse('next sunday')->endOfDay(),])
->get();
I am new to Laravel (doing it for about 10 days now) and this concept is very new to me. (I have no issues writing a standard query)

Try this:
return $this->instance->user()->with(['driver.delivery' => function($query){
$query->whereBetween('created_at', [
Carbon\Carbon::parse('last monday')->startOfDay(),
Carbon\Carbon::parse('next sunday')->endOfDay() ]);
}])->with(['driver.trailer' 'driver.truck'])->get();

Related

Laravel query with eloquent

Good morning.
I have a question that I can't solve with eloquent, let me put it in context.
I have several farms I need all the subscribers of that farm that are taken out through a pivot table and in turn all the receipts of those subscribers, so far so good.
The problem comes in that I put a condition in the dates of the receipts, and I want that it does not extract the subscribers that do not fulfill that condition.
$estates = Estate::with(['adminEstate.neighbours' => function ($query) use ($past_date_init) {
$query->with(['receiptHeader' => function ($query2) use ($past_date_init) {
$query2
->where('receipt_h_billing_init', '<=', $past_date_init)
->where('receipt_h_billing_end', '>=', $past_date_init);
$query2->with('receiptDetail');
}
]);
}])->get();
If they do not meet the date condition, I will not be able to get the subscribers.
Thanks for your help
Well for now you can use
query2
->whereDate('receipt_h_billing_init', '<=', $past_date_init)
->whereDate('receipt_h_billing_end', '>=', $past_date_init);
query2
->whereBetween(DB::raw('Date(receipt_h_billing_init)'),[$past_date_init, $past_date_init]);
as you can see here I didn't use whereBetween because it will compare also the time the first one will work fine

How to set alias table name in Laravel table model

I have this query builder in Laravel:
$obj_table = MyTable::get();
Now, how to make my MyTable to have alias name?
The reason I need this, I need to use with() and Joining with my another tables.
Anyone got the same problems with me?
Thanks!
From laravel documentaion
You may also alias the relationship count result, allowing multiple counts on the same relationship:
$posts = Post::withCount([
'comments',
'comments AS pending_comments' => function ($query) {
$query->where('approved', false);
}
])->get();
For more information have a look at
https://laravel.com/docs/5.4/eloquent-relationships
Cheers,
Hope this helps

Eloquent eager loaded query not quite working with joins

I'm working on a Chemical database and am learning Eloquent as I go. This is in Slim Framework, not Laraval itself.
This thread helped get me close to what I need, but now I'm seeing something odd and I haven't been able to find a solution, though lots of people asking similar questions.
I have
$chemicals = $app->Chemical->with(array('Company', 'Room', 'Location', 'Measurement'))
->join('company', 'company_id', '=', 'company.id')
//->join('room', 'room_id', '=', 'room.id')
//->join('location', 'location_id', '=', "location.id")
->where('company', '=', 'ROUSSEL')
->get();
Notice the 2 Joins commented out. Those 2 fields do display properly in my table, but company is blank. If I switch which join is shown, it follows suit.
If I don't use any of the joins, I can do a where just fine with one of the chemical fields. My question is why does having a join seem to break that particular With statement and is there a way to fix it? I get the feeling that it's something to do with the With statement doing some kind of behind the scenes join, but I haven't been able to find any specifics..
Thanks,
Forgot to mention I had tried Eager Loading Constraints before as well.
$chemicals = $app->Chemical->with(
array(
'Company',
'Room',
'Measurement',
'Location' => function ($query) {
$query->where('location', '=', 'FLAMCAB');
}
))
//->where('company', '=', 'FISHER')
->get();
Using above without the where commented out gives me the message that the chemicals table does not have a column called company, which is true.
Not using it, I do get results:
As you can see it does filter the locations table, but it does only that, it doesn't filter chemicals by that, which is what I'm trying to do.
If you want to filter Chemicals based on their related Locations, you can combine constraining eager loads with querying relationship existence:
$filter = function ($query) {
$query->where('location', '=', 'FLAMCAB');
};
$chemicals = $app->Chemical->with(
array(
'Company',
'Room',
'Measurement',
'Location' => $filter
)
->whereHas('location', $filter)
->get();
I'm not sure how efficient this is though - you might want to check out the resulting query. Another option is to simply filter the collection using Collection filters after you run the query.
This question: Complex query with filters with Eloquent might also help you.

Deeply nested relationships filtering

Recently I faced problem accessing and filtering deeply nested relationship, so I decided to seek for a help.
So, I have this db structure:
http://s21.postimg.org/motrjy3dj/Screenshot_from_2015_07_24_12_14_51.png
And I need to get all teams within a project, and then for each team I need to get assigned users (of that team).
So far so good, my problem starts when I try to get the offer for each user. User can have only one offer for the assigned team which brings me to a problem.
Here is my code:
$project = Project::with("variants")
->with(array(
"teams" => function($query) {
$query->with(array(
"users" => function($query) {
$query->with("offers");
}
));
}
))
->find($projectID);
I have a hasManyThrough relationship "offers" in the "User" model which returns me all offers for user, but actually I just need (one) offer for related team_user table.
I tried filtering offers with scopes but it's a bad solution, because for each user I have additional query to db..
Is there some way to filter these offers dynamically?
Thanks!
I highly recommend using joins for this sort of complex query:
$projectOffers = Project
->join('team', 'team.project_id', '=', 'project.id')
->join('team_user', 'team_user.team_id', '=', 'team.id')
->join('user', 'user.id', '=', 'team_user.user_id')
->join('offer', 'offer.id', '=', 'team_user.offer_id')
->get([
'project.id',
'team.id AS team_id',
'user.id AS user_id',
'offer.id AS offer_id',
// any other columns you want
]);

Querying relations with a where clause on the child table

I have been using the has method to query the existence of data in a related table and that is working just fine. Using the code example on the Laravel web site, you can do the following to get any post that has comments associated with it.
$posts = Post::has('comments')->get();
What I would like to be able to do, as an example, is query for any post which has comments from the last thirty days. Since the has method only has the ability to count related rows I am not sure of a good way to do this.
Ok, this is what I could come up with. It might not be the best solution, but it does work and doesn't seem too polluted. First, we'll need to add reference to Carbon and the Eloquent\Collection classes.
use \Carbon\Carbon;
use \Illuminate\Database\Eloquent\Collection;
Carbon does come with Laravel as a dependency, out of the box, but it would be smart to add it to your own project's dependencies anyway. Then, this code should do it:
// Gather all distinct 'post_id' from Comments made in the last 30 days
// along with its Post objects
$comments = Comment::with('Post')
->where('created_at', '>', Carbon::now()->subMonth())
->distinct()
->get(array('post_id'));
// Since we only want Posts, loop through the Comments collection and add
// the Posts to a new collection
$posts = new Collection;
foreach ($comments as $comment) {
$posts->add($comment->post);
}
From the Laravel 4 Documentation:
$posts= Post::with(array('comments' => function($query)
{
$query->where('published', '>=', 'date- 1 month'); //look date functions up
}))->get();
See Eager Load Constraints under laravel 4 documentation

Categories