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

如何将指定原生SQL查询转换为Eloquent以实现分页功能?

方案1:转换为Eloquent/查询构造器写法实现分页

你的原始SQL逻辑本质是获取「用户创建的项目」+「用户通过district_group_project_users关联的项目」的并集,去重后返回完整项目数据,转换为Laravel查询构造器/Eloquent写法后可直接调用内置分页方法:

// 子查询1:获取用户关联的项目ID
$sub1 = DB::table('district_group_project_users')
    ->where('user_id', $id)
    ->select('project_id as id');

// 子查询2:获取用户创建的项目ID
$sub2 = DB::table('projects')
    ->where('created_by', $id)
    ->select('id');

// 合并两个子查询并去重,和原SQL逻辑完全对齐
$unionSub = $sub1->unionAll($sub2)->distinct();

// 写法1:查询构造器直接分页,返回stdClass类型的项目数据
$projects = DB::table('projects')
    ->joinSub($unionSub, 'sub', 'sub.id', '=', 'projects.id')
    ->paginate(10); // 括号内参数为每页展示条数,可自定义

// 写法2:Eloquent模型分页,前提是你已经创建了Project Eloquent模型,返回模型实例
$projects = \App\Models\Project::joinSub($unionSub, 'sub', 'sub.id', '=', 'projects.id')
    ->paginate(10);

上述写法返回的分页实例和Laravel默认paginate方法返回的实例完全一致,可直接调用links()渲染分页组件。

方案2:不改动原始SQL的原生查询分页方案

如果不想调整原SQL逻辑,可以手动通过LengthAwarePaginator实现分页:

use Illuminate\Pagination\LengthAwarePaginator;

$perPage = 10; // 每页条数
$page = request()->input('page', 1); // 读取当前页码,默认第1页
$offset = ($page - 1) * $perPage; // 计算查询偏移量

// 查询符合条件的总条数
$total = DB::select(
    "SELECT COUNT(*) as count FROM projects INNER JOIN(select DISTINCT * from (SELECT project_id FROM district_group_project_users where user_id=? UNION ALL select id from projects where created_by=?) as sub ) as sub on sub.project_id=projects.id",
    [$id, $id]
)[0]->count;

// 给原SQL加分页限制,查询当前页数据
$projects = DB::select(
    "select * from projects INNER JOIN(select DISTINCT * from (SELECT project_id FROM district_group_project_users where user_id=? UNION ALL select id from projects where created_by=?) as sub ) as sub on sub.project_id=projects.id LIMIT ? OFFSET ?",
    [$id, $id, $perPage, $offset]
);

// 实例化分页器,使用效果和内置paginate方法完全一致
$projects = new LengthAwarePaginator(
    $projects,
    $total,
    $perPage,
    $page,
    ['path' => request()->url(), 'query' => request()->query()]
);

注意:两种方案都采用了参数绑定传入用户ID,避免直接拼接SQL产生的注入风险,请勿使用原始代码里的字符串拼接写法。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.10.17 15:36:02