必须先执行SELECT User,Host FROM mysql.user WHERE User = ''确认匿名用户存在,再DELETE FROM mysql.user WHERE User = ''并立即FLUSH PRIVILEGES;若无结果则无需删除,且需排查root空密码等更常见隐患。
很多人一上来就删,结果发现 SELECT User,Host FROM mysql.user; 里压根没空用户名——那删个寂寞。匿名用户的本质是 User = ''(空字符串),不是 NULL,也不是 'anonymous'。MySQL 5.7+ 默认初始化时可能留一个 ''@'localhost',但 MySQL 8.0+ 安装脚本已默认跳过这步;如果你是离线安装或从旧版本升级而来,才更可能遇到。
SELECT Host, User FROM mysql.user WHERE User = '';—— 只查空字符串,不查
IS NULL,避免误判''@'127.0.0.1' 和 ''@'localhost' 当成两个,其实它们都算匿名,都要删只执行 DELETE FROM mysql.user WHERE User = ''; 是无效的——MySQL 不会自动重载权限缓存。你立刻再用 mysql -u '' -h localhost 尝试连接,大概率还能进(尤其在未重启服务的情况下)。
FLUSH PRIVILEGES;,强制 MySQL 重新读取
mysql.user 表DROP USER ''@'localhost':该语法在 MySQL 5.7 中不支持空用户名,会报错 ERROR 1396 (HY000): Operation DROP USER failed
SELECT User,Host FROM mysql.user WHERE User = '';,确保返回空集很多所谓“匿名登录成功”,其实是 root 用户密码为空导致的:当你执行 mysql -u root 不输密码就进了,误以为是匿名用户在作祟。这种情况比真正匿名用户更常见,也更危险。
SELECT User,Host,authentication_string FROM mysql.user WHERE User = 'root';,若
authentication_string 为空或为 *(MySQL 5.7),说明密码未设ALTER USER 'root'@'localhost' IDENTIFIED BY 'YourStrongPass123!';
ALTER USER 'root'@'localhost' IDENTIFIED WITH caching_sha2_password BY 'YourStrongPass123!';
FLUSH PRIVILEGES;,否则新密码不生效离线部署常跳过初始化安全脚本(如 mysql_secure_installation),导致一堆隐患埋着不动,直到被扫描器打中。
DROP DATABASE IF EXISTS test;,并删掉对应权限记录:
DELETE FROM mysql.db WHERE Db = 'test' OR Db = 'test\\_%';
root 是否只允许 'localhost',而非 '%';若不需要远程管理,直接删掉所有非 localhost 的 root 记录/etc/my.cnf 或 /etc/mysql/my.cnf 里有没有残留的 [mysqld] 下的 skip-grant-tables——有它等于完全放弃权限校验FLUSH PRIVILEGES 没跑,或者 root 还裸奔,删了匿名用户也白删。