thinkphp5与thinkphp3的不同点

1、默认的报错级别,全部为fatal级别,包括变量未定义之类的,可以在common.php里定义error_reporting,入口文件定义无效
2、伪静态路由,直接在route.php里配置一个数组就可以了,但是有个坑,类似这样的路由index.php/module/controller/action/param/value,转换成伪静态后,比如
‘news/:id’ => ‘index/news/article’,
接收参数id是没法通过get或者request之类来接收的需要在action里这样写
public function article(Request $req){
$id = $req->param(“id”);

3、模板,所有模板标签全部改成花括号,比如原先3.x这样写<volist …>,5.x必须这样{volist …}
4、模型,必须要给每个表定义model,然后才能使用model(“table”)来操作模型
5、取消单字母函数,因此不能用M()函数来操作模型,正确方法见上一条
6、join,链式sql的join方法,参数改了,第一参数是被连接表及别名,第二参数是连接条件,add方法取消了,改用insert方法
7、模板渲染,需要用return ,比如return $this->fetch(‘duan’);
8、控制器文件名和类名都不用再加controller

thinkphp的一些优化

1、生成运行时文件,这个runtime.php将合并所有用到的php文件到一个文件中,减少include的开销,直接在index.php里设置

define(‘NO_CACHE_RUNTIME’,false);

2、关闭调试模式,config.php

‘APP_DEBUG’=> false

3、开启模板缓存,config.php

‘TMPL_CACHE_ON’   => true

4、关闭日志功能,config.php

‘LOG_RECORD’=>false

5、开启动态页面浏览器端缓存,在index.php最前面加上

session_cache_limiter(‘public’);

注:数据变化快的动态页慎用,要强刷才会去服务器请求更新

6、去掉X-Powered-By:ThinkPHPxxx

header会输出这么一条信息,是thinkphp自己输出的,很是讨厌,就怕谁不知道用的是think?

ThinkPHP/Lib/Think/Core/View.class.php

找到header(“X-Powered-By:ThinkPHP”),注释掉

 

 

 

 

thinkphp的URL_MODEL参数

URL_MODEL,显然是url地址模式,建议设置值为2。
据说默认值就是2,不过我用的这个不知道什么版本,确认默认值不是2,结果url就是类似这样的:localhost/index.php/xxx/yyy/zzz,多了index.php,非常难看,查了一下才知道,原来是URL_MODEL设置问题,在项目配置文件里,显式申明一下这个配置项,置为2,index.php就不见了。

文件或者图片写入到mysql再读出来

标题有点罗嗦,图片为什么要存库里呢?简单说有人就是喜欢这样,没其他原因。。。

直接上代码吧,存库比较简单,还是要先上传文件,只不过不是将临时文件move到目录,还是要读出文件字节流,然后存库。

// pic上传file控件名
if($_FILES['pic']['name'] && $_FILES['pic']['error'] == UPLOAD_ERR_OK){
	// 判断上传文件大小类型安全等略
	$fp=fopen($_FILES["pic"]["tmp_name"] , "rb");
	$file_data = fread($fp, filesize($_FILES["pic"]["tmp_name"]));
	fclose($fp);
	// 将file_data存到表里,字段请用longblob,代码略
}

不过读出来遇到点问题,读出后发现文件最前面多了三个字节,直接到库里看,原始数据又是正常的,什么原因呢,因为读文件是用thinkphp写的,想了一下,有可能是think的问题,要么在比较前面有header输出?要么文件编码问题?反正导致读出的数据输出后多了三个字节,没办法,写了段原生的php脚本:

$DB_CONN = mysql_connect($host, $user, $password);
if($DB_CONN){
	mysql_select_db($dbname, $DB_CONN) ;
	mysql_query('SET NAMES utf8',$DB_CONN);
	$result = mysql_query("select filedata from file where id=1", $DB_CONN);
	$row = mysql_fetch_assoc($result);
	if($row){
		header("Content-Type:image/jpeg");
		echo $row['filedata'];
	}
}

有时候bug很难找,换种环境或者写法,轻松搞定

 

thinkphp模板里html标签属性解析

thinkphp模板类里提供htmltag,在lib\think\template\taglib\taglibhtml.class.php

提供了editor、select、grid、list、imagebtn、checkbox、radio等html标签的封装,可能用的最多的是select吧,有这个东西,生成下拉框就容易多了,不过属性真难记啊,找到_select,属性列表如下:

name:select控件名

id:select的id

options:绑定数据的二维数组,数组的key就是options的value,值就是option的显示的内容

selected:默认选项的值,不过写法非常奇葩,奇葩,selected=”aaa” selected=”aaa[bbb]”,标签变量请务必去掉$,数组下标务必用[]引用,千万不要用.引用

change:就是onchange,这个还是可以理解的

style:这个是class,简直无法理解,class为什么要用style,如果直接在select上写style属性,请问怎么写?

其他属性略,最奇葩就是selected和style

 

 

thinkphp有特殊字符或中文url翻页bug

thinkphp自带的page类,有个bug,当翻页地址里有特殊字符或者中文的时候,翻页后,会对这些字符进行两次urlencode转义,一次是在U函数里,具体说是在thinkphp的源码包里common\functions.php,function U,找urlencode,把他去掉。

光这样还不行,外部输入的数据不知道在哪里又被转义了一次,懒得去找了,直接在引用get参数的地方,使用urldecode反转义一次,解决问题。

thinkphp有关魔术字符转义的bug

服务器在开启magic_quotes_gpc的情况下,thinkphp不会去判断服务器的环境,还是会继续转义,于是含有单引号反杠等字符串插库后就被两次转义,每编辑一次就多一倍的转义。

本以为在db类里找到escapeString,加上判断就可以解决问题了,实际上并没有那么简单,就算把db类的转义函数escapeString改成不转义,还是会两次转义,不知道哪里还有转义代码,麻烦死了,后来查了一下,可以在入口文件那里做处理,把外部输入数据先去掉转义,反正thinkphp会转义一次,所以去掉转义也没问题,唯一的问题是所有sql都要使用thinkphp封装了,或者使用_get() _post()等方法引用外部输入数据。

入口处理代码如下: 继续阅读“thinkphp有关魔术字符转义的bug”