根本原因是多服务器SSL配置未逐个适配,每个$cfg['Servers'][$i]必须独立设置ssl_mode、PDO::MYSQL_ATTR_SSL_CA等参数,混合部署时CA路径、验证模式须严格匹配目标服务器策略。
phpmyadmin 连多服务器时 ssl 握手失败,根本原因不是“证书有问题”,而是每个服务器的 ssl 配置独立、pdo 连接参数未按目标服务器逐个适配。同一套 $cfg['servers'][$i] 配置不能复用,尤其在混合部署(本地 mysql + 云 rds + 自签测试库)场景下,90% 的失败源于 ssl_mode 和 pdo::mysql_attr_ssl_ca 路径写错或缺失。
phpMyAdmin 多服务器配置里必须为每个 $cfg['Servers'][$i] 单独设 SSL 参数
phpMyAdmin 不会自动继承全局 SSL 设置,$cfg['Servers'][1] 和 $cfg['Servers'][2] 必须各自声明完整 SSL 选项,哪怕只差一个服务器——漏配就直接报 SQLSTATE[HY000] [2002] SSL connection error。
-
ssl_mode=VERIFY_IDENTITY仅适用于已配置 CA 且域名匹配的生产环境;对自签名或内网测试库,必须改用ssl_mode=REQUIRED,否则连接立即中断 -
PDO::MYSQL_ATTR_SSL_CA路径必须是绝对路径,且 PHP 进程用户(如www-data)有读取权限;Alpine 容器中默认无/etc/ssl/certs/ca-certificates.crt,得显式挂载并指定路径 - 云数据库(如阿里云 RDS)必须用控制台下载的专用 CA 文件(如
aliyun-rds-ca-cert.pem),不能复用 Let’s Encrypt 或本地生成的证书
本地 MySQL 与云 RDS 混连时,host 和 ssl_mode 必须严格对应监听方式
本地 MySQL 常监听 127.0.0.1:3306(TCP),而云 RDS 监听公网 IP 或内网 VIP,二者网络路径不同,SSL 配置不能互换。
- 若本地 MySQL 开了
skip-networking或只启用 Unix socket,host设为localhost就无法走 SSL(socket 不支持 TLS),必须切到127.0.0.1并确认 MySQL 已启用 TCP 监听 - 云 RDS 强制要求
ssl_mode=VERIFY_IDENTITY+PDO::MYSQL_ATTR_SSL_CA指向其专用 CA,只写ssl_mode=REQUIRED会被拒绝(服务端设了require_secure_transport=ON) - 容器环境(如 Docker Compose)中 MySQL 容器名(如
mysqldb)不能直接用于 SSL 连接——DNS 解析后仍是内网 IP,但 SNI 和证书 SAN 可能不匹配,建议用固定 IP +proxy_ssl_name显式指定
常见错误现象与快速验证命令
别猜,直接在服务器上用命令行验证目标服务器是否可 SSL 连通,再比对 phpMyAdmin 配置。
-
mysql -u root -p -h 127.0.0.1 --ssl-mode=VERIFY_IDENTITY --ssl-ca=/path/to/ca.pem:若失败,说明服务端证书链或 CA 路径不对;若成功,问题一定出在 phpMyAdmin 的 DSN 或 options 里 -
openssl s_client -connect rds-host:3306 -servername rds-host -CAfile aliyun-rds-ca-cert.pem:验证云 RDS 证书是否被系统信任,输出含Verify return code: 0 (ok)才算通过 - 检查 phpMyAdmin 日志(
/var/log/apache2/error.log或 Nginx 错误日志):出现unknown ca表明PDO::MYSQL_ATTR_SSL_CA路径无效;出现SSL connection timeout很可能是防火墙或安全组拦截了 3306 端口
最易被忽略的是:多个服务器共用同一份 CA 文件路径,但实际文件只存在于某一台机器上;或者把 ssl_mode=REQUIRED 当作万能开关,却没意识到服务端策略可能更严格。每个 $cfg['Servers'][$i] 都得当成全新连接来配,而不是复制粘贴改个 host 就完事。
立即学习“PHP免费学习笔记(深入)”;



















