如何排查MySQL用户远程登录被拒绝的问题

作者:袖梨 2026-08-12

远程登录被拒绝主因是'user'@'host'不匹配、bind-address未监听外部地址或防火墙未放行3306端口;需依次查mysql.user表、修改bind-address为0.0.0.0、开放防火墙及云安全组规则,并执行FLUSH PRIVILEGES。

远程登录被拒绝,90%不是密码错,而是 MySQL 根本没“认出”你这个连接来源——得从 user@host 匹配、监听地址、防火墙三层依次卡点排查。

检查 mysql.user 表中用户 host 是否匹配客户端 IP

报错 Host '192.168.1.50' is not allowed to connect 就是这一层失败的典型信号。MySQL 不看你是谁,只严格比对 userhost 字段组合。

  1. SELECT user, host FROM mysql.user WHERE user = 'root'; —— 如果只有 'root'@'localhost',那远程必然拒绝
  2. 不要直接 UPDATE mysql.user SET host = '%':MySQL 8.0+ 会报 ERROR 1396,且跳过密码加密逻辑
  3. 正确做法是新建或重命名:CREATE USER 'root'@'%' IDENTIFIED BY 'StrongPass2026!';ALTER USER 'root'@'localhost' RENAME TO 'root'@'%';
  4. 授权后必须执行 FLUSH PRIVILEGES;,否则内存缓存不更新,改了也白改

确认 mysqld 是否监听外部地址(bind-address)

即使用户权限全开,如果 mysqld 只绑定了 127.0.0.1,所有远程 TCP 包在系统层就被丢弃,连错误日志都不会记。

  1. 查配置文件(常见路径:/etc/mysql/mysql.conf.d/mysqld.cnf/etc/my.cnf),找 [mysqld] 下的 bind-address
  2. 若值为 127.0.0.1,改为 0.0.0.0(IPv4 全开)或注释掉该行(MySQL 会默认监听所有接口)
  3. 重启服务:sudo systemctl restart mysql(Debian/Ubuntu)或 sudo systemctl restart mysqld(RHEL/CentOS)
  4. 验证监听状态:sudo ss -tlnp | grep :3306,输出中必须含 *:33060.0.0.0:3306,不能只有 127.0.0.1:3306

验证防火墙与云平台安全组是否放行 3306/tcp

端口不通时,telnet your-server-ip 3306 会直接超时或报 Connection refused;前者是防火墙拦截,后者才是 MySQL 层问题。

  1. 本地防火墙:sudo ufw status(Ubuntu)或 sudo firewall-cmd --list-ports(CentOS),确保含 3306/tcp
  2. 添加规则:sudo ufw allow 3306sudo firewall-cmd --add-port=3306/tcp --permanent && sudo firewall-cmd --reload
  3. 云服务器(阿里云/腾讯云/AWS):必须进控制台检查「安全组」规则,手动添加入方向 TCP 3306,源 IP 建议填具体客户端 IP,而非 0.0.0.0/0
  4. 注意:某些云厂商的安全组优先级高于系统防火墙,即使 ufw 关了,安全组没开照样连不上

绕过 SSL 强制和认证插件兼容性问题

MySQL 8.0 默认启用 caching_sha2_password 插件,老客户端(如旧版 Navicat、某些 Python MySQL 驱动)可能握手失败,表现就是“连接被拒绝”,但日志里没有明确提示。

  1. 临时兼容:创建用户时指定插件:CREATE USER 'app'@'%' IDENTIFIED WITH mysql_native_password BY 'Pass123!';
  2. 或修改已有用户:ALTER USER 'app'@'%' IDENTIFIED WITH mysql_native_password BY 'Pass123!';
  3. 检查是否强制 SSL:SHOW VARIABLES LIKE 'require_secure_transport';,若为 ON,需在用户授权时加 REQUIRE NONE 或配好证书
  4. 生产环境别关 SSL,但测试阶段可先用 mysql -h your-ip -u user -p --default-auth=mysql_native_password 快速验证是不是插件问题

最易被忽略的是:改完 my.cnf 忘记重启服务,或执行了 GRANT 却漏掉 FLUSH PRIVILEGES;;还有人把安全组规则加在错误的实例上——这些点不卡死,前面所有操作都白费。

相关文章

精彩推荐