「本機能用 127.0.0.1 連線,卻用不了 localhost」或反過來,是 MySQL 連線最經典的坑。根因在於 MySQL 將 localhost 視為 Unix Socket 連線,127.0.0.1 視為 TCP/IP 連線,兩者權限、配置、檔案路徑完全獨立。本文系統診斷並給出雙向修復方案。
| 連線方式 | 主機標識 | 傳輸協議 | 權限表匹配 | 關鍵配置 |
|---|---|---|---|---|
| Unix Socket | localhost | 本地檔案描述符 | User@'localhost' | socket=/path/to/mysql.sock |
| TCP/IP | 127.0.0.1 | TCP 回環介面 | User@'127.0.0.1' | port=3306, bind-address |
Warning: mysql_connect(): Can't connect to local MySQL server through socket '/var/run/mysqld/mysqld.sock' (2)
systemctl status mysql 或 ps aux | grep mysqldmysqld --verbose --help 2>/dev/null | grep '^socket'
# 輸出範例:socket /var/run/mysqld/mysqld.sock
php.ini:
mysql.default_socket = /var/run/mysqld/mysqld.sock
mysqli.default_socket = /var/run/mysqld/mysqld.sock
pdo_mysql.default_socket = /var/run/mysqld/mysqld.sock
systemctl restart php7.4-fpm--with-mysql-sock=/tmp/mysql.sock,但 PHP 預設讀 /var/lib/mysql/mysql.sock)。my.cnf 的 [client] 區段未指定 socket,導致 mysql 命令列工具與 PHP 使用不同 Socket。ls -l /var/run/mysqld/mysqld.sock 確保 mysql 用戶可讀寫,PHP 運行用戶(如 www-data)有目錄執行權限。Warning: mysql_connect(): Can't connect to MySQL server on '127.0.0.1' (111 "Connection refused")
netstat -ntlp | grep 3306 或 ss -ntlp | grep 3306。若無輸出,檢查 my.cnf:
[mysqld]
# 註釋或刪除
# skip-networking
bind-address = 0.0.0.0 # 或具體 IP,127.0.0.1 僅允許本機
修改後 必須重啟 MySQL。
SELECT User, Host FROM mysql.user WHERE User='root';
-- 若無 'root'@'127.0.0.1',需建立:
CREATE USER 'root'@'127.0.0.1' IDENTIFIED BY 'password';
GRANT ALL PRIVILEGES ON *.* TO 'root'@'127.0.0.1' WITH GRANT OPTION;
FLUSH PRIVILEGES;
# CentOS/RHEL 7+
firewall-cmd --permanent --add-port=3306/tcp
firewall-cmd --reload
# SELinux 典型錯誤日誌 /var/log/audit/audit.log
# 臨時關閉驗證:setenforce 0
# 永久:/etc/selinux/config 設 SELINUX=disabled 並重啟
# 或精準放行:setsebool -P mysql_connect_any 1
127.0.0.1 localhost 存在且無衝突條目。# 追蹤 PHP 進程連線嘗試
strace -f -e trace=connect,open,stat php your_script.php 2>&1 | grep -E 'connect|mysql.sock'
# 追蹤 MySQL 進程接受連線
strace -p $(pidof mysqld) -e trace=accept,read,write 2>&1
可精準定位是 Socket 路徑錯誤、權限拒絕、還是 TCP 連線被拒。
my.cnf [client] 區段明確指定 socket 路徑,命令列工具、PHP、Python 等客戶端均會讀取此配置。127.0.0.1 或 Service IP),Socket 僅用於 Sidecar 同 Pod 通訊。核心口訣: localhost 走 Socket,127.0.0.1 走 TCP;權限分開配,路徑要對齊;防火牆 SELinux 別忘記。