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

Laravel Eloquent实现PostgreSQL WITH查询的技术问题

解决方案

在Laravel里可以直接通过查询构建器的with方法定义CTE,不需要绕路用from传查询实例,直接把你已经构建好的查询作为CTE的子查询即可,具体代码如下:

// 构建带左连接和distinct的子查询
$subQuery = Model::query()
    ->distinct('models.id')
    ->leftJoin('blah', 'blah.id', '=', 'models.blah_id')
    ->orderByRaw('models.id, blah.created_at desc');

// 定义CTE并查询
$result = DB::query()
    ->with('list', function ($query) use ($subQuery) {
        // 将子查询作为CTE的数据源
        $query->fromSub($subQuery, 'list');
    })
    ->select('*')
    ->from('list')
    ->orderBy('created_at', 'desc')
    ->get();

也可以用更简洁的写法,直接把子查询传入with:

$subQuery = Model::query()
    ->distinct('models.id')
    ->leftJoin('blah', 'blah.id', '=', 'models.blah_id')
    ->orderByRaw('models.id, blah.created_at desc');

$result = DB::query()
    ->with(['list' => $subQuery])
    ->select('*')
    ->from('list')
    ->orderBy('created_at', 'desc')
    ->get();

说明

  • 这里用的with是查询构建器的CTE定义方法(区别于Eloquent关联的with),第一个参数是CTE的名称(比如这里的list),第二个参数用来定义CTE的具体内容。
  • fromSub方法可以直接把查询构建器实例转换成子查询,无需手动拼接SQL字符串,完美适配你的需求。
  • 最终的查询逻辑和你想要的SQL结构完全一致:先定义包含左连接和去重的CTE,再从CTE中查询并排序。

内容的提问来源于stack exchange,提问作者Jaquarh

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.07.11 23:44:56