PHP连接OceanBase使用MySQL协议,无需专用驱动,直接用mysqli或PDO_MYSQL即可;需确认租户为mysql模式、地址端口(2883)正确、用户名格式为user@tenant#cluster、密码匹配、禁用PDO预处理模拟,并注意SQL语法兼容性。

PHP 连 OceanBase 用的是 MySQL 协议,不是专用驱动
OceanBase 兼容 MySQL 协议(v5.7 / 8.0),所以 PHP 不需要额外装 OceanBase 官方驱动,直接用 mysqli 或 PDO_MYSQL 就行——前提是 OceanBase 实例已开启 MySQL 兼容模式(默认开启),且网络、账号权限都通。
常见错误现象:Connection refused、Access denied for user、Unknown database,基本都卡在这几处,不是驱动问题。
- 确认 OceanBase 租户类型是
mysql(非oracle),可通过SHOW VARIABLES LIKE 'ob_compatibility_mode'查看返回是否为mysql - 连接地址填的是 OBProxy 地址或直连 OBServer 地址(推荐用 OBProxy,支持负载和读写分离)
- 用户名格式必须是
user_name@tenant_name#cluster_name,例如admin@sys#obdemo;单机版可能简化为admin@sys - 密码要跟创建租户用户时设置的一致,注意大小写和特殊字符(如
@、/需 URL 编码,但 mysqli_connect 不自动解码,建议避免)
mysqli_connect() 连接 OceanBase 的关键参数写法
用 mysqli_connect() 最简单,但容易因用户名格式或端口错导致静默失败。OceanBase 默认端口是 2883(不是 MySQL 的 3306),这点必须显式指定。
$host = '192.168.1.100'; $port = 2883; $user = 'root@sys#obdemo'; // 注意 @ 和 # 符号 $password = 'your_password'; $dbname = 'test';$conn = mysqli_connect($host, $user, $password, $dbname, $port); if (!$conn) { die('Connect Error: ' . mysqli_connect_error()); }
- 不传
$dbname参数也能连上,但后续执行USE db_name会报Unknown database—— 因为 OceanBase 要求库名必须事先存在且用户有权限 - 如果连的是系统租户(如
sys),不能直接选业务库,得先CREATE DATABASE再授权 -
mysqli_options($conn, MYSQLI_OPT_CONNECT_TIMEOUT, 10)建议加上,OBProxy 在高负载下响应可能延迟
PDO 连 OceanBase 要禁用预处理模拟
用 PDO_MYSQL 时,如果开启 PDO::ATTR_EMULATE_PREPARES(默认 true),部分复杂 SQL(如带变量的 SELECT @@session.sql_mode)会解析失败,报 SQLSTATE[HY000]: General error: 1096 No tables used 类似错误。
立即学习“PHP免费学习笔记(深入)”;
- 必须显式关闭模拟预处理:
$pdo->setAttribute(PDO::ATTR_EMULATE_PREPARES, false) - DNS 中不要加
charset=utf8mb4参数(OceanBase 当前对 charset 参数解析不稳定),改用连接后执行SET NAMES utf8mb4 - 连接 DSN 示例:
mysql:host=192.168.1.100;port=2883;dbname=test,user和pass单独传入new PDO(...)第二、三参数
连上后执行 SQL 的几个兼容性注意点
OceanBase 对 SQL 语法做了严格校验,有些在 MySQL 能跑的语句在这里会直接报错,不是连接问题,而是语义不通过。
-
INSERT ... ON DUPLICATE KEY UPDATE支持,但要求唯一键或主键明确,不能依赖隐式索引 -
GROUP BY必须包含 SELECT 中所有非聚合字段(SQL92 模式),否则报ERROR 1055 - 不支持
SELECT * FROM (SELECT ...) t这种无别名子查询,需补别名:SELECT * FROM (SELECT ...) AS t -
SHOW CREATE TABLE返回的建表语句里含TABLEGROUP等 OB 特有字段,PHP 解析时注意跳过或正则过滤
真正卡住的往往不是“怎么连”,而是连上之后第一条 INSERT 或 JOIN 就报错——这时候该查 SQL 兼容性文档,而不是换驱动。











