tidb连接php需显式指定port=4000、charset=utf8mb4,并禁用localhost(避免socket)、手动控制事务、启用异常模式;tidb cloud还需tls及用户名前缀。

PDO 和 mysqli 就够了,TiDB 不需要专用驱动,也不支持 socket 连接 —— 用错协议或端口,90% 的连接失败就发生在这里。
PHP8.2 连 TiDB 必须显式写 port=4000
TiDB Server 默认监听 4000 端口,不是 MySQL 的 3306。哪怕你只连本地,也得写清楚:host=127.0.0.1;port=4000。用 localhost 会触发 Unix socket,而 TiDB 根本不提供 socket 文件,直接报 Connection refused。
-
mysqli_connect('127.0.0.1', 'root', '', 'test', 4000)—— 正确(端口单独传) -
mysqli_connect('localhost', ...)—— 错误(走 socket,TiDB 不响应) -
$dsn = 'mysql:host=localhost;port=4000;...'—— 错误(localhost优先走 socket,port 被忽略) - PHP8.2 已默认启用
mysqli和PDO_MYSQL,无需额外安装扩展,但需确认php -m | grep -E 'mysqli|pdo_mysql'有输出
charset=utf8mb4 是硬性要求,不是可选项
TiDB 对 MySQL 的 utf8(即 utf8mb3)支持不完整,漏掉 charset=utf8mb4 会导致中文插入失败,报错 ERROR 1366 (HY000): Incorrect string value。
-
$dsn = 'mysql:host=127.0.0.1;port=4000;dbname=test;charset=utf8mb4'—— 必须带 - 不要用
SET NAMES utf8mb4替代 DSN 参数 ——PDO::MYSQL_ATTR_INIT_COMMAND在 TiDB 中可能被忽略或引发兼容问题 - 如果用 ThinkPHP,配置里
'charset' => 'utf8mb4'也要显式写,不能留空或沿用旧项目的utf8
事务控制必须手动,autocommit=true 是默认陷阱
PHP 默认开启 autocommit,你在事务里执行 UPDATE 后没 commit(),TiDB 就真不提交 —— 不像 MySQL 那样可能“看起来生效”,TiDB 的快照隔离会让后续查询读不到未提交变更,容易误判为“SQL 没跑”。
- 务必用
$pdo->beginTransaction()开启,$pdo->commit()或$pdo->rollback()显式结束 - 别依赖析构函数自动 commit:PHP 请求结束时不会帮你 commit,只会 rollback
- TiDB 不支持长事务(> 10 分钟)和事务内 DDL(如
ALTER TABLE),ThinkPHP 的Db::transaction()若含 schema 操作,大概率报ERROR 8028 - PHP8.2 的
PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION必须开,否则事务失败会被静默吞掉,debug 成本翻倍
TiDB Cloud Serverless 还得多配 TLS 和用户名前缀
本地 TiDB 可以裸连,但 TiDB Cloud Serverless 强制 TLS,且用户名带点号前缀(如 abc123def456.root),这两点 PHP 默认都不处理。
-
dsn字段必须加sslmode=VERIFY_IDENTITY&sslca=/etc/ssl/cert.pem(Linux/macOS)或对应 Windows 证书路径 - 用户名不能被 ThinkPHP 的
parse_params解析截断 —— 关闭它,或确保配置中无该键 - 连接超时建议设为
15:Serverless 实例冷启动延迟可达 3 秒,time_out=3会频繁超时 - 禁用自动重连:
'break_reconnect' => true,避免在冷启动期间反复无效尝试
127.0.0.1 写成 localhost、charset 漏写、事务忘了 commit 这三处。TiDB 行为比 MySQL 更严格,容错更低 —— 它不给你“差不多能用”的错觉。php免费学习视频:立即使用
踏上前端学习之旅,开启通往精通之路!从前端基础到项目实战,循序渐进,一步一个脚印,迈向巅峰!











