Fork me on GitHub

Access denied for user 'xxxx'@'localhost' (using password: YES)

问题

版本:MySQL 5.6

新建一个用户且正确授权之后,登陆失败报错:

access denied for user ‘xxxx’@’localhost’ (using password: YES)

新建用户操作:

CREATE USER ‘xxxx’ IDENTIFIED BY ‘xxxx’;

授权操作:

GRANT ALL PRIVILEGES ON `TargetTable`.* TO ‘xxxx’@’%’;

原因

存在匿名用户:’’@’localhost’ identified by ‘’。

MySQL 连接时从 mysql.user 表中匹配主机和用户名,将所有符合条件的条目排序, 选取排序第一的条目进行验证,主机名和用户名的排序规则:

  1. 主机名优先用户名;
  2. 具体主机名优先所有主机%;
  3. 具体用户名优先匿名用户’’;
  4. 空字符串’’能匹配所有用户名,’%’能匹配所有主机名。

在本地使用MySQL Installer安装MySQL Server 5.6时,在本地自动新建了一个匿名用户,查看mysql.user表可以看到有一个用户名为空字符串的用户:

SELECT * FROM `mysql`.`user`;

所以在登陆 xxxx@localhost 时,用户表中有两个条目匹配成功:

  • ‘’@’localhost’
  • ‘xxxx’@’%’ (%所有主机)

此时,匿名用户的主机更精确,所以排在想要登录的’xxxx’前面,MySQL 会用匿 名用户的账号’’@’localhost’ identified by ‘’来进行验证,这个时候输入的密码 是’xxxx’,匿名用户的密码是空字符串’’,所以会报拒绝访问,登录失败;这个时 候我输入的密码如果是空字符串’’的话,反而能够登录成功。

有趣的是,然而这样虽然登录成功了,但是登陆的账号并不是想登陆的’xxxx’,而是匿名用户。

查看登录时指定的用户和当前登录的用户,就能发现,登录时指定的用户是’xxxx’,但是登录的却是匿名用户。

SELECT USER(), CURRENT_USER();

解决方法

删除本地的匿名用户。

BJTU-HXS wechat
海内存知己,天涯若比邻。