Laravel查询users表获取用户信息 用户不存在时如何处理报错
问题根源
findOrFail()方法在用户不存在时会直接抛出404异常,不会进入你写的else分支,头用户判断逻辑完全失效- 查询第二层后代(
lsu/rsu/ltu/rtu)时,没有判断上层用户($lfu/$rfu)是否为null,直接访问$lfu->id会触发「尝试访问null的属性」错误,这就是你说的无后代时报错的核心原因 - 冗余查询:每次先调用
exists()再调用first(),相当于对同一条件执行两次SQL查询,性能低下 - 视图代码存在变量拼写错误:
$lsu对应的Network Worth字段错误调用了$lfu->network_bonus
修复方案
第一步:控制器代码基础优化
public function show_genealogy($id) { // 用find代替findOrFail,找不到自动返回null,无需额外判断 $headuser = User::find($id); $lfu = $rfu = $lsu = $rsu = $ltu = $rtu = null; if ($headuser) { // 直接first(),不存在自动返回null,无需exists判断 $lfu = User::where('l_id', $headuser->id)->first(); $rfu = User::where('r_id', $headuser->id)->first(); // 先判断上层用户存在再查询后代,避免访问null属性报错 if ($lfu) { $lsu = User::where('l_id', $lfu->id)->first(); $rsu = User::where('r_id', $lfu->id)->first(); } if ($rfu) { $ltu = User::where('l_id', $rfu->id)->first(); $rtu = User::where('r_id', $rfu->id)->first(); } } return view('users.genealogy-tree', compact('headuser','lfu','rfu','lsu','rsu','ltu','rtu')); }
第二步:更优方案(推荐):使用Eloquent关联减少查询
先在User模型中定义关联关系:
// app/Models/User.php public function leftChild() { return $this->hasOne(User::class, 'l_id'); } public function rightChild() { return $this->hasOne(User::class, 'r_id'); }
控制器可以简化为以下代码,预加载三层数据只需要4次SQL查询,性能远高于单独多次查询:
public function show_genealogy($id) { $headuser = User::with([ 'leftChild.leftChild', 'leftChild.rightChild', 'rightChild.leftChild', 'rightChild.rightChild' ])->find($id); return view('users.genealogy-tree', compact('headuser')); }
对应视图里直接用链式属性访问后代即可:
- 第一层左后代:
$headuser?->leftChild - 第二层左左后代:
$headuser?->leftChild?->leftChild,其他后代以此类推,和原来的变量逻辑完全一致
第三步:视图代码优化
- 修复
$lsu对应的Network Worth字段的变量拼写错误 - 用PHP null合并运算符
??简化三元判断:把类似{{$headuser->name ? $headuser->name : 'No Record'}}的写法改成{{ $headuser->name ?? 'No Record' }},逻辑完全一致更简洁。
内容的提问来源于stack exchange,提问作者WonderPlug
相关产品推荐
相关产品推荐

