Laravel Eloquent分表方法并使用模型关联的实现


Posted in PHP onNovember 25, 2019

众所周知 Laravel 是 PHP 开发项目最优美的框架之一,尤其是 Eloquent 对数据库的操作提供了特别多的便利。
在实际开发中我们经常涉及到分库分表场景,那么怎样才能继续配合 Eloquent 优雅的使用 Model 模型呢,接下来给大家分享下我在实际开发中所遇到的问题。(备注:此方法来源 Stack OverFlow 原文地址找不到了,配合我们实际项目更能清晰表述)

1、假设我们有一万本书籍,每本书籍有两千章节,我们创建数据库时的表结构是书籍信息表:books;以及章节信息表:chapters,前面说到书籍越多章节数也就越多解决方案是将章节表分成十个形式为 chapters_0、chapters_1、......chapters_9 表后缀规则是书籍 ID 与 10 取余,这样所有的书籍章节会分散在这 10 个 chapters 中。

2、表建好后开始创建 model 模型,按照惯例所有的模型都将写在 App\Models 下;首先我们先创建一个类名为 Model 的模型并继承 Illuminate\Database\Eloquent\Model

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Model as EloquentModel;

class Model extends EloquentModel
{
  protected $suffix = null;

  // 设置表后缀
  public function setSuffix($suffix)
  {
    $this->suffix = $suffix;
    if ($suffix !== null) {
      $this->table = $this->getTable() . '_' . $suffix;
    }
  }

  // 提供一个静态方法设置表后缀
  public static function suffix($suffix)
  {
    $instance = new static;
    $instance->setSuffix($suffix);

    return $instance->newQuery();
  }

  // 创建新的"chapters_{$suffix}"的模型实例并返回
  public function newInstance($attributes = [], $exists = false)
  {
    $model = parent::newInstance($attributes, $exists);
    $model->setSuffix($this->suffix);

    return $model;
  }
}

2、其他模型全都继承以上的 Model 而不是继承 Illuminate\Database\Eloquent\Model,获取某本书的章节 controller

<?php

namespace App\Http\Controllers;

use App\Models\{Book, Chapter};

class ChaptersController extends Controller
{
  public function chapter (Book $book)
  {
    // 章节列表(普通查询)
    $list = Chapter::lists($book->id);

    // 章节列表(使用模型关联)
    $list = $book->chapters()->oldest('id')->get();
  }
}

3、chapter 模型(普通查询)

<?php

namespace App\Models;

class Chapter extends Model
{
  public static function lists ($bookId)
  {
    $suffix = $bookId % 10;
    /*
    * 例如 $sufiix = 1; 我要要获取的就是:chapters_1的模型实例
    * 使用Model类中提供的静态方法创建该表的模型实例
    * 返回指定书籍的章节
    */
    return self::suffix($suffix)->where('book_id', $bookId)->get();
  }
}

3、好了,我们章节的分表模型已经完成了。那么如何使用模型关联呢?我们来看 Book 模型如何关联 Chapter

<?php

namespace App\Models;

use Illuminate\Database\Eloquent\Relations\HasMany;

class Book extends Model
{
  public function chapters ()
  {
    /*
    * books表的id和chapters表中的book_id关联
    * 一对多关系(一本书对应多条章节)
    */
    $instance = new Chapter();
    $instance->setSuffix($this->id % 10);

    $foreignKey = $instance->getTable . '.' . $this->getForeignKey();
    $localKey = $this->getKeyName();

    return new HasMany($instance->newQuery(), $this, $foreignKey, $localKey);
  }
}

到此 model 发表查询及 model 关联就完成了,如果有其他更好的方式,请大家不吝赐教。第一次发表文章,如有不对的地方希望大家多多指教!!也希望大家多多支持三水点靠木。

