用户权限

创建用户

create user 'ua'@'%' identified by 'pa';

这条语句的逻辑是创建一个用户’ua’@’%’,密码是pa。(%表示可以从任意ip登录,可以指定ip)

这条命令做了两个动作:

  1. 磁盘上,往mysql.user表里插入一行,由于没有指定权限,所以这行数据上所有表示权限的字段的值都是N;
  2. 内存里,往数组acl_users里插入一个acl_user对象,这个对象的access字段值为0。

权限操作

  • 赋予权限:grant 权限列表 on 数据库.[.表名] to 用户名 [with grant option];(with grant option表示可以传递给其他用户)
  • 取消权限:revoke 权限列表 on 数据库.[.表名] from 用户名;

全局权限:

全局权限,作用于整个 MySQL 实例用于管理MySQL服务器的操作,这些权限信息保存在 mysql 库的 user 表里,只能用*.*赋予。

revoke命令与grant命令,做了如下两个动作:

  1. 磁盘上,将mysql.user表里,用户这一行的所有表示权限的字段的值都修改为”N”或者”Y”;
  2. 内存里,从数组acl_users中找到这个用户对应的对象,将access的值修改为0或者1。

但是每个连接会有一个线程对象,会将全局权限值拷贝到线程对象中,之后所有关于全局权限的判断,都直接使用线程对象内部保存的权限位。

数据库权限:

对于数据库权限,会在磁盘上生成一个mysql.db表;在内存里,生成数组acl_dbs,这个是一个全局数组,所有线程判断db权限都用这个数组;并不会存在线程对象中。

表权限和列权限:

表权限定义存放在表mysql.tables_priv中,列权限定义存放在表mysql.columns_priv中。这两类权限,组合起来存放在内存的hash结构column_priv_hash中。

跟数据库权限类似,这两个权限每次grant的时候都会修改数据表,也会同步修改内存中的hash结构。因此,对这两类权限的操作,也会马上影响到已经存在的连接

对于flush privileges命令:

flush privileges命令会清空内存中的权限数组,然后从磁盘中对应的表中读取数据重新加载,重新构造一个数组。所以如果内存的权限数据和磁盘数据表相同的话,不需要执行flush privileges。

权限列表:(所有权限all privileges)

  1. 数据权限 增删查改(select\update\delete\insert)
  2. 结构权限 结构操作(create\drop)
  3. 管理权限 权限管理(create user\grant\revoke)