为什么MySQL执行SET PASSWORD操作后权限没有立即生效

作者:袖梨 2026-06-20
MySQL 8.0+ 中 SET PASSWORD 已弃用且对 caching_sha2_password 无效,ALTER USER 才是标准方式;密码修改仅影响新连接,不刷新当前会话;FLUSH PRIVILEGES 不作用于认证字段;需确认 host 匹配、插件兼容性及是否启用 --skip-grant-tables。

SET PASSWORD 在 MySQL 8.0+ 中已被弃用

MySQL 8.0 起,SET PASSWORD 命令默认不再更新 authentication_string 字段,而是可能静默失败或仅作用于旧插件(如 mysql_native_password),尤其当用户使用 caching_sha2_password(8.0 默认)时,该语句完全不生效。官方文档明确标注其为“deprecated”,且在 8.4+ 版本中已移除。

ALTER USER 不刷新连接会话的认证状态

即使你成功执行了 ALTER USER 'user'@'host' IDENTIFIED BY 'pwd',当前已建立的连接仍维持原有认证上下文——密码变更只影响**后续新连接**。这不是 bug,是设计行为。

  • 已登录的客户端不会自动登出或重认证
  • FLUSH PRIVILEGES 对密码字段无效(它只刷新权限缓存,不触碰认证数据)
  • 若用 mysql -u user -p 重连仍失败,说明 host 匹配不对(比如你改的是 'user'@'localhost',但实际连的是 'user'@'127.0.0.1'

认证插件不匹配导致“看起来没改”

执行 SELECT user, host, plugin, authentication_string FROM mysql.user WHERE user = 'your_user'; 后,如果 plugincaching_sha2_password,但客户端(如老版本 MySQL Workbench、某些 Python 驱动)只支持 mysql_native_password,就会出现“密码正确却连不上”的假象。

  • 修复方式:显式指定插件 ALTER USER 'user'@'host' IDENTIFIED WITH mysql_native_password BY 'pwd';
  • 或升级客户端驱动,确保支持 caching_sha2_password
  • 不要依赖 PASSWORD() 函数——它在 8.0+ 已移除,用它生成的哈希值无法被新插件识别

配置文件或启动参数绕过认证

最隐蔽但也最常见:MySQL 启动时加了 --skip-grant-tables,或配置文件 my.cnf 里写了 [mysqld] skip-grant-tables。此时所有用户免密登录,任何密码修改都“生效但不可见”——因为压根没走认证流程。

  • 检查运行参数:ps aux | grep mysqld 看是否含 skip-grant-tables
  • 检查配置文件:grep -i "skip-grant" /etc/mysql/my.cnf /etc/mysql/mysql.conf.d/mysqld.cnf 2>/dev/null
  • 若存在,注释掉并重启服务:sudo systemctl restart mysql
真正卡住的地方往往不是 SQL 写错,而是你正在跟一个根本没启用认证的实例打交道。先确认它是不是真在验密码,再调密码。

相关文章

精彩推荐