mysqli_connect()失败返回false但无报错,需立即检查返回值并调用mysqli_connect_error()获取真实原因;常见原因包括未开启错误提示、错误被@抑制、MySQLi扩展未启用、连接被拒绝或权限不足。

mysqli_connect() 返回 false 但没报错?检查 mysqli_connect_error()
PHP 连数据库失败却看不到具体错误,大概率是没开启错误提示或没捕获返回值。mysqli_connect() 失败时返回 false,但不会自动抛异常,必须手动调用 mysqli_connect_error() 才能拿到真实原因。
常见遗漏点:
- 没在连接后立刻检查返回值,直接对
false调用mysqli_query(),导致后续报“expects mysqli object”类错误 - 错误信息被
@抑制,或display_errors = Off+log_errors = Off导致完全静默 - MySQLi 扩展未启用(
php -m | grep mysqli确认)
建议写法:
$conn = mysqli_connect($host, $user, $pass, $db, $port);
if (!$conn) {
die('连接失败:' . mysqli_connect_error());
}
连接被拒绝(Connection refused)?重点查端口、服务状态和防火墙
Connection refused 表示 PHP 尝试 TCP 握手失败,不是账号密码错,而是根本连不到 MySQL 进程。
立即学习“PHP免费学习笔记(深入)”;
按顺序排查:
- 确认 MySQL 服务正在运行:
systemctl status mysql(Linux)或任务管理器里看mysqld.exe(Windows) - 确认监听地址和端口:默认是
127.0.0.1:3306,但配置文件中bind-address设为127.0.0.1时无法从容器或远程连接;Docker 场景常用host.docker.internal或宿主机 IP - 检查防火墙/SELinux:Linux 上
firewall-cmd --list-ports看 3306 是否放行;云服务器还要查安全组规则 - 本地测试用
telnet 127.0.0.1 3306或nc -zv 127.0.0.1 3306验证端口可达性
Access denied for user 错误?权限、主机名、认证插件三者都要核对
Access denied for user 'xxx'@'yyy' 是最典型的权限类错误,但 yyy 不一定是你想象的来源地址。
关键点:
- MySQL 用户是
'user'@'host'组合,'root'@'localhost'和'root'@'%'是两个不同用户,后者才允许远程连接 - PHP 连接时的
$host值决定匹配哪个@host:填127.0.0.1匹配@'127.0.0.1',填localhost在 Unix 套接字下可能走 socket 而非 TCP,行为不一致 - MySQL 8.0+ 默认用
caching_sha2_password插件,老版本 PHP(ALTER USER 'xxx'@'%' IDENTIFIED WITH mysql_native_password BY 'pwd';
pdo_mysql 扩展已启用但 new PDO() 报 Class not found?检查 PHP SAPI 模块差异
CLI 和 Web(如 Apache mod_php / FPM)可能加载不同的 php.ini,导致一个环境能连、另一个不能。
验证步骤:
- Web 环境下访问
页面,搜pdo_mysql,确认已启用且版本匹配 - CLI 下运行
php -m | grep pdo和php --ini,对比配置路径是否与 Web 环境一致 - 某些 Docker 镜像(如
php:alpine)需手动安装扩展:docker-php-ext-install pdo_mysql,仅apk add php-pdo不够 - FPM 场景下修改了
php.ini必须重启php-fpm进程,reload 不一定生效
连接字符串中主机名、端口、字符集(?charset=utf8mb4)漏写或写错,也会静默失败或报语法错误,这类细节最容易在迁移环境时被忽略。











