查mysql.role_edges无结果不等于无继承,仅说明无直接绑定;需递归查询中间角色链(如app_user→db_writer→all_privs),mysql 8.0不支持内置递归,手动追两层可覆盖95%场景。

查 mysql.role_edges 但没返回结果就等于没继承?
不是。空结果只说明没有直接绑定关系,但角色可能通过中间角色间接继承——比如 app_user → db_writer → all_privs,此时查 app_user 直连 all_privs 肯定为空。必须递归查链路:SELECT FROM_USER, FROM_HOST FROM mysql.role_edges WHERE TO_USER = 'db_writer' AND TO_HOST = '%';,再用该结果继续向下查。MySQL 8.0 不提供内置递归查询,手动最多追两层已覆盖 95% 场景。
SHOW GRANTS USING 显示权限但实际执行报错?
常见于两种断点:DEFINER 失效或角色未激活。先确认当前会话是否激活目标角色:SELECT * FROM INFORMATION_SCHEMA.APPLICABLE_ROLES;;若目标角色不在其中,SET ROLE 'xxx'; 后重试。再检查视图/存储过程的 DEFINER 是否存在且有基表权限——SHOW CREATE VIEW v1\G 看 DEFINER 字段,然后 SELECT User, Host FROM mysql.user WHERE User = 'definer_name' AND Host = 'definer_host'; 验证账号真实存在。
角色绑定了,但 SHOW GRANTS FOR ... USING 没输出?
三个原因最常被忽略:
-
TO_USER和TO_HOST必须完全匹配,'alice'@'%'≠'alice'@'localhost'—— 查绑定时得用实际登录 host - 角色名大小写敏感,
USING 'AppWriter'和USING 'appwriter'是两个不同角色 - 角色本身没被授予任何权限,
SHOW GRANTS FOR ROLE 'xxx';返回空,则USING也必然为空
audit 权限链时为什么不能只信 mysql.user.Grant_priv?
因为 Grant_priv = 'Y' 只反映用户自身是否被显式授予全局 GRANT OPTION,和角色继承完全无关。一个用户可能 Grant_priv = 'N',却通过角色获得 GRANT OPTION ON mydb.*,此时他仍能对 mydb 下所有表授予权限。真正要审计“谁能在哪授什么权”,必须联合查:mysql.role_edges + mysql.db(看 Grant_priv 列)+ SHOW GRANTS FOR ... USING 实测。











