NetworkError常见原因包括MySQL未监听正确地址、host配置导致Unix socket或TCP连接错误、防火墙/SELinux/Docker网络拦截等,需逐层排查服务状态、监听端口、连接参数及网络策略。
PHP 连接 MySQL 提示 NetworkError 的常见原因
这通常不是 PHP 本身报错,而是 mysqli_connect() 或 PDO::__construct() 失败时抛出的底层网络异常,比如 Connection refused、Operation timed out 或 php_network_getaddresses: getaddrinfo failed。根本问题不在代码逻辑,而在连接链路某处断了。
检查 MySQL 服务是否真正运行并监听正确地址
很多情况下,MySQL 虽然“启动了”,但实际没监听外部请求,或只绑定了 127.0.0.1(IPv4)而 PHP 尝试用 ::1(IPv6)连,导致失败。
- 执行
sudo systemctl status mysql(Linux)确认服务 active - 查监听状态:
ss -tlnp | grep :3306或netstat -an | grep 3306,看是否出现*:3306或127.0.0.1:3306 - 若只显示
127.0.0.1:3306,而 PHP 中 host 写的是localhost,注意:PHP 的localhost会优先走 Unix socket(不是 TCP),若 socket 文件路径不对或权限不足,也会表现为 NetworkError - 临时改用
127.0.0.1替代localhost测试,可绕过 socket 查找逻辑
PHP 连接参数中 host 和 port 的实际影响
host 值决定连接方式:localhost → Unix socket;127.0.0.1 或 192.168.x.x → TCP/IP;port 在 host 是 IP 类型时才生效,socket 模式下 port 被忽略。
- 确认
my.cnf中bind-address是否为127.0.0.1或0.0.0.0(后者允许远程,但需配合防火墙和用户权限) - 如果 MySQL 运行在 Docker 容器里,宿主机 PHP 要连容器 MySQL,host 不能写
localhost,得写容器 IP 或host.docker.internal(macOS/Windows)或自定义网络网关(Linux) - 检查
mysqli.default_port或PDO::ATTR_PORT是否被意外覆盖;默认是 3306,但改过配置又没同步到连接参数就会连错端口
防火墙、SELinux 和 Docker 网络隔离的隐性拦截
即使 MySQL 监听 0.0.0.0:3306,Linux 防火墙(ufw/firewalld)、SELinux 策略、Docker user-defined network 的默认隔离都可能静默丢包。