You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

Laravel按用户分组查询工厂消息时如何获取每组最新message_text

解决方案

你可以通过分组拼接取首值或者子查询两种方式实现需求,以下是适配你现有代码的修正方案:

return Messages::where('factory_id', '=', 27)
    ->select(
        'user_id',
        DB::raw('COUNT(*) as total'),
        // 按消息ID倒序拼接后取第一条,即为最新消息内容
        DB::raw('SUBSTRING_INDEX(GROUP_CONCAT(message_text ORDER BY id DESC SEPARATOR "|||"), "|||", 1) as latest_message')
    )
    ->groupBy('user_id')
    ->with(['user' => function($query) {
        // 对齐users表的字段名profile_pic
        $query->select('id', 'name', 'profile_pic');
    }])
    ->get();

关键说明

  • 你原有代码中的leftjoin('users')属于冗余逻辑,with预加载已经会单独拉取关联用户数据,无需额外连表。
  • GROUP_CONCAT默认拼接分隔符是逗号,如果你的消息内容可能包含逗号,可以自定义SEPARATOR为非常用字符避免截断错误。
  • 注意你原有预加载语句中写的profilepic和users表实际字段profile_pic不一致,需要修正才能正常获取头像字段。

大数据量优化方案(Laravel 6+支持)

如果消息表数据量较大,使用子查询的方式性能更好:

return Messages::where('factory_id', 27)
    ->select('user_id', DB::raw('COUNT(*) as total'))
    ->addSelect(['latest_message' => Message::select('message_text')
        ->whereColumn('user_id', 'messages.user_id')
        ->where('factory_id', 27)
        ->latest('id')
        ->take(1)
    ])
    ->groupBy('user_id')
    // 简化预加载字段写法
    ->with('user:id,name,profile_pic')
    ->get();

内容的提问来源于stack exchange,提问作者reza haj rahimi

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.05 15:18:03