ThinkPHP SQL注入防御需五步:一、禁用PDO模拟预处理;二、开启SQL绑定日志验证;三、入口层过滤GET/POST参数;四、禁用raw等危险方法;五、模型层强制字段白名单校验。

如果您在ThinkPHP项目中发现SQL注入风险,可能是由于未启用参数绑定机制、动态字段未校验或原生SQL未绑定参数所致。以下是配置SQL注入防御的具体步骤:
一、启用PDO预处理并禁用模拟预处理
确保数据库连接强制使用真实预处理,防止MySQL低版本或Docker环境中因PDO::ATTR_EMULATE_PREPARES = true导致绑定失效。
1、打开应用配置文件config/database.php或环境配置env文件。
2、在数据库连接配置的params项中显式设置PDO::ATTR_EMULATE_PREPARES => false。
立即学习“PHP免费学习笔记(深入)”;
3、确认deploy配置为0(单服务器部署),避免集群模式下连接复用引发的绑定跳过。
二、全局开启SQL日志与绑定验证
通过日志实时监控是否真正触发PDO参数绑定,而非仅显示占位符的伪绑定日志。
1、在config/app.php中将debug设为true。
2、启用sql_explain选项,设置'sql_explain' => true。
3、执行一次含用户输入的查询后,检查运行时日志目录下的sql.log,确认出现Binding: [value]记录而非仅SQL: ... WHERE id = ?。
三、配置入口层统一参数过滤
在应用入口文件public/index.php中增加对全局GET/POST参数的初步清洗,拦截典型注入特征。
1、在define('APP_PATH', ...)之后插入过滤代码段。
2、遍历$_GET和$_POST,对每个值调用stripslashes_deep()去除反斜杠转义。
3、使用正则匹配/(union|select|insert|update|delete|drop|create|alter|exec|execute|declare|xp_)/i,对命中关键词的请求直接exit('Access Denied')。
四、限制危险方法的使用权限
通过框架配置禁用高危接口,从源头杜绝raw()、exp()等绕过绑定的调用。
1、在config/app.php中添加'forbidden_methods' => ['raw', 'exp', 'whereRaw']配置项。
2、创建中间件app/middleware/MethodGuard.php,在handle()中检查请求中是否包含_method或method参数值匹配禁用列表。
3、若匹配,返回HTTP 403响应并记录Security Alert: Forbidden method attempted。
五、强制模型层白名单字段校验
防止通过force参数或动态字段名拼接导致的注入,要求所有可写字段必须显式声明。
1、在基类模型app/common/model/BaseModel.php中重写allowField()方法。
2、定义受信字段白名单数组,如$allowed = ['username', 'email', 'status', 'create_time']。
3、调用parent::allowField()前,对传入字段数组执行array_intersect(),丢弃不在白名单中的字段名。



















