Laravel查询筛选问题:如何正确获取指定条件的请求记录
问题分析与修正方案
让我帮你拆解一下查询出错的核心原因,再给出符合需求的正确写法:
1. 逻辑运算符优先级混乱
你混用了where和orWhere但没有做分组处理,而SQL中AND的优先级高于OR,导致你的查询实际执行的逻辑完全偏离预期:
WHERE (asset_status_tracker.status_before != null) OR (asset_status_tracker.changed_by = $approver_id) OR (asset_request.approver_id = $approver_id AND asset_status_tracker.status_after = '17')
这种逻辑会把大量无关记录(比如003、005)也包含进来,因为只要满足其中一个松散的条件就会被返回。
2. 多余的条件限制
你额外添加了where('asset_status_tracker.status_after','=','17'),但你的需求里,status_tracker表中changed_by='1866'的记录(比如001的status_after=18、004的status_after=19)也需要被纳入,这个条件直接把这些符合要求的记录过滤掉了。
另外,判断字段非null应该用Laravel的whereNotNull方法,而不是!= null,后者在SQL中可能不会按预期工作。
正确的Laravel查询写法
根据你的需求,我们需要分组两个OR核心条件:要么是request表中approver_id=1866且status_id=17,要么是status_tracker表中changed_by=1866。具体代码如下:
$approver_id = '1866'; $users = DB::table('asset_status_tracker') ->leftJoin('asset_request', 'asset_status_tracker.request_id', '=', 'asset_request.request_id') ->where(function ($query) use ($approver_id) { // 条件1:status_tracker中操作人是指定ID $query->where('asset_status_tracker.changed_by', '=', $approver_id) // 条件2:request中审批人是指定ID且状态为已审核(17) ->orWhere(function ($subQuery) use ($approver_id) { $subQuery->where('asset_request.approver_id', '=', $approver_id) ->where('asset_request.status_id', '=', 17); }); }) // 可选:去重同一个request_id的重复记录 ->distinct('asset_status_tracker.request_id') ->get();
逻辑说明
- 外层闭包用
OR连接两个核心条件,确保符合任一要求的记录都会被选中。 - 内层闭包把
approver_id和status_id用AND绑定,保证只有已审核且审批人是指定ID的request记录才会被纳入。 - 添加
distinct是为了避免同一个request_id因为多条tracker记录被重复返回(比如001有4条tracker记录,但我们只需要它出现一次)。
执行这个查询后,你会得到预期的记录:001、002、004。
内容的提问来源于stack exchange,提问作者user3386779
相关产品推荐
相关产品推荐

