php - 首发,laravel最优雅的分表、关联、分页查询,手册方法的熟练运用。 - 个人文章 - SegmentFault 思否


本站和网页 https://segmentfault.com/a/1190000010750380 的作者无关,不对其内容负责。快照谨为网络故障时之索引,不代表被搜索网站的即时页面。

php - 首发,laravel最优雅的分表、关联、分页查询,手册方法的熟练运用。 - 个人文章 - SegmentFault 思否
注册登录问答专栏标签招聘活动发现✓使用“Bing”搜本站使用“Google”搜本站使用“百度”搜本站站内搜索注册登录首发,laravel最优雅的分表、关联、分页查询,手册方法的熟练运用。吟渐的小风dee595关注作者首页专栏php文章详情27首发,laravel最优雅的分表、关联、分页查询,手册方法的熟练运用。吟渐的小风dee595发布于2017-08-20  
前几天写了一遍关于laravel分表关联的查询,但是我个人觉得还不算完美,于是今天重新看了一下laravel模型的底层代码,终于写出我暂时觉得最满意的代码-laravel风格,简洁、优雅是核心。
下面直接上demo代码,主要是3个表,一个用户表,一个是用户送礼表,送礼表按月分表
user表id用户IDnickname昵称
<?php
namespace App\Models;
use Eloquent;
class User extends Eloquent
send_gift_2017_07,send_gift_2017_08 送礼表id自增主键user_id用户IDworth礼物价值uper_id主播ID(也是用户表的)created_at送礼时间
<?php
namespace App\Models;
use Eloquent;
class SendGift extends Eloquent
//关联用户表,外键是user_id
public function user()
return $this->belongsTo(User::class);
关联用户表 外键是uper_id
public function uper()
return $this->belongsTo(User::class);
现在做一个输入开始日期和结束日期查看用户的送礼记录并且分页。
<?php
namespace App\Http\Controllers;
use App\Models\SendGift;
use DB;
use Carbon\Carbon;
class IndexController extends Controller
public function index()
// 开始日期,和日期有关的,都建议用内置的carbon处理,非常好用,而且简洁
$start = Carbon::parse(request('start'));
// 结束日期
$end = Carbon::parse(request('end'));
// 查询集合
$queries = collect();
// 循环比较年月,添加每一张表的查询
for ($i = $start->copy(); $i->format('Y-m') <= $end->format('Y-m'); $i->addMonth()) {
$queries->push(
DB::table("send_gift_{$i->format('Y_m')}")
// 建议都用select查询字段,SQL尽可能的优化性能
->select('user_id', 'worth', 'uper_id', 'created_at')
->whereBetween('created_at', [$start, $end->tomorrow()])
);
// 出列一张表作为union的开始
$unionQuery = $queries->shift();
// 循环剩下的表添加union
$queries->each(function ($item, $key) use ($unionQuery) {
$unionQuery->unionAll($item);
});
// 设置临时表的名称,添加临时表,顺序不能反过来,否则用关联约束会找不到表
$lists = with(new SendGift)->setTable('union_send_gift')
// 添加临时表
->from(DB::raw("({$unionQuery->toSql()}) as union_send_gift"))
// 合并查询条件
->mergeBindings($unionQuery)
// 关联约束,不在用户表的不用查出来
->has('user')
// 按时间倒序
->orderBy('created_at', 'desc')
// 分页
->paginate();
// 加载关联关系
$lists->load([
'user' => function ($query) {
// 关联查询也要优化sql
$query->select('id', 'nickname');
},
'uper' => function ($query) {
$query->select('id', 'nickname');
]);
// 测试结果
$lists->each(function ($item, $key) {
echo "用户:{$item->user_id}-{$item->user->nickname}在{$item->created_at->toDateTimeString()}送出了价值{$item->worth}元的礼物给主播:{$item->uper_id}-{$item->uper->nickname}<br>";
});
然后我们看看SQL。
关联查询用了渴求式加载,就能有效减少SQL的条数,保证数据库的性能。
phplaravel阅读 16.8k发布于 2017-08-20 赞27收藏32分享本作品系原创,采用《署名-非商业性使用-禁止演绎 4.0 国际》许可协议吟渐的小风dee595 声望20 粉丝关注作者0 条评论得票最新提交评论评论支持部分 Markdown 语法:**粗体** _斜体_ [链接](http://example.com) `代码` - 列表 > 引用。你还可以使用 @ 来通知其他用户。推荐阅读如何使用 PHPStorm 进行优雅的项目开发?PHP Storm 这个开发工具,很多 phper 应该有所耳闻,甚至也有不少人使用其作为生产工具,但是很多人都没有最大限度的使用它,本文就来总结一些优雅开发的小技巧。唯一丶赞 45阅读 4.6k评论 7One 一个简洁的博客、微博客系统代码:[链接]文档:[链接]系统预览首页:微博列表:微博详细:文章列表:文章详细:归档:搜索,目前只能依据分类、标签搜索😀:管理后台:Eyeswap赞 45阅读 2.2k评论 1怎样用 PHP 来实现枚举?在数学和计算机科学理论中,一个集的枚举是列出某些有穷序列集的所有成员的程序,或者是一种特定类型对象的计数。这两种类型经常(但不总是)重叠。枚举是一个被命名的整型常数的集合,枚举在日常生活中很常见,...唯一丶赞 25阅读 6.1k评论 4PHP 性能终极 Debug - 生成火焰图2012 年刚开始学习 PHP,那个时候的 PHP 应用很简单,没有太多复杂的设计模式,像依赖注入,工厂模式这些还几乎没有,Reflection API 那时也才刚出来,一个 PHP 应用就是一些包了前端代码的脚本文件,正是因为 PH...路易港赞 5阅读 3.4kLaravel : Syntax error or access violation: 1055 Error?上面这样一段代码, 测试服务器很好, 上线后报错了.Syntax error or access violation: 1055 Error : MySQL : isn't in GROUP BY云云小金子赞 7阅读 12k评论 4golang实现php里的serialize()和unserialize()序列和反序列方法Golang 实现 PHP里的 serialize() 、 unserialize()安装 {代码...} 用法 {代码...} github地址:[链接]JonLee赞 2阅读 6.6k郑方方打怪升级日记 — 初识HTML5与CSS3任务名称:响应式砸蛋页面任务背景前辈:方方啊,最近项目也没什么事情,你看这个砸蛋页面不是很好看,要不你做一个响应式砸蛋页面吧?系统:郑方方接下前辈的任务 - 郑方方自动解析任务步骤任务:响应式砸蛋页面HTML5与C...郑方方赞 1阅读 3.1k评论 3吟渐的小风dee595 声望20 粉丝关注作者宣传栏文章目录跟随▲2732产品热门问答热门专栏热门课程最新活动翻译酷工作课程Java 开发课程PHP 开发课程Python 开发课程前端开发课程移动开发课程资源每周精选用户排行榜帮助中心建议反馈合作关于我们广告投放职位发布讲师招募联系我们合作伙伴关注产品技术日志社区运营日志市场运营日志团队日志社区访谈条款服务协议隐私政策下载 AppCopyright © 2011-2022 SegmentFault. 当前呈现版本 22.12.19浙ICP备15005796号-2浙公网安备33010602002000号ICP 经营许可 浙B2-20201554杭州堆栈科技有限公司版权所有