问题
Consider the following case.
we have the Users
table and Tasks
table. they are in relation with belongsToMany
with table task_user
.
How to get the list of all users who are not under any task? i.e. their user_id is not at all under that given task or even in the task_user
table.
why I need this is because like this we can only provide a list of users who are yet to be assigned a task. the task will be assigned to users and not a single user at a time.
Editing_____________
also how to filter with users based on group table? below is not working
$users = Group::with(['subscribers' => function ($q){
$q->doesntHave("tasks");
}])->whereId($gid)->latest()->get();
回答1:
Assuming you've named your relationships properly, you should be able to use doesntHave("tasks")
:
$tasklessUsers = User::doesntHave("tasks")->get();
doesntHave()
checks for the non-existence of the supplied relationship ("tasks"
, in this case) and returns all objects that pass this check.
If your function name is different, use that, but the relationship should be:
User.php
:
public function tasks(){
return $this->belongsToMany(Task::class, "task_user");
}
Edit: doesntHave()
is the simple version, whereDoesntHave()
allows a custom query. See https://laravel.com/docs/5.8/eloquent-relationships#querying-relationship-absence for full details.
Second Edit:
As stated in the comments below, with()
will not filter the Model
it is being called on, so this query won't work as you'd expect:
$users = Group::with(['subscribers' => function ($q){
$q->doesntHave("tasks");
}])->whereId($gid)->latest()->get();
To fix this, use a chained doesntHave()
query:
$query = Group::doesntHave('subscribers.tasks')
->where('id', '=', $gid)
->latest()
->first();
// OR
$query = Group::whereHas('subscribers', function($subQuery){
$subQuery->doesntHave('tasks');
})->where('id', '=', $gid)
->latest()
->first();
$users = $query->subscribers; // Return `users` (aliased to `subscribers`)
Either approach will check the existence of subscribers
that don't have any associated tasks
relationship, and also only return where id
is $gid
.
Note: Used first()
for the queries, as using id
in a query should only ever return a single Group
record, and get()
is for returning multiple records in a Collection
来源:https://stackoverflow.com/questions/59273470/how-to-get-list-of-users-who-are-not-under-belongstomany-relation-under-a-table