MySQL中如何得到权限信息

    最近在做一次MySQL数据迁移的时候,突然发现自己遗漏了一个地方,那就是权限信息没有导出,如果我们使用mysqldump
--all-databases的时候没有添加--flush-privileges的时候,导出的数据中是不会包含mysql数据库的。

   而我其实是比较懒的,不想因为这个重新导出一次,那么我就有几种方式选择。

   如果在MySQL 5.5,5.6的版本中,我可以直接导出mysql.user的数据即可。

   如果使用脚本化完成,基本是这样的形式即可,本意其实就是show grants for 'xxx'的组合形式,不断拼接解析。

mysql -e "SELECT DISTINCT CONCAT('show grants for
','''',user,'''@''',host,'''',';') AS query FROM mysql.user where
user!='root'" | grep -v query >/tmp/showgrants.sql && mysql
</tmp/showgrants.sql | egrep -v 'Grants for|query'

    运行后的语句大体是如下的形式:

GRANT ALL PRIVILEGES ON *.* TO 'adm'@'localhost' IDENTIFIED BY PASSWORD '*3DCFB64FE0CB05D63B9AF64492B5CD6269D82EE8'
GRANT ALL PRIVILEGES ON `Cyou_DAS`.* TO 'adm'@'localhost'
GRANT USAGE ON *.* TO ''@'mysqlactivity'

    这一招在5.5,5.6中都是可行的,但是迁移的数据库是5.7的,看到下面导出的语句,我感觉不对劲,难道都不要密码,如果确实没有,这是一个多么大的坑。

GRANT USAGE ON *.* TO 'phplamp'@'localhost'
GRANT ALL PRIVILEGES ON `phplampDB`.* TO 'phplamp'@'localhost'    我知道5.7做了一些改进,本身对于show grants也有一些限制,没想到真碰上这种情况,教训是如此的深刻。

    所以回到问题,如果现在要解决,就有大体的三种方式来同步权限;
方法1:重新导出导入整个数据库    不评论,我绝对不会这么做,只是看起来是一个完整的过程,但是无用功太多,很容易被鄙视
方法2:导出mysql的权限配置    如果是在5.5,5.6的环境,直接导出mysql.user表数据即可,但是在5.7中可不行,一种方式就是导出整个mysql库的数据
方法3:pt工具导出         使用自定义脚本或者pt工具来导出权限信息

当然解决方法很多,我就说说方法2,方法3

我对比了5.6和5.7 的表结构情况。不看不知道,一看差别还真不小。

MySQL 5.7的mysql.user表含有45个字段
MySQL 5.6的mysql.user表含有43个字段

这是表面现象,不是5.7多两个字段这么简单,真实情况如下:

1) MySQL5.7中多了下面的3个字段,字段和数据类型如下:

 password_last_changed  | timestamp            
 password_lifetime      | smallint(5) unsigned
 account_locked         | enum('N','Y') 
2)这么一看总数对不上,这是因为MySQL 5.7相比5.6少了password字段

3)还有个细节可能被忽略,那就是MySQL 5.7的字段user相比MySQL 5.6长度从16字符增长到了32字符。

   这就奇怪了,为什么没有了password字段呢,没有了password字段,这个功能该怎么补充呢

MySQL5.6中查看mysql.user的数据结果如下:

> select user,password,authentication_string from mysql.user;               
| user           | password               | authentication_string |
| app_live_im    | *E96DB97255EF3ED52454A10EDA1AE7BABC8D3700 |    |
| mysqlmon       | *0571D080430BC7B60A3F4D41A8D71501E6B8FDAA |    | 而在MySQL 5.7中,结果却有所不同

