Laravel+MongoDB下如何按关联模型的game.name字段排序查询数据?
解决Laravel+MongoDB环境下按关联模型字段排序的问题
问题原因
你当前的写法不生效,核心原因是with()属于延迟加载:Laravel会先查询games_played集合的主数据,再批量查询关联的games集合数据,最后将关联结果附加到主模型上。主查询阶段根本不存在game.name这个字段,因此orderBy('game.name')不会产生任何排序效果。
解决方案
方案1:使用关联Join(推荐,保持Eloquent模型特性)
通过join将games集合的字段关联到主查询中,直接基于关联字段排序:
// 假设GamesPlayed对应集合为games_played,Game对应集合为games $sortDir = request()->input('sort_dir', 'DESC'); // 从请求获取排序方向,默认倒序 $gamesPlayedRequest = GamesPlayed::select( 'games_played.created_at', 'games_played.user_id', 'games_played.game_id', 'games_played.score' ) ->join('games', 'games_played.game_id', '=', 'games._id') ->orderBy('games.name', $sortDir) ->with('game:id,name');
- 优点:返回的仍是Eloquent模型实例,可直接使用模型的方法和属性
- 适配表格排序场景:前端点击表头时,传入
sort_dir参数(如ASC/DESC)即可切换排序方向
方案2:使用MongoDB原生聚合查询
如果需要更贴合MongoDB文档特性,可使用聚合操作实现关联+排序:
$sortOrder = request()->input('sort_dir') === 'ASC' ? 1 : -1; // 1正序,-1倒序 $gamesPlayedRequest = GamesPlayed::raw(function($collection) use ($sortOrder) { return $collection->aggregate([ // 关联games集合 [ '$lookup' => [ 'from' => 'games', 'localField' => 'game_id', 'foreignField' => '_id', 'as' => 'game' ] ], // 展开关联的game数组(lookup默认返回数组) [ '$unwind' => '$game' ], // 按game.name排序 [ '$sort' => ['game.name' => $sortOrder] ], // 只返回需要的字段 [ '$project' => [ 'created_at' => 1, 'user_id' => 1, 'game_id' => 1, 'score' => 1, 'game._id' => 1, 'game.name' => 1 ] ] ]); });
- 注意:聚合查询返回的是数组而非Eloquent模型实例,若需模型实例需额外转换
内容的提问来源于stack exchange,提问作者Liiisey
相关产品推荐
相关产品推荐

