mysql 数据库运维

mysql8.0 mysql5.7安装,mysql 创建 赋权用户
mysql8.0用户的创建,赋权

20180628 Chenxin
20190801 Update
说明
本文档除特殊说明处,均为8.0版本默认方式.5.7版本也支持.特殊说明处只针对mysql5.7版本.
卸载系统预装的mysql(否则在初始化数据库的时候无法成功):
yum remove mysql (可能需要执行2次)
which mysql (确保mysql删除完毕)

安装
下载安装包
cd /opt
wget https://dev.mysql.com/get/Downloads/MySQL-8.0/mysql-8.0.11-linux-glibc2.12-x86_64.tar.gz #8.0
wget https://dev.mysql.com/get/Downloads/MySQL-5.7/mysql-5.7.27-linux-glibc2.12-x86_64.tar.gz #5.7

执行安装
/usr/sbin/groupadd mysql
/usr/sbin/useradd -M -g mysql mysql -s /sbin/nolgin
yum install -y cmake ncurses-devel bison libnuma numactl libaio1 libaio-dev
tar xzvf mysql-8.0.11-linux-glibc2.12-x86_64.tar.gz #根据版本调整
mv mysql-8.0.11-linux-glibc2.12-x86_64 /usr/local/mysql
mkdir /usr/local/mysql/data
chown -R mysql:mysql /usr/local/mysql

修改环境变量
cat >> /etc/profile << EOF
export PATH=/usr/local/mysql/bin:/usr/local/mysql/lib:$PATH
EOF
source /etc/profile

配置文件
更改/etc/my.cnf配置文件(注意编码问题)
cat /etc/my.cnf
[client]
port = 3306
socket = /tmp/mysql.sock
default-character-set = utf8mb4

[mysqld]
port = 3306
user = mysql
socket = /tmp/mysql.sock
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
log-error = error.log

关闭bin-log

skip-log-bin
binlog_expire_logs_seconds = 172800 # 5.7版本需要注释掉

增加 为默认值的10倍

innodb_buffer_pool_size=1342177280

使用老版本的密码认证方式,客户端暂时不支持

default-authentication-plugin=mysql_native_password

新加的编码,适用于5.X版本,8.X版本不知道是否适用(部分适用)

character-set-server=utf8mb4
collation-server=utf8mb4_general_ci

default-character-set = utf8mb4 开启会导致msyql8无法启动

大小写敏感,专用coinw

lower_case_table_names=1

最大连接数设置

max_connections=2000

[mysql]
default-character-set = utf8mb4

[mysql.server]
default-character-set = utf8mb4

[mysqld_safe]
default-character-set = utf8mb4

log-error=mysqld.log 同error.log,开启会覆盖msyqld的配置

未采用此方式启动,不会生效.不会覆盖mysqld配置

pid-file=mysqld.pid
初始化
8.0初始化

有密码初始化 #mysqld --defaults-file=/etc/my.cnf --initialize

无密码初始化 #mysqld --defaults-file=/etc/my.cnf --initialize-insecure

这里root用户默认没有密码,执行: mysqld --defaults-file=/etc/my.cnf --initialize-insecure

5.7初始化

有密码初始化 mysqld --initialize --user=mysql --basedir=/usr/local/mysql/ --datadir=/usr/local/mysql/data/

无密码初始化 mysqld --defaults-file=/etc/my.cnf --initialize-insecure

启动mysql
/usr/local/mysql/support-files/mysql.server start

全部搭建完成,启动服务后可以验证一下编码: show variables like '%char%'; #要先初始化才能执行
mysql> show variables like '%char%';
+--------------------------+----------------------------------+
| Variable_name | Value |
+--------------------------+----------------------------------+
| character_set_client | utf8mb4 |
| character_set_connection | utf8mb4 |
| character_set_database | utf8mb4 |
| character_set_filesystem | binary |
| character_set_results | utf8mb4 |
| character_set_server | utf8mb4 |
| character_set_system | utf8 |
| character_sets_dir | /usr/local/mysql/share/charsets/ |
+--------------------------+----------------------------------+
8 rows in set (0.01 sec)