+-----------------+-------------------------------------------+
| user            | authentication_string                     |
+-----------------+-------------------------------------------+
| gym             | *0CD6502815166F2C7E17B630C3248B900065FCEA |
| actv_test       | *82A4DC7B3F5E73E822529E9EF4DE8C042253445A |一个重要差别就在于mysql.user表的字段值 plugin

 max_connections: 0
  max_user_connections: 0
                plugin: mysql_native_password
 authentication_string:
      password_expired: N
 password_last_changed: 2016-11-09 11:38:39
     password_lifetime: 0

 基于这个安全策略,可以做很多的事情,5.7默认就是这种模式。

   看起来之前的那种show grants得到的信息很有限,那么我们来看看pt工具的效果,直接运行./pt-show-grants即可

-- Grants for 'webadmin'@'10.127.8.207'                             
CREATE USER IF NOT EXISTS 'webadmin'@'10.127.8.207';  
ALTER
USER 'webadmin'@'10.127.8.207' IDENTIFIED WITH 'mysql_native_password'
AS '*DA43F144DD67A3F00F086B0DA1288C1D5DA7251F' REQUIRE NONE PASSWORD
EXPIRE DEFAULT ACCOUNT UNLOCK;
GRANT ALL PRIVILEGES ON *.* TO 'webadmin'@'10.127.xx.xx';            

 这样的语句相对来说就是完整的,使用show grants的结果少了很多,只包含基本的权限信息。        

> show grants for 'webadmin'@'10.12.20.133';
| GRANT ALL PRIVILEGES ON *.* TO 'webadmin'@'10.12.xx.xxx' |   为什么使用pt工具能够得到更多,不是这个工具有多神奇,而是里面充分利用了新特性的东西。

pt-show-grants里面是这样写的,对于MySQL 5.7的处理方式。

      # If MySQL 5.7.6+ then we need to use SHOW CREATE USER
      my @create_user;
      if ( VersionCompare::cmp($version, '5.7.6') >= 0 ) {
         eval {
            @create_user = @{ $dbh->selectcol_arrayref("SHOW CREATE USER $user_host") };
         };
         if ( $EVAL_ERROR ) {
            PTDEBUG && _d($EVAL_ERROR);
            $exit_status = 1;
         }
         PTDEBUG && _d('CreateUser:', Dumper(\@create_user));
         # make this replication safe converting the CREATE USER into
         # CREATE USER IF NOT EXISTS and then doing an ALTER USER
            my $create = $create_user[0];
            my $alter  = $create;
            $create =~ s{CREATE USER}{CREATE USER IF NOT EXISTS};
            $create =~ s{ IDENTIFIED .*}{};
            $alter  =~ s{CREATE USER}{ALTER USER};
            @create_user = ( $create, $alter );
            PTDEBUG && _d('AdjustedCreateUser:', Dumper(\@create_user));
      }

简化一下就是使用show create user这种方式,在这个基础上额外补充一下,使得这个语句更加健壮。

我们使用show create user 'webadmin'@'10.12.20.133'得到的结果如下:

| CREATE USER 'webadmin'@'10.12.20.133' IDENTIFIED WITH
'mysql_native_password' AS '*DA43F144DD67A3F00F086B0DA1288C1D5DA7251F'
REQUIRE NONE PASSWORD EXPIRE DEFAULT ACCOUNT UNLOCK |

语句看起来丰满了很多,但是似乎还是少了些权限的信息,

这是因为5.7里面完整的信息是通过show create user和show grants for 'xx'这两种方式完成的,而在5.6中只需要通过show grants for 'xxx’即可。
   明白了原委和解决方法,这个问题处理起来其实就很简单了。

时间: 2024-08-02 04:47:11

MySQL中如何得到权限信息的相关文章

详解MySQL中的存取权限_Mysql

看到很多网友提出关于MySQL登录不上服务器的问题,包括有的是在PHP中调用MySQL时发生的不能登录MySQL数据库服务器的问题,以为是PHP出了问题.其实是MySQL权限的问题. MySQL的权限系统在MySQL的手册中是很长的一章,我把它打印出来足足印了20多页!这里就将我对它的理解简要地写出来,希望能对刚刚接触MySQL的同志有点帮助:有说得不对的地方,也请同志们指出. 在我了解了MySQL的权限机制后,不由得不赞叹它的严密与巧妙:也许所有的数据库系统都是如此罢,只是别的大型数据库把权限

