1. 云栖社区>
  2. PHP教程>
  3. 正文

PHP利用反射升级数据库结构

作者:用户 来源:互联网 时间:2017-12-01 12:06:24

数据库php升级结构反射利用

PHP利用反射升级数据库结构 - 摘要: 本文讲的是PHP利用反射升级数据库结构, 用自己开发的php框架,是一个短期内可能很爽,长期来看,当开发人数和代码规模上升的时候,很痛苦的选择。使用文档、单元测试、代码生成工具、性能优化、Log和Debug等基础设施的建设将极大的消耗你的精力,让你无法专心于真正的业务上。 公司开

用自己开发的php框架,是一个短期内可能很爽,长期来看,当开发人数和代码规模上升的时候,很痛苦的选择。使用文档、单元测试、代码生成工具、性能优化、Log和Debug等基础设施的建设将极大的消耗你的精力,让你无法专心于真正的业务上。


公司开发的系统是一套SaaS的建站系统,架构上是所有客户使用同一套代码,但是每个站点有自己独立的数据库。而我们的系统开发时一个迭代的过程,开发新功能难免会对数据库做一些修改,比如:加一张新表,加一个新字段。对于我们这样的系统需要将所有客户的数据库都做数据库的改动。


第一阶段:我们使用最原始的方法,代码上线前,手动让运维将所有客户的表进行更新,然后上传代码。但是我们知道这个方法不是长久之计,于是很快我们就进入了第二阶段。


第二阶段:sql文件+version,每次需要变动表结构,新建一个sql文件,文件名为site1.sql、site2.sql... 以此类推,我们会在每个站点自己的表里保存一个version字段,初始值为1,每次客户访问时自动运行最新的sql文件,并更新version值,保证不会重复执行相同的sql文件。这个方法很有效,后来我们的业务上来了,开发的新功能越来越多,sql文件疯狂上涨,突然我们发现每天总有些站点表里version增加,但是表里没有新增的表或字段,导致访问报错,影响很大。有一个同事为了保证不会再报错,在用到这张表的php语句前都加上创建语句。于是其他同事纷纷效仿,我们进入第三阶段。


第三阶段:直接在使用php中加入修改sql,一开始是配合第二阶段一起用的,渐渐的,第二阶段的sql文件方式被抛弃了。这个方式的弊端也出现了:


1. 性能上,修改表结构的sql,被重复执行,只有第一次是有效的。


2. 开发上,当修改的表在多个地方使用,每个地方都需要加修改表结构的sql,很容易遗漏,导致程序出错。


于是为了解决以上两个问题,于是我负责开发了第四代的升级数据库结构的方式,在方便使用的同时解决第三阶段的弊端。


在这个方案中,第一步:我们创建一个Tbfix类,修改表结构的sql以表为单位拆分,分别写在这个类的不同的函数中,函数名为fix_加上表名,比如:有张表ss_image_resources的升级创建写在函数fix_image_resources函数中,并且统一提供对外接口Tbfix::fix($tablename),这个代码根据表名利用PHP反射机制自动执行对应函数。


代码地址如下:


http://git.oschina.net/jamesren_781/5azrsv4ow98gijxeqhmfu.code.git


第二步:利用mysql_query执行错误sql语句会return false的原理,我们在数据库访问封装类Mysql中,在增、删、改、查函数中加入判断,当mysql_query函数return false,利用Tbfix::fix($tablename)升级对应的表结构,然后重新执行函数。


以查询数据库函数为例,调用代码如下:


public function findAll($table_name,$params = array(),$where = '',$orderby='')
{// 通过参数拼接sql语句,省略。。。
$res = mysql_query($_sql,$this->conn);
if($res === false)
{
$ret=Tbfix::fix($table_name); //查询语句报错,尝试修复对应的表
if(!$ret){
$this->halt('Select is failed.',$_sql);
return false;
}else{
return $this->findAll($table_name,$params ,$where,$orderby);//修复成功,重新执行函数
}
}while($row = mysql_fetch_array($res, RSTYPE_MYSQL))
{
$return[] = $row;
}
//释放数据库结果集
mysql_free_result($res);
return $return;
}

通过这种方式保证了升级逻辑执行的自动化和执行效率相对最优化,既方便了开发者,也提高了性能。


这个方案已经在实践之中,未来会继续根据实践结果去做修改,所有的方案都不是万能的,我觉得重要的是不断改进优化从而找到当前最合适自己的方案。路漫漫其修远兮,吾将上下而求索。



以上是云栖社区小编为您精心准备的的内容,在云栖社区的博客、问答、公众号、人物、课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索数据库 , php , 升级 , 结构 , 反射 利用 ,以便于您获取更多的相关知识。