数据库与网站的关系
在数据库中区分有数据库系统用户与数据库普通用户,二者的划分主要体现在对一些高级函数与资源表的访问权限上。直白一些就是高权限系统用户拥有整个数据库的操作权限,而普通用户只拥有部分已配置的权限。
网站在创建的时候会调用数据库链接,会区分系统用户链接与普通用户链接;当多个网站存在一个数据库的时候,root就拥有最高权限可以对多个网站进行管辖,普通用户仅拥有当前网站和配置的部分权限。所以当我们获取到普通用户权限时,我们只拥有单个数据库权限,甚至文件读写失败;取得高权限用户权限,不仅可以查看所有数据库,还可以对服务器文件进行读写操作。
多个网站可能共用同一个mysql服务器,关系图可能如下
高权限注入就是例如网站A含有SQL注入漏洞,那我们注入后通过MYSQL服务器不止能够访问数据库A还可以同时对数据库B进行查看,但前提是网站A使用的账号也就是访问的用户权限足够访问数据库B,一般是root权限等。
在上上个文章中有提到,在我们搭建的mysql数据库的服务器中包含4个数据库,分别数information_schema库,informance_schema库,mysql库,以及sys库,其中mysql库里就有保存我们用户的一些信息,包括能够访问的权限等。
MYSQL中存在4个控制权限的表,分别为user表,db表,table_priv表,columns_priv表
mysql权限表的验证过程为:
先从user表中的Host, User ,Password这3个字段中判断连接的ip、用户名、密码是否存在,存在则通过验证
通过身份认证后,进行权限分配,
按照user, db, tables_priv, columns_priv的顺序进行验证。
即先检查全局权限表user,如果user中对应的权限为v,则此用户对所有数据库的权限都为v,
将不再检查db,tables_priv,columns_priv:如果为N,则到db表中检查此用户对应的具体数据库,
并得到db中为Y的权限﹔如果db中为N,则检查tables_priv中此数据库对应的具体表,取得表中的权限Y,以此类推。
接下来我们以版本为8.0.12的MYSQL进行操作
通过进入我们的数据库查询后发现有一个上面说的mysql库
接着我们使用mysql这个数据库,进入后查询发现了我们所说的user表,table_priv表,columns_priv表这四个表,如下图
首先我们要知道MYSQL的权限级别有哪些
MysQL权限级别分为:
全局性的管理权限:作用于整个MysQL实例级别
数据库级别的权限:作用于某个指定的数据库上或者所有的数据库上
数据库对象级别的权限:作用于指定的数据库对象上(表、视图等)或者所有的数据库对象
接下来我们查看mysql这个数据库中有哪些用户,语句为
select user,host from mysql.user;
从这个表可以看到表里一共有4个用户,其中包括我们用于登录的root这个用户,接下来我们来看看root这个登录账号有什么权限,即查看用户对应的权限,语句如下:
select * from user where user='root' and host='localhost' \G;
这下我们可以看到这个最高权限,root权限,基本上都是yes的,接下来我们创建一个普通用户来对比权限上的区别
有两种方式创建MySQL授权用户
1.执行create user/grant命令(推荐方式)
2.CREATE USER 'finley'@' localhost’IDENTIFIED BY 'some_pass ';通过insert语句直接操作MysQL系统权限表。
这里我们以第二种方式来示例,解读为创建一个test1的用户,密码为12345
CREATE USER 'test1'@'localhost'IDENTIFIED BY '12345';
接下来我们重复之前的操作,查询mysql这个数据库中的用户有哪些,语句也就是和上面相同
select user,host from mysql.user;
这时候就发现多了一个test1的用户,接着我们查看一下test1这个用户的权限有哪些,语句相同
select * from user where user='test1' and host='localhost' \G;
发现test1这个普通用户的权限很低,什么都干不了,我们来验证一下是不是这样我们先退出当前的root用户,然后用下列语句登录我们的test1的普通用户
mysql -utest1 -p12345
发现我们访问不到任何数据库只能访问到它自带的information_schema这个数据库,这个默认有权限访问的数据库。接下来我们给test1这个用户赋予root的权限,即把普通用户变为管理员的语句:
GRANT ALL PRIVILEGES ON *.* TO 'test1 '@' localhost' WITH GRANT OPTION;
然后按上述查询权限语句,查看test1这个用户的权限有没有发生变化,发现test1这个用户的权限发生了改变,基本上都可以执行
然后我们退出root账户,登录test1账户,查看数据库,发现已经有权限可以查询到数据库了
如果想要删除用户,然后查询数据库中的用户,即删除用户语句如下
drop user test1@'localhost';
我们还可以玩一点奇怪的,如果你只想赋予用户一点权限,但又不想赋予像root一样那么多的权限,假如我们创建一个test2用户,我们的数据库中有一个test数据库,里面有一张表叫做t1表,我们给test2用户查询test数据库中t1这张表的id的权限,即只提供id查询权限的语句如下:
grant select(id) on test.t1 to test2@'localhost' identified by '12345';
发现我们可以查询得到test这个数据库但却无法查询到所有有关t1的信息,这是因为我们前面设置了test2这个用户只能查看t1表中的id,不能看其他的,所以查询语句得改成:
select id from t1;
发现可以正常查询到id了