mysql 8.0权限问题根源是认证未通过、字段未对齐、角色未激活;必须用mysqld --upgrade=force重建系统表结构,确认plugin和authentication_string非空,并显式授予动态权限与角色。

权限没“失效”,是认证没过、字段没对齐、角色没激活——三件事卡住一个,就进不去库。
mysql.user表字段还是5.7结构
升级后连SELECT User, Host, plugin FROM mysql.user;都报Unknown column 'plugin',说明系统表根本没升级。MySQL 8.0 已删掉Password字段,新增plugin和authentication_string,但旧数据目录直接复用,这些字段就不存在。
- 停服务后必须用 8.0 的
mysqld二进制执行--upgrade=FORCE,不是跑mysql_upgrade(它在 8.0.16+ 已彻底移除) -
mysqld --datadir=/var/lib/mysql --upgrade=FORCE --user=mysql启动一次,让内核自动重建mysql库表结构 - 别信
mysqldump --all-databases导入权限表——mysql库不能这么导,会丢数据字典和角色元数据
caching_sha2_password导致客户端连不上
SHOW GRANTS能查出权限,但一连接就报ERROR 2054 (HY000): The server requested authentication method unknown to the client,这是握手阶段失败,根本没到权限校验那步。
- 确认插件:
SELECT User, Host, plugin FROM mysql.user WHERE User = 'your_user';,若返回caching_sha2_password,而你用的是 PHP 7.4 的mysqli、旧版 Navicat 或 PythonMySQLdb,就必然失败 - 临时修复:
ALTER USER 'your_user'@'%' IDENTIFIED WITH mysql_native_password BY 'pwd'; FLUSH PRIVILEGES; - 注意:host 必须完全匹配——
'user'@'localhost'≠'user'@'127.0.0.1',应用连的是哪个,就得改哪个
动态权限和角色没显式授予
用户能登录、SHOW GRANTS也显示正常,但执行BACKUP DATABASE或CREATE ROLE就报Access denied,因为 MySQL 8.0 的BACKUP_ADMIN、ROLE_ADMIN等是动态权限,不体现在传统授权语句里。
- 查当前用户缺失的动态权限:
SELECT * FROM information_schema.role_edges WHERE TO_HOST = 'your_host'; - 显式授角色:
GRANT r1 TO 'u'@'%';之后还要SET DEFAULT ROLE r1 TO 'u'@'%'; - 授动态权限:
GRANT BACKUP_ADMIN ON *.* TO 'u'@'%';,不是GRANT SELECT那种老写法
最易被忽略的是:plugin字段为空、authentication_string为空、或者mysqld启动时没带--upgrade=FORCE——这三项任一出错,后续所有操作都是在错误基础上徒劳调试。