PHP 相关文章推荐
PHP读取MySQL数据代码
Jun 05 PHP
Ext.data.PagingMemoryProxy分页一次性读取数据的实现代码
Apr 07 PHP
php自动注册登录验证机制实现代码
Dec 20 PHP
smarty获得当前url的方法分享
Feb 14 PHP
php初始化对象和析构函数的简单实例
Mar 11 PHP
ThinkPHP让分页保持搜索状态的方法
Jul 02 PHP
php面象对象数据库操作类实例
Dec 02 PHP
PHP实现递归无限级分类
Oct 22 PHP
几个优化WordPress中JavaScript加载体验的插件介绍
Dec 17 PHP
php图片上传类 附调用方法
May 15 PHP
基于php判断客户端类型
Oct 14 PHP
PHP对称加密算法(DES/AES)类的实现代码
Nov 14 PHP
PHP call_user_func和call_user_func_array函数的简单理解与应用分析
Nov 25 #PHP
使用Git实现Laravel项目的自动化部署
Nov 24 #PHP
PhpStorm 如何优雅的调试Hyperf的方法步骤
Nov 24 #PHP
laravel框架中视图的基本使用方法分析
Nov 23 #PHP
laravel框架中表单请求类型和CSRF防护实例分析
Nov 23 #PHP
laravel框架中控制器的创建和使用方法分析
Nov 23 #PHP
laravel框架模型中非静态方法也能静态调用的原理分析
Nov 23 #PHP
You might like
用php写的serv-u的web申请账号的程序
2006/10/09 PHP
PHP中::、-&amp;gt;、self、$this几种操作符的区别介绍
2013/04/24 PHP
实现获取http内容的php函数分享
2014/02/16 PHP
几个比较经典常用的jQuery小技巧
2010/03/01 Javascript
js onkeypress与onkeydown 事件区别详细说明
2012/12/13 Javascript
查找页面中所有类为test的结点的方法
2014/03/28 Javascript
JavaScript Math 对象常用方法总结
2016/04/28 Javascript
JS实现兼容各种浏览器的获取选择文本的方法【测试可用】
2016/06/21 Javascript
jQuery查找节点方法完整实例
2016/09/13 Javascript
浅谈使用splice函数对数组中的元素进行删除时的注意事项
2016/12/04 Javascript
微信小程序开发入门基础教程
2017/04/19 Javascript
JS触摸事件、手势事件详解
2017/05/04 Javascript
jQuery常见面试题之DOM操作详析
2017/07/05 jQuery
Scala解析Json字符串的实例详解
2017/10/11 Javascript
Vue递归实现树形菜单方法实例
2018/11/06 Javascript
详解Element 指令clickoutside源码分析
2019/02/15 Javascript
在element-ui的select下拉框加上滚动加载
2019/04/18 Javascript
layui加载数据显示loading加载完成loading消失的实例代码
2019/09/23 Javascript
你准备好迎接vue3.0了吗
2020/04/28 Javascript
在Uni中使用Vue的EventBus总线机制操作
2020/07/31 Javascript
element-ui tree结构实现增删改自定义功能代码
2020/08/31 Javascript
[06:40]2014DOTA2西雅图国际邀请赛 DK战队巡礼
2014/07/07 DOTA
python数据结构之二叉树的建立实例
2014/04/29 Python
Python flask框架post接口调用示例
2019/07/03 Python
Python使用itcaht库实现微信自动收发消息功能
2020/07/13 Python
python线程优先级队列知识点总结
2021/02/28 Python
如果NULL定义成#define NULL((char *)0)难道不就可以向函数传入不加转换的NULL了吗
2012/02/15 面试题
中职应届生会计求职信
2013/10/23 职场文书
如何写一份好的英文求职信
2014/03/19 职场文书
毕业生自荐信如何写
2014/03/24 职场文书
市场营销专业毕业生求职信
2014/03/26 职场文书
美容院店长岗位职责
2014/04/08 职场文书
建筑学专业自荐书
2014/07/09 职场文书
就业协议书样本
2014/08/20 职场文书
师德师风个人自我剖析材料
2014/09/27 职场文书
2015年计划生育责任书
2015/05/08 职场文书