【问题标题】:Laravel 5.8 - Eloquent not listening to where on relationLaravel 5.8 - 雄辩的不听关系在哪里
【发布时间】:2020-01-06 07:15:18
【问题描述】:

我正在尝试对名为 employee_label 的关系进行 where 查询。

表格employee_label 如下所示:

+----+-------------+----------+
| id | employee_id | label_id |
+----+-------------+----------+
|  1 |         123 |      123 |
|  2 |         456 |      456 |
|  3 |         768 |      768 |
+----+-------------+----------+

另一个where()orWhere() 默认传递一个空的array(),但可以包含数据,例如:['inactive' => 0]

预期结果:
当我为关系提供标签 123 作为 where() 时,我希望只接收带有标签 123 的员工。

实际结果:
返回所有员工,不过滤数据。

代码:

$employees = Employee::with(['employee_label' => function($query) use ($request) {
    $query->where('label_id', '=', $request->get('label'));
}])->where($searchQuery)->orWhere($orQuery)->orderBy('inactive', 'asc')->paginate(20);

我的尝试:
我尝试将$query->where('label_id') 更改为$query->where('employee_label.label_id'),结果没有任何变化。

型号Employee

class Employee extends Model
{
    protected $table = 'employees';
    protected $fillable = [
        'name',
        'surname',
        'inactive',
        'entered_into_service'
    ];

    public function employee_label() {
        return $this->hasOne('App\EmployeeLabel');
    }

}

型号EmployeeLabel

class EmployeeLabel extends Model
{

    protected $table = 'employee_label';
    protected $fillable = [
        'employee_id',
        'label_id'
    ];

    public function employee() {
        return $this->belongsTo('App\Employee');
    }

    public function label() {
        return $this->belongsTo('App\Label');
    }

}

【问题讨论】:

  • 我认为,您有 ->orWhere($orQuery) 使其之前的条件成为可选,因此您可能需要将其放在闭包内。
  • 请也发布您的模型
  • @PrafullaKumarSahu 刚刚尝试删除->orWhere(),不幸的是结果相同。
  • @AdnanMumtaz 已将它们添加到帖子中。
  • @ChrisDekker 你能把你生成的 sql 查询记录下来并在这里发布吗?

标签: php mysql laravel laravel-5 eloquent


【解决方案1】:

经过长时间的搜索,我终于找到了这个奇怪问题的答案。

显然,您必须使用Employee::whereHas(),而不是使用Employee::with()

所以最终的代码是:

$employees = Employee::whereHas('employee_label', function($query) use ($request) {
    $query->where('label_id', '=', $request->get('label'));
})->where($searchQuery)->orWhere($orQuery)->orderBy('inactive', 'asc')->paginate(20);

请参阅documentation 了解更多信息。

感谢所有帮助过的人!

【讨论】:

  • 是的,你是对的,要根据相关模型过滤模型,你需要使用whereHas方法。
【解决方案2】:

尝试将员工模型更新为:

    public function employeeLabel() {
        return $this->hasOne('App\EmployeeLabel', 'employee_id', 'id');
    }

这会自动绑定关系,因此您不需要在雄辩的调用中。

然后是获取所有员工和相关标签并返回分页的方法:

$employees = Employee::all()->with('employeeLabel')
                            ->orderBy('inactive', 'asc')
                            ->paginate(20);

https://laravel.com/docs/6.x/eloquent-relationships#one-to-one

【讨论】:

    【解决方案3】:

    我想你忘了返回你的 $query 对象

    代替

    $query->where('label_id', '=', $request->get('label'));
    

    尝试从 employee_label 回调方法返回您的 $query

    return $query->where('label_id', '=', $request->get('label'));
    

    【讨论】:

    • 不幸的是,添加 return 并没有改变结果。
    • 这是错误的答案,他明确提到要根据相关模型过滤模型。
    猜你喜欢
    • 2014-04-14
    • 2015-03-14
    • 2018-11-28
    • 2015-01-11
    • 2021-06-03
    • 2020-03-26
    • 1970-01-01
    相关资源
    最近更新 更多