我把头发拉过这个头发,我觉得我已经尝试了各种方法!
这是我的问题。
我有2张桌子
用户
ID | FIRSTNAME | EMAIL_ADDRESS
1 | Joe Bloggs | joe@bloggs.com
状态
ID | USER_ID | STATUS | DATE
1 | 1 | 'In' | 2018-06-04 09:01:00
2 | 1 | 'Out' | 2018-06-04 09:00:00
正如您在上表中所看到的,每个用户都可以拥有多个状态',但每个用户必须拥有1个最新状态,我这样做(请告诉我,如果我做错了)
public function statusCurrent(){
return $this->hasOne('App\Status', 'user_id', 'id')->orderBy('date', 'desc')->limit(1);
}
然后我在我的视图中显示了一个表单,它通过$request
将过滤器传递给控制器。
我需要能够使用过滤器,并将它们应用到最近的1个状态。例如,如果有人搜索日期2018-06-04 09:00:00
和用户ID 1
,我需要它显示无结果,因为该用户的1条最新记录与该日期不匹配,但是在如果它不匹配,它将跳过最近的一个,并获得下一个记录。
我尝试了似乎所有方法,我尝试过这样的
$users = Users::with(['StatusCurrent' => function($query){
$query->where('status.status', 'In');
}])->get();
哪个获得了正确的最新行,但是如果我尝试status.status, 'out'
,那么它只会跳过并获得状态为out的记录号2。
我也尝试过这样的
$users = Users::has('StatusCurrent')->paginate(10);
if(!empty($request->statusIn)){
$users = $users->filter(function ($item){
$item = $item->statusCurrent->status == 'in';
return $item;
});
}
return $users;
哪个效果很好但是在尝试为过滤器添加任何GET
参数时,分页会中断。
普通英语
我需要能够获得用户的最新状态,然后一旦我拥有它,我需要能够在其中应用where语句/过滤器/参数,如果它们不匹配,则完全忽略那个用户。
答案 0 :(得分:1)
您必须将JOIN与子查询结合起来:
$users = User::select('users.*')
->join('status', 'users.id', 'status.user_id')
->where('status.status', 'in')
->where('status.id', function($query) {
$query->select('id')
->from('status')
->whereColumn('user_id', 'users.id')
->orderByDesc('date')
->limit(1);
})
->get();
答案 1 :(得分:0)
您可以先获取ID,然后使用过滤器进行查询:
$status_id = Users::find($user_id)->statusCurrent()->id;
现在使用$status_id
子句中的whereHas
执行实际查询:
$users = Users::with('statusCurrent')
->whereHas('statusCurrent', function($query) use($status_id) {
$query->where('status.status', 'In')
->where('id',$status_id);
})->get();