【问题标题】:Laravel Eloquent How Can I Select Using Condition "where" for pivot tableLaravel Eloquent 如何选择使用条件“where”作为数据透视表
【发布时间】:2019-09-24 14:46:18
【问题描述】:

我有三个数据库表,分别称为 user(id,name)、group(id,name) 和 user_group(user_id, group_id,valid_before),它们的关系是多对多的。

class User extends Model
{
    protected $table = 'user';

    public function groups()
    {
        return $this->belongsToMany(Group::class, 'user_group')
               ->withPivot('valid_before');
    } 
}

class Group extends Model
{
    protected $table = 'group';

    public $timestamps = false;

public function user()
{
    return $this->belongsToMany(User::class, 'user_group');
}
}

如何选择所有拥有

的用户(使用 Eloquent)
valid_before < $some_date

?

【问题讨论】:

  • valid_before 字段是否属于user 表?如果是,您不需要在此处进行支点。就像select * from users where valid_before &lt; some_date
  • 否,valid_before 属于 user_group 表。

标签: laravel laravel-5 eloquent


【解决方案1】:

有很多方法可以实现这一目标。我将向您展示一个使用 query scopes 的示例。

在您的User 课程中,您必须进行一些更新:

class User extends Model
{
    protected $table = 'user';

    public function groups()
    {
        return $this->belongsToMany(Group::class, 'user_group')
               //->withPivot('valid_before'); <-- Remove this
    }
}

并在您的 Group 模型中创建一个范围:

class Group extends Model
{
    protected $table = 'group';

    public $timestamps = false;

    public function user()
    {
        return $this->belongsToMany(User::class, 'user_group');
    }    

    /**
     * This scope gets as input the date you want to query and returns the users collection
     *
     * @param  \Illuminate\Database\Eloquent\Builder $query
     * @param  string $date
     * @return \Illuminate\Database\Eloquent\Builder
     */
    public function scopeUsersValidBefore($query, $date)
    {
        return $query->users()->wherePivot('valid_before', '<', $date);
    }
}

现在,我想您有一个GroupController,它在某处创建了一个查询来检索之前的有效用户。比如:


// [...]

$users = Group::usersValidBefore($yourDate)->get();

// [...]

如果您想从另一方创建查询,我的意思是您想使用 User 模型并列出与填充的 valid_before 具有枢轴关系的所有用户,而不是正确的方法是创建 UserGroup intermediate model 可轻松用于创建查询。

【讨论】:

  • 查询范围在 Laraval 8.x.x 中不可用
  • @HarshalLonare 是的。看看docs
【解决方案2】:

如果你使用的是 Laravel 8.x.x

内联关系存在查询更容易

如果您想使用附加到关系查询的单个简单 where 条件来查询关系是否存在,您可能会发现使用 whereRelation 和 whereMorphRelation 方法更方便。例如,我们可能会查询所有包含未批准 cmets 的帖子:

use App\Models\Post;

$posts = Post::whereRelation('comments', 'is_approved', false)->get();

当然,就像调用查询构建器的 where 方法一样,你也可以指定一个操作符:

$posts = Post::whereRelation(
    'comments', 'created_at', '>=', now()->subHour()
)->get();

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 2018-09-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-07-10
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多