Laravel 中如何根据其他 Model 上的现有记录过滤记录(实现用户拦截)

问题描述 投票:0回答:1

我有一个

User
模型和一个
Blocklist
模型,现在当我调用
User::all()
时,我只想返回根据阻止列表中的记录不相关的用户。

例如:

user
桌子

id ...
1 ...
2 ...
3 ...
4 ...
5 ...

blocklist
桌子

id 用户 ID 可阻止_id 可阻止_类型
1 1 2 \应用程序\模型\用户
2 1 3 \应用程序\模型\用户
2 5 1 \应用程序\模型\用户

User
型号

...

public function blocklist()
{
    return $this->hasMany(Block::class);
}

Blocklist
型号

...

public function blockable(): MorphTo
{
   return $this->morphTo();
}

UserController

...
$users = \App\Models\User::whereDoesntHave('blocklist', function (Builder $query) {
    $query->where('user_id', auth('sanctum')->id());
    $query->orWhere(function (Builder $query) {
       $query->where('blockable_id', auth('sanctum')->id());
       $query->where('blockable_type', User::class);
    });
})->all();

这个想法是,如果

user: 1
提出此请求,他们不应该看到他们已阻止的
user: 2
user: 3
,而且他们也不应该看到也阻止了他们的
user: 5
,但事实并非如此。有效,无论我做什么,所有用户仍然会返回。

php laravel database eloquent laravel-11
1个回答
0
投票

我认为这可能会对您有所帮助,您的查询中存在一个小逻辑错误,您应该检查 user_id 是否匹配,而不是检查 blockable_id 是否等于身份验证用户的 id。

$users = \App\Models\User::whereDoesntHave('blocklist', function (Builder $query) {
$query->where('user_id', auth('sanctum')->id()); // Check if the authenticated user is blocking someone
$query->orWhere(function (Builder $query) {
    $query->where('blockable_id', auth('sanctum')->id()); // Check if someone is blocking the authenticated user
    $query->where('blockable_type', User::class);
});
})->get();
© www.soinside.com 2019 - 2024. All rights reserved.