原 DB 类的改进

Discuz! X2.5 新版对数据库 DB 层进行了功能和安全方面的加强:

  • addslashes 的处理

仅 insert(),update(),delete() 方法对传入其的数组形式的参数进行 intval 或 addslashes 安全处理,字符串形式的参数将不处理,请注意

  • 新添加的方法 fetch_all($sql),order(), limit(),field() 等方法

其中 fetch_all 方法以数组方式返回查询多条记录数据,且可以设置数据的 KEY 值使用某字段值;
order(),limit(),field() 返回 SQL 语句中相应的部分

  • SQL 语句 format 的支持
//例:查询 10 个用户 uid 大于 100 的用户数据,以 uid 为返回结果数组的 key
$arr = DB::fetch_all('SELECT * FROM %t WHERE uid>%d LIMIT %d', array('common_member', '100', '10'), 'uid');

支持的 fomat 有:

 %t DB::table()
 %d intval()
 %s addslashes()
 %n in IN (1,2,3)
 %f sprintf('%f', $var)
 %i 直接使用不进行处理
  • 返回值的处理

在非 UNBUFFERED 的情况下:INSERT SQL 语句返回 insert_id();UPDATE 和 DELETE SQL 语句返回 affected_rows()

新增数据层:数据层的规范和约定

  • 一个数据表一个 class 文件,以 table_加上不带前缀的表名命名,尽量不操作其它表;
  • 不能使用 $_G 、 $POST 、 $GET 等全局变量;
  • 关联查询 (JOIN) 尽量拆分为单条查询,不能拆分的放入主表的类中;
  • 方法名以下划线分隔,全部为小写,全部为单数,直接返回结果,保留关键字:on 、 get 、 set, 方法参数不能以数组的形式传入,数据可以;
  • 除数据表文件以外,其它文件禁止出现 SQL 语句;
  • 查询结果返回一行记录方法名使用 fetch 开头,返回多行记录方法名使用 fetch_all 开头,查询中使用 SQL 语句 count 函数返回一个数值的使用 count 开头;
  • 方法名中 by 后面的是以下划线 (_) 分隔的表字段名,不要使用复数型,例如: fetch_all_by_uid() 而不是 fetch_all_by_uids();
  • 方法名需去掉表名,如:common_member 表类方法 fetch_member_by_username 应命名为 fetch_by_username;
  • 数据表类继承 discuz_table 基类,基类实现 CURD 操作,fetch 方法实现了根据一个主键 值得到一行记录、 fetch_all 方法实现了根据一组主键值得到多行记录 (二维数据,主 键值为 key) 、 count 方法返回了表的总记录数据;
  • 如果表是无主键或是关联主键,则基类中的 CURD 将不能使用,需自己在相应的表类中实现, 同时将 $this->_pk 设置为空;
  • DB 层封装的函数实现了 addslashes,个别直接写 sql 语句的需主意 addslashes;
  • 使用 C::t('tablename')->method(); 调用;
  • C::t 插件调用方式
  • 表名:mytablename
    目录:source/plugin/mypluginid/table/table_mytablename.php
    类名:table_mytablename
    用法:C::t('#mypluginid#mytablename')->method();