根本原因是权限配置不严:PROCESS权限允许查看所有连接的SQL,performance_schema表若被授予SELECT权限则可绕过限制获取完整语句;必须双路阻断——收回PROCESS权限并撤销performance_schema相关SELECT权限。

普通用户为什么能查到别人正在执行的 SQL
根本原因不是“MySQL 默认开放”,而是权限配置没收严:PROCESS 权限一旦授予,用户就能通过 SHOW PROCESSLIST 或查 information_schema.PROCESSLIST 看到所有连接的 Info 字段(即当前 SQL);更危险的是,如果还开了 performance_schema 且用户有对应表的 SELECT 权限,就能直接读 performance_schema.events_statements_current 拿到完整语句——哪怕被截断的 SHOW PROCESSLIST 也比这安全。
-
SHOW PROCESSLIST返回的Info列默认最多显示 100 字符,但只要有PROCESS权限,就对所有线程可见 -
information_schema.PROCESSLIST是视图,权限控制和SHOW PROCESSLIST完全一致,查它等价于执行命令 -
performance_schema表(如events_statements_current)需单独授权,但一旦给了SELECT权限,就能绕过PROCESS限制,看到任意线程的完整SQL_TEXT
如何真正禁止——只留自己能看到的入口
不能只靠“不给 PROCESS 权限”,因为 performance_schema 是独立权限体系。必须双路阻断:
- 收回
PROCESS权限:REVOKE PROCESS ON *.* FROM 'app_user'@'%';—— 这让SHOW PROCESSLIST只返回自己的行,information_schema.PROCESSLIST同理 - 禁用
performance_schema相关访问:REVOKE SELECT ON performance_schema.events_statements_current FROM 'app_user'@'%';,同理处理threads、events_statements_history等关键表 - 确认
performance_schema本身已启用(SHOW VARIABLES LIKE 'performance_schema';必须为ON),否则上述REVOKE无意义;但别误以为关掉它就安全——关掉后用户虽查不到events_*表,却仍可通过PROCESS权限看SHOW FULL PROCESSLIST
查自己当前 SQL 的安全替代方案
业务排查常需要“看我这次执行了啥”,但又不能放权给所有人看全局。此时应引导用户用受限方式自查:
面向 CRM 系统的 MySQL 8 数据库模式设计。当用户需要为客户关系管理(CRM)系统设计、评审、优化或生成数据库模式时,应使用此项技能。
- 用
CONNECTION_ID()查本会话:SELECT THREAD_ID FROM performance_schema.threads WHERE PROCESSLIST_ID = CONNECTION_ID();再查events_statements_current—— 这条链路只要用户有自己线程的SELECT权限即可,无需PROCESS - 确保该查询只返回一行:若
PROCESSLIST_ID匹配不到,说明会话已断开或performance_schema.threads中记录被清理(它只存活跃线程) - 避免用
LIKE '%xxx%'在SQL_TEXT上模糊匹配——字段内容含绑定变量(如:b1)、换行、大小写混杂,极易误判或漏判
最容易被忽略的兼容性陷阱
MySQL 8.0+ 引入角色(role)后,很多 DBA 会把 SELECT_CATALOG_ROLE 或自定义角色批量授给开发账号,却忘了这个角色默认包含 SELECT on information_schema.PROCESSLIST —— 也就是变相恢复了 PROCESS 效果。检查时务必运行:
SELECT * FROM role_edges WHERE TO_ROLE = 'your_dev_role'; 看它是否间接继承了高危权限;更稳妥的做法是,不用角色统授,而用显式 GRANT/REVOKE 控制每张表、每个视图的访问粒度。