参数说明
1.最大连接数(默认为100)
a.临时方案,重启失效
查看最大连接数 show variables like '%max_connections%';
修改最大连接数 set GLOBAL max_connections = 2000;
b.修改my.cnf

最大连接数设置

max_connections=2000

用户创建与权限配置
登陆
/usr/local/mysql/bin/mysql -u root
use mysql

安全初始化方式后,默认会自动生成一个密码,放到log文件里,比如error.log,格式类似
2019-08-01T07:30:19.871772Z 1 [Note] A temporary password is generated for root@localhost: tlq!*/4fQ
/usr/local/mysql/bin/mysql -u root -P 10306 -p
登陆后,必须先重置密码才能执行其他指令,如下(否则报错,由参数default_password_lifetime导致的):
alter user user() identified by "12345...6";

创建admin用户
CREATE USER 'admin'@'localhost' IDENTIFIED BY 'xxx';
CREATE USER 'admin'@'%' IDENTIFIED BY 'xxx';

赋权admin用户
GRANT ALL PRIVILEGES ON . TO 'admin'@'localhost' WITH GRANT OPTION;
GRANT ALL PRIVILEGES ON . TO 'admin'@'%' WITH GRANT OPTION;

配置产品库和对应用户
CREATE DATABASE coinw01;
CREATE USER 'coinw'@'%' IDENTIFIED BY 'xxx';
CREATE USER 'coinw'@'localhost' IDENTIFIED BY 'xxx';
GRANT ALL PRIVILEGES ON coinw01.* TO 'coinw'@'%';
GRANT ALL PRIVILEGES ON coinw01.* TO 'coinw'@localhost;

创建备份账户
CREATE USER 'dumper'@'localhost' IDENTIFIED BY 'cvv......kkfggh[]65.,jk';
GRANT SELECT,LOCK TABLES,EVENT ON . TO 'dumper'@'localhost' WITH GRANT OPTION;

删除多余用户
为安全考虑,mysql的admin建议暂时只启用本地登录;删除mysql中的root和test用户:
use mysql;delete from user where user='';delete from user where user='root'; flush privileges;

查看用户权限
use mysql;
select * from user \G;

清除DB密码记录的日志文件:
echo > /root/.mysql_history

