ThinkPHP踩坑记录之数据库篇

虽然这么多年来ThinkPHP框架已经更新到大版本8了,越来越接近Laravel框架了,但是ThinkPHP 8框架还是有很多坑,我在工作中遇到不少,在此记录一下,以警醒后来人。

第1个坑,使用Db门面的inserA()批量插入数据到Oracle报错

因为ThinkPHP生成的批量插入SQL语句不符合Oracle语法。

避开这个坑的一个方法是,使用循环语句一条条地插入数据到Oracle,不要使用inserA()批量插入数据。

第2个坑,使用Think ORM操作Oracle 11g报错:SQLSTATE[HY000]: General error: 972 OCIStmtExecute: ORA-00972: identifier is too long

Oracle 11g的标识符的名字的长度不能超过30字节,标识符包括表名、视图名、序列名或触发器名。Oracle后续版本把标识符的名字的长度上限提高到了128字节。

ThinkPHP ORM 在处理 Oracle 时,有一个内部规范化逻辑(在 think-orm/src/db/connector/Oracle.phpBuilder 类中),会把表名/字段名转为小写+ 下划线风格(snake_case),以兼容 Oracle 的大小写不敏感特性。但当表名本身就包含大写或下划线时,这种转换会产生超长的蛇形名称,例如,把VIEW_JW_SPECIALTYDIRECTION转换为v_i_e_w__j_w__s_p_e_c_i_a_l_t_y_d_i_r_e_c_t_i_o_n,从而触发 Oracle 的长度限制。

ThinkPHP’s Facade vs. Laravel’s Facade

ThinkPHP’s facade implementation borrows from Laravel’s real-time facades feature: it lets you call non-static methods on a class statically, without needing to instantiate it first.

But it’s not as seamless as Laravel’s version (where you just prefix the class with the Facades\ namespace during import, and it magically turns into a facade). In ThinkPHP, you have to roll your own facade class manually.

ThinkPHP框架的门面(Façade) vs Laravel框架的的门面

ThinkPHP框架的门面实现了Laravel框架的实时门面(Real-Time Facades)特性:可以让某个类无需实例化而直接进行静态方式调用它的非静态方法。

但是没有Laravel框架的实时门面那么方便(只需在use一个类时,加上Facades\命名空间前缀,这个类就自动变成了一个门面),ThinkPHP框架需要你自己写门面类。