MySQL中导出用户权限设置的脚本分享_Mysql

在对MySQL数据库进行迁移的时候,有时候也需要迁移源数据库内的用户与权限.对于这个迁移我们可以从mysql.user表来获取用户的相关权限来生成相应的SQL语句,然后在目标服务器上来执行生成的SQL语句即可.本文提供了生成提取用户权限的脚本并给出演示. 1.生成用户权限的脚本 复制代码 代码如下: [root@HKBO ~]# more exp_grant.sh  #!/bin/bash  #Function export user privileges    pwd=123456  expg

mysql中循环截取用户信息并插入到目标表对应的字段中_Mysql

操作环境:有表game_list,字段:uid,score1,score2,seat_id,last_update: 传入参数为i_player_detail ,传入的值为多个用户的id.之前分数.之后分数.座位号,每个用户的数据用分号(:)隔开: 操作目的:将各个用户对应的属性插入到目标表对应的字段中,last_update为数据更新日期: 传入参数i_player_detail ,里面存放多个用户的信息,每个用户的一组数据用分号隔开,每个用户的信息多个,比如 "用户id,score,desk

MySQL中设置prompt实现信息提示的教程

然后来看看默认情况下的样子 在看看 使用prompt参数后的样子 然后看看黑科技的玩法 好了 现在来说说最后彩色显示的方法,默认在使用--prompt参数后是显示不出彩色的,为了显示彩色,我们需要借助系统上功能才可以的, [root@GCE-Node1_www.dwhd.org ~]# awk '/mariadb/' .bashrc alias mysql=$(echo -e '/usr/local/mariadb-galera/bin/mysql -uroot -p****** -h127.0

mysql-百度地图从MySql中获取经纬度

问题描述 百度地图从MySql中获取经纬度 <%@ page contentType="text/html; charset=utf-8" %> <%@ page language="java" %> <%@ page import="com.mysql.jdbc.Driver" %> <%@ page import="java.sql.*" %> <% String dr

MySQL中show命令方法得到表列及整个库的详细信息(精品珍藏)_Mysql

show databases;show tables from db_name; show columns from table_name from db_name;show index from talbe_name [from db_name]; show status;show variables; show [full] processlist;show table status [from db_name]; show grants for user; 除了status,process

mysql中权限参数说明

1 授权表范围列的大小写敏感性 +--------------+-----+-----+---------+----+-----------+------------+ | 列           |Host |User |Password |Db  |Table_name |Column_name | | 大小写敏感性 |No   |Yes  |Yes      |Yes |Yes        |No          | +--------------+-----+-----+------

信息-mysql中有关两张表关联的查询语句

问题描述 mysql中有关两张表关联的查询语句 宝宝信息表中存的是已经接种过疫苗的信息,is_vaccined为1,另外一张表中,存的是所有疫苗的详细信息.现在,我想通过获取宝宝id来查询该宝宝所有的疫苗的状态(包括已经接种的和未接种的),改怎么写查询语句?? 解决方案 select t1.*, t2.* from t_baby_info t1 left outer join t_vaccine t2 on t1.vaccine_id= t2.vaccine_id 解决方案二: @caozhy

代码-Jsp页面中查询到MySQL数据库里的表格信息,怎样导出到本地excel

问题描述 Jsp页面中查询到MySQL数据库里的表格信息,怎样导出到本地excel jsp页面从数据库中读出了一个message表格,怎样通过jsp编写把这个表格导出到excel.最好是详细代码 解决方案 response.reset(); response.setContentType("application/vnd.ms-excel;charset=GBK"); response.setHeader("Content-Disposition", "i