数据文件分盘存储/data分区
/data/mysql_data/data/**.
首先mv /usr/local/mysql/data /data/mysql_data/
再 ln -s /data/mysql_data/data /usr/local/mysql/data

导出表结构/导出整个库
导出表结构(mysqldump -d dbname > xxx.sql),一般几分钟
mysqldump --default-character-set=utf8mb4 -uxbzj -psjErbN29h7heU8sg -P 10306 -d xlogin > xlogin.sql
mysqldump --default-character-set=utf8mb4 -h rm-m5emc856519a6ocibyo.mysql.rds.aliyuncs.com -uroot1 -p -P 3306 -d btc018_vcoin > coinw01.sql

导出整个数据,一般几分钟
遇到报错mysqldump: Got error: 1066: Not unique table/alias: 'avirtualwallettransfer' when using LOCK TABLES,则添加 --single-transaction参数,如下
mysqldump --default-character-set=utf8mb4 --single-transaction -h localhost -uroot1 -p -P 3306 btc018_vcoin > coinw01.sql
另外,若导出非常慢,可以尝试增加参数
mysqldump --default-character-set=utf8mb4 --max_allowed_packet=4194304 --net_buffer_length=16384 -ucoinw -psjE...g -P 10306 btc018_vcoin > ./btc018_vcoin.sql

导入到新建的库中去(时间比较长)
mysql --default-character-set=utf8mb4 -ucoinw -psj....8s..g -P 10306 coinw01 < coinw01.sql # 3.5G数据导入需要2小时

问题:

这里遇到一次连接阿里云RDS异常的情况,原因
1.因为密码里有感叹号,只能手动复制(放在命令行会报错)
2.因为RDS是3306,而本地/etc/my.cnf配置client端口10306(mysql客户端默认连接10306端口).在访问外部3306的RDS时,务必手动指定.如 mysql -h rm-m5...rds.aliyuncs.com -uroot1 -p -P3306 (否则默认连接的会是10306)

mysqldump导出慢的解决方法:
-e 使用包括几个VALUES列表的多行INSERT语法;
--max_allowed_packet=XXX 客户端/服务器之间通信的缓存区的最大大小;
--net_buffer_length=XXX TCP/IP和套接字通信缓冲区大小,创建长度达net_buffer_length的行。
1.先查看目标库的参数值 如下:
mysql> show variables like 'max_allowed_packet';
mysql> show variables like 'net_buffer_length';
2.导出时加上参数: mysqldump --max_allowed_packet=4194304 --net_buffer_length=16384 ... dbname > dbname.sql

备份
备份脚本
[xbzj@ip-10-10-0-200 ~]$ cat rds-bak/sql-xlogin-backup.sh

!/bin/bash

Des: for RDS xlogin backup to S3

20180914 Chenxin

source /etc/profile
cd /bak || mkdir -p /bak

echo "预期整个过程大约会持续10-30分钟"
echo

DB信息

DBuser='xbzj'
DBpasswd='xxxxx'
DBhost='xlogin-read.cyp7d7zwyhrc.us-east-1.rds.amazonaws.com'
DBname='xlogin'
bktime=date +%Y%m%d%H%M%S

删除多日前数据

find ./ -mtime +7 -name "*sql.tar.gz" -exec rm -rf {} ;
filename="$DBname"-"$bktime".sql

执行备份

touch $filename

echo "开始dump数据文件,生成临时sql文件"
mysqldump --column-statistics=0 --opt -R -E --single-transaction --default-character-set=utf8mb4 -h $DBhost -P 10306 -u$DBuser -p$DBpasswd $DBname > $filename

若备份成功,执行压缩和上传至S3

if [ $? == 0 ];then
echo "sql文件dump成功,正在执行压缩sql文件"
tar czvf "$filename".tar.gz $filename --remove-files
echo "压缩完成,正在执行本地文件上传至S3"
/usr/bin/aws s3 sync /bak/ s3://xbzj-data-backup/rds-xlogin-read/ --exclude '' --include 'xlogin-' --acl private --region eu-central-1
fi

mysqldump参数说明:

--column-statistics=0
仅用于mysql8,否则会报一个错误

--opt
等同于--add-drop-table, --add-locks, --create-options, --quick, --extended-insert, --lock-tables, --set-charset, --disable-keys 该选项默认开启, 可以用--skip-opt禁用.

--routines, -R
导出存储过程以及自定义函数。

--events, -E
导出事件。

--single-transaction
保证导出的一致性状态.该选项在导出数据之前提交一个BEGIN SQL语句,BEGIN 不会阻塞任何应用程序且能保证导出时数据库的一致性状态。它只适用于多版本存储引擎(它不显示加锁通过判断版本来对比数据),仅InnoDB。本选项和--lock-tables 选项是互斥的,因为LOCK TABLES 会使任何挂起的事务隐含提交。要想导出大表的话,应结合使用--quick 选项。( --quick, -q 不缓冲查询,直接导出到标准输出。默认为打开状态,使用--skip-quick取消该选项。)

备份策略说明:
将此任务加到预热服的计划任务里,每天1次备份.
加到预热服的Jenkins里作为一个任务,供维护的时候使用.

恢复已备份的库文件
mysql --default-character-set=utf8mb4 -h 192.168.31.129 -P 3306 -uxbzjsqladmin -p..password.. xlogin < ./xlogin-20181030152405.sql

客户端管理工具
MySQL Workbench
mysql官方工具,支持最新的用户加密方式,但安装后,通过新的加密方式(默认)连接的时候会报错,报"发生外部未知错误".重新在服务器上安装mysql,并采用老的加密方式后,就可以连接了.这个工具比较全面,可以查看服务器各状态,用户权限等等.
https://dev.mysql.com/downloads/workbench/

Mysql-front
比较轻量级的mysql-front(不支持mysql8.0的用户新的加密模式),当前版本6.0
http://www.mysqlfront.de/

MySQL 8.0 删除 binlog.0000XX文件 以及 关闭log-bin功能
(注意,仅用于单机版,不能用到主从或集群模式)

参考: https://blog.csdn.net/yunuobing/article/details/74779995

关闭原因(需求):
开启binlog记录功能,会增加从库磁盘I/O等的压力,非必要开启,请关闭。必须开启情况:
1)级联同步A->B->C中间的B时.
2)在从库做数据库备份,数据库备份必须要有全备和binlog日志,才是完整的备份。

关闭流程: 先删除不需要的binlog文件,然后通过配置文件关闭binlog记录功能

1.确认当前状态. 先登录数据库查询log-bin的状态(8.0版本默认是开启的)。
mysql> show variables like 'log_bin';
+---------------+-------+
| log_bin | ON |
+---------------+-------+

2.手动删除binlog
查看当前文件
mysql> show binary logs;
+---------------+------------+
| Log_name | File_size |
+---------------+------------+
| binlog.000031 | 49983 |
| binlog.000032 | 39670 |
| binlog.000033 | 1074115884 |
| binlog.000034 | 1074594937 |

删除1天以前的
mysql> PURGE MASTER LOGS BEFORE DATE_SUB( NOW( ), INTERVAL 1 DAY);
Query OK, 0 rows affected (0.05 sec)

确认删除是否生效
mysql> show binary logs;
+---------------+-----------+
| Log_name | File_size |
+---------------+-----------+
| binlog.000086 | 802811016 |
| binlog.000087 | 155 |
+---------------+-----------+
2 rows in set (0.00 sec)

删除指定某个文件之前的所有日志
mysql> PURGE MASTER LOGS TO 'binlog.000087';
Query OK, 0 rows affected (0.19 sec)

确认删除是否生效
mysql> show binary logs;
+---------------+-----------+
| Log_name | File_size |
+---------------+-----------+
| binlog.000087 | 155 |
+---------------+-----------+
1 row in set (0.00 sec)

3.修改配置文件
编辑my.cnf文件,一般路径为:/etc/my.cnf
在mysqld下面添加:skip-log-bin 或者disable-log-bin(未测试)

4.重启Mysql.
/usr/local/mysql/support-files/mysql.server restart

5.确认状态修改是否成功
mysql> show variables like 'log_bin';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| log_bin | OFF |
+---------------+-------+
1 row in set (0.00 sec)

再次查看binlog,则会报错(因为关闭了):
mysql> show binary logs;
ERROR 1381 (HY000): You are not using binary logging

mysql> show variables like 'expire_log%';
+------------------+-------+
| Variable_name | Value |
+------------------+-------+
| expire_logs_days | 0 |
+------------------+-------+
1 row in set (0.00 sec)

mysql> show variables like 'binlog_expire_logs_seconds';
+----------------------------+--------+
| Variable_name | Value |
+----------------------------+--------+
| binlog_expire_logs_seconds | 172800 |
+----------------------------+--------+
1 row in set (0.00 sec)

附,对应的my.cnf配置文件:
[root@localhost data]# cat /etc/my.cnf
[client]
port = 3306
socket = /tmp/mysql.sock
default-character-set = utf8mb4

[mysqld]
port = 3306
user = mysql
socket = /tmp/mysql.sock
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
log-error = error.log

关闭bin-log

skip-log-bin

关闭后,过期时间就无所谓了

binlog_expire_logs_seconds = 172800

使用老版本的密码认证方式,客户端暂时不支持

default-authentication-plugin=mysql_native_password

新加的编码,适用于5.X版本,8.X版本不知道是否适用

character-set-server=utf8mb4
collation-server=utf8mb4_general_ci

default-character-set = utf8mb4 开启会导致msyql8无法启动

[mysql]
default-character-set = utf8mb4

[mysql.server]
default-character-set = utf8mb4

[mysqld_safe]
default-character-set = utf8mb4

log-error=mysqld.log 同error.log

pid-file=mysqld.pid

扩展知识
mysql8.0用户的创建,赋权
20180628 Chenxin
mysql8在创建用户赋权跟以前的版本有所不同.

配置老的加密方式-配置文件my.cnf
因目前mysql8最新的用户验证方式,很多客户端不支持,且目前来看,不是很推荐(貌似乱码).修改回老的认证方式的话,my.cnf文件配置:
default-authentication-plugin=mysql_native_password

创建用户与赋权用户
create user '用户'@'主机' identified by '密码';
grant 权限 on 数据库 to '用户'@'主机'

会报错的写法:(过去都是这种写法-无需create)
GRANT ALL PRIVILEGES ON . TO 'admin'@'localhost' IDENTIFIED BY 'xxx';
报错信息:Error Code: 1064. You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near 'IDENTIFIED BY 'xxx” at line 1
正确的写法:
CREATE USER 'admin'@'localhost' IDENTIFIED BY 'xxx';
GRANT ALL PRIVILEGES ON . TO 'admin'@'localhost';

不推荐:GRANT ALL PRIVILEGES ON . TO 'admin'@'localhost' WITH GRANT OPTION;

可见,在授权的语句中需要去掉 IDENTIFIED BY 'password';其中,关键字 “privileges” 可以省略.

WITH GRANT OPTION说明
让授权的用户可以将这些权限 grant 给其他用户.这个特性一般用不到.实际中,数据库权限最好由 DBA 来统一管理.
grant, revoke 用户权限后,该用户只有重新连接 MySQL 数据库,权限才能生效.

grant 增删改查.
grant insert,delete,update,select on testdb.* to common_user@'%'

grant 作用在整个 MySQL 服务器上:
grant all on . to dba@localhost; — dba 可以管理 MySQL 中的所有数据库

grant 作用在存储过程.函数上:
grant execute on procedure testdb.pr_add to ‘dba'@'localhost'
grant execute on function testdb.fn_add to ‘dba'@'localhost'

单独授予某种权限的写法:
GRANT SELECT ON db.table TO 'test'@'localhost';

更新用户密码
mysql-8
ALTER USER 'admin'@'%' IDENTIFIED WITH mysql_native_password BY 'password';
说明:(上一个版本使用以下)
mysql-5
use mysql
update user set password=password('as..password...2') where user='mysqladmin' and host='%';
flush privileges;

查看用户权限(几种方式)
select host, user, authentication_string, plugin from user;
SELECT DISTINCT CONCAT('User: ''',user,'''@''',host,''';') AS query FROM mysql.user;
select * from user \G; (如果采用新加密方式,输出非常容易乱码,造成控制台异常.不知道对数据是否有影响.之后重装了)

查看某个用户对哪些库拥有权限
show grants for 'xbzjsqladmin'@'localhost';
显示:GRANT USAGE ON . TO xbzjsqladmin@localhost #这里USAGE是无权限的意思
对于GRANT USAGE ON:
mysql> GRANT USAGE ON . TO 'name'@'localhost';
一个账户有用户名name,没有密码.该账户只用于从本机连接.未授予权限.通过GRANT语句中的USAGE权限,你可以创建账户而不授予任何权限.它可以将所有全局权限设为'N'.假定你将在以后将具体权限授予该账户.

查看当前用户权限
show grants;

收回权限
revoke 跟 grant 的语法差不多,只需要把关键字 “to” 换成 “from” 即可:
revoke all on . from 'admin'@'%';
REVOKE只能取消用户权限,而不能删除用户.
即使取消了所有的权限,用户仍然可以连接到服务器.
要想彻底的删除用户,必须使用DELETE语句将该用户的记录从MySQL数据库中的user表中删除.
该语句的语法格式如下:
Delete from user where user = "user_name" and host = "host_name" ;
再比如:
delete from user where user='';
delete from user where user='root';
flush privileges;

刷新权限-所有操作后,应执行
flush privileges;

备注1
grant经常给开发人员的权限
创建表.索引.视图.存储过程.函数等权限.

grant 创建.修改.删除 MySQL 数据表结构权限.
grant create on testdb.* to developer@'192.168.0.%';
grant alter on testdb.* to developer@'192.168.0.%';
grant drop on testdb.* to developer@'192.168.0.%';

grant 操作 MySQL 外键权限.
grant references on testdb.* to developer@'192.168.0.%';

grant 操作 MySQL 临时表权限.
grant create temporary tables on testdb.* to developer@'192.168.0.%';

grant 操作 MySQL 索引权限.
grant index on testdb.* to developer@'192.168.0.%';

grant 操作 MySQL 视图.查看视图源代码 权限.
grant create view on testdb.* to developer@'192.168.0.%';
grant show view on testdb.* to developer@'192.168.0.%';

grant 操作 MySQL 存储过程.函数 权限.
grant create routine on testdb.* to developer@'192.168.0.%';
grant alter routine on testdb.* to developer@'192.168.0.%';
grant execute on testdb.* to developer@'192.168.0.%';

备注2
mysql授权表共有5个表

user表
列出可以连接服务器的用户及其口令,并且它指定他们有哪种全局(超级用户)权限.
在user表启用的任何权限均是全局权限,并适用于所有数据库.
例如,如果你启用了DELETE权限,在这里列出的用户可以从任何表中删除记录,所以在你这样做之前要认真考虑.

db表
db表列出数据库,而用户有权限访问它们.在这里指定的权限适用于一个数据库中的所有表.

host表
host表与db表结合使用在一个较好层次上控制特定主机对数据库的访问权限,这可能比单独使用db好些.
这个表不受GRANT和REVOKE语句的影响,所以,你可能发觉你根本不是用它.

tables_priv表
tables_priv表指定表级权限,在这里指定的一个权限适用于一个表的所有列.

columns_priv表
columns_priv表指定列级权限.这里指定的权限适用于一个表的特定列.

扩展知识2-msyql的启动方式与匹配的配置文件
一、MySQL读取配置文件的顺序
读取顺序:/etc/my.cnf > /etc/mysql/my.cnf > /usr/etc/my.cnf > ~/.my.cnf
命令验证:
[root@mysql ~]# mysql --verbose --help | grep my.cnf
order of preference, my.cnf, $MYSQL_TCP_PORT,/etc/my.cnf /etc/mysql/my.cnf /usr/etc/my.cnf ~/.my.cnf

二、MySQL启动方式
MySQL的启动方式通常分成三种:mysqld、mysqld_safe、mysqld_multi(主要用于多实例启动)

三种方式的关系:
首先当我们使用service mysqld start或者/etc/init.d/mysqld start这样的方式启动的时候,其实是使用了mysql.server这个脚本,这个脚本默认会调用mysqld_safe来启动mysqld,所以通常我们启动mysql之后查看进程的时候会发现有mysqld和mysqld_safe这两个进程存在。这两种通常都是单实例的启动方式,当然也可以使用mysqld来启动多实例的。而mysqld_multi用来启动多实例,也是通过先调用mysqld_safe和mysqld来启动mysql的。

三、MySQL启动原理
默认的mysql的服务启动程序是mysql.server,mysql.server程序主要是会用到两个程序和一个函数,分别是my_print_defaults、myslqd_safe和parse_server_arguments
1、my_print_defaults:读取my.cnf配置文件,输出参数传递给parse_server_arguments,该程序只读my.cnf中[mysqld]中的参数。
2、parse_server_arguments:该函数处理my_print_defaults传递过来的参数赋值给--basedir、--datadir、--pid-file、--server-startup-timeout
3、myslqd_safe:mysqld_safe程序调用mysqld程序来启动mysql服务,[mysqld_safe]会覆盖mysqld部分中的参数
4、mysqld_multi会读取配置文件中的[mysqld_muti],[mysqldN]下面的参数,N需要时一个整数,建议用端口号表示,该部分的配置会覆盖[mysqld]部分中的配置
5、在mysqld进程挂掉的时候,mysqld_safe进程会监测到并重新将mysqld启动起来。

posted @ 2020-04-21 13:56  ChanixChen  阅读(1578)  评论(0编辑  收藏  举报