索引查询
image.pngMySQL程序架构简图
image.pngMySQL程序的架构
image.png分区变为不同的"块"--存储数据和元数据
中间层--VFS(虚拟文件系统)--同一接口,操作不同的文件系统
程序=指令(算法)+数据(数据结构)
索引--平衡树 Blance Tree--每个叶子到根的距离相同--范围/等值查询
mysql 老不死的 降低数据冗余/支持事务操作
事务
付款-收款--两个操作必须同时完成,否则回滚至初始状态,即:事务不能忽略
评价--显示了一半--两个操作可以不同时完成,即:事务可以忽略
评论转发显示的次数--不是很重要--kv store
MySQL 事务好,性能低
MariaDB
Percona-server 提供开源工具和新论文
NewSQL 事务和性能兼具
TiDB 国内
系统工程师(安装启动数据库并部署在文件系统上) dba 程序员
表 索引 行式存储
yum -y install mariadb-server
rpm -ql mariadb-server 服务端
systemctl start mariadb.service; ss -ntl 3306
ls /var/lib/mysql 数据存放处
ls /var/lib/mysql/mysql
.MYD
.MYI
.frm 格式
mysql
show engines; 支持的存储引擎 如下图1 横排显示
show engines\G 竖排显示
create database mydb;
use mydb
create table tbl1 (id int unsigned,name varchar(200));
show table status; 显示所有表
show table status\G 竖排显示 如下图2
show table status like 'tbl1'; 显示指定的表
show table status like 'tbl1'\G
% 任意长度的任意字符
_ 单个长度的任意字符
show table status like 'tbl%'\G
show table status like 'tbl_'\G
show table status where engine='Innodb'\G 按条件进行过滤
ls /var/lib/mysql/mydb/ 只显示tbl1的.frm表格式文件
数据文件都存放在/var/lib/mysql/ibdata1中,不支持高级功能
vim /etc/my.cnf.d/server.cnf
更改配置--每表使用单独的表空间文件
[mysqld]
innodb_file_per_table = ON 不区分字符大小写,路径可能区分
systemctl restart mariadb.service
mysql
use mydb
create table tbl2 (id int unsigned,name varchar(200));
ls /var/lib/mysql/mydb/ 显示tbl2的.frm表格式文件和.ibd数据文件,支持高级的数据管理特性
show engine innodb status; innodb本身自带的内容
show engine innodb status\G
窗口1
mysql
use mydb
lock tables tbl1 read;
窗口2
mysql
use mydb
select * from tbl1; 虽然锁了tbl1,但是可以查询
insert into tbl1 values (1,'tom'); 需等待别人释放锁,因为此数据被施加读锁
窗口1:unlock tables; 释放施加的所有表中的锁
窗口2:显示insert操作完成
窗口1:lock tables tbl1 write;
窗口2:select * from tbl1; tbl1被施加写锁,不能查询
窗口1:unlock tables;
窗口2:显示select操作完成
窗口1:lock tables tbl1 write;
窗口2:lock tables tbl1 read; tbl1被施加写锁--需等别人释放锁后--我们才可施加读锁
其他
flush tables 把表数据同步至磁盘
flush tables with read lock;
flush tables with write lock; 把表数据同步至磁盘+立即施加读锁 (for update;备份用)
select cluase [for update | lock in share mode] 较少使用
for update 写锁
lock in share mode 读锁
查询到表中某一行数据后,以更新的方式对此行数据加锁
每个操作语句会自动施加锁,不用手动添加
只有当我们偶尔备份需要请求全局锁时,才需要去手动施加锁
图1
image.png
图2
image.png
图3 事务日志介绍
image.png事务日志介绍 如上图3
mysql两类变量 服务器变量 状态变量
mysql
show variables; 显示服务器变量--配置参数--可自己改
show variables\G
运行时可修改--不重启,修改后立即有效,临时生效
运行时不可修改--配置文件中修改,需重启,才会永久有效
show global variables; 有管理权才可以看
show global variables\G
全局设置--管理权才可修改
修改后,对新建立的所有会话有效,对当前会话和已经建立的会话无效
show session variables; session可省略
会话设置--当前会话有效
set session/global 变量名
set @@global.变量名
set @@session.变量名
show status; 显示状态变量--计数器--服务器的工作状态--手动置0/服务器自动调整
show status\G
show variables like 'innodb%';
show variables like 'innodb%log%';
innodb_log_files_in_group 2
ll /var/lib/mysql/ -h 5M ib_logfile0/ib_logfile1
innodb_mirrored_log_groups 1
设置为2,最好两个镜像组放在不同的路径下
innodb_flush_log_at_trx_commit 1/0/2
提交事务时,如何同步事务 每秒同步一次 or commit就立即同步
show global variables like 'autocommit';
ON/true/yes/1 表示真--开启
OFF/faulse/no/0 表示假--未开启
set @@global.autocommit=0;
show global variables like 'autocommit'; 显示OFF
set @@global.autocommit=1;
show global variables like 'autocommit'; 显示ON
select @@global.autocommit; 显示1
select @@session.autocommit; 显示1
set @@global.autocommit=0;
select @@global.autocommit; 显示0
select @@session.autocommit; 显示1 修改全局设置后,对当前会话和已经建立的会话无效
窗口2:select @@session.autocommit; 显示0
临时生效,写入配置文件,重启mariadb-server,永久有效
set @@session.autocommit=0; 不会自动提交事务/减少io压力/需要手动提交事务
启动事务/标记为一个事务的开始/在一个事务内部操作 手动提交事务
start transaction;
show tables;
select * from tbl1; 生产中,一定要加where条件
insert into tbl1 values (2,'jerry'),(3,'lucy');
select * from tbl1;
rollback; 回滚 (or commit; 提交)
select * from tbl1; 显示插入的数据没了
支持保存点,一个事务很大(30个语句/执行到29个时/发现第26个错误/想回滚)
每执行2个语句就保持一下,类似快照
start transaction;
insert into tbl1 values (2,'jerry');
savepoint first; 保存一次即保存点1,命名为first
insert into tbl1 values (3,'lucy');
savepoint second; 保存点2
delete from tbl1 where id=1;
select * from tbl1;
rollback to second; 不想删除1了,回滚至最近一次的保存状态即保存点2
select * from tbl1; 又有1了
commit; 确认提交,此时再回滚,就要手动操作删除了
数据本身回滚--容易;如果create table/database,可能就麻烦了
select @@session.tx_isolation; 查看隔离级别,默认第三级别--可重复读(幻读)
设置为第一级别--读未提交
窗口1和窗口2:set @@session.tx_isolation='read-uncommitted';
窗口1和窗口2:start transaction;
窗口1:delete from tbl1 where id=2; select * from tbl1;
窗口2:select * from tbl1; 未显示id=2
设置隔离级别为"读未提交",则只要改了,就可以看见
窗口1:rollback;
窗口2:select * from tbl1; 显示id=2 看到数据变化,脏读
窗口2:commit; or rollback; 结束事务
设置为第二级别--读提交
窗口1和窗口2:set @@session.tx_isolation='read-committed';
窗口1和窗口2:start transaction;
窗口1:delete from tbl1 where id=2; select * from tbl1; id=2消失
窗口2:select * from tbl1; 显示id=2仍在
设置隔离级别为"读提交",只要别人没提交,就看不见改变的数据
窗口1:commit;
窗口2:select * from tbl1; id=2消失 看到数据变化,不可重复读
窗口2:commit; 结束事务
设置为第三级别--可重复读
窗口1和窗口2:set @@session.tx_isolation='repeatable-read';
窗口1和窗口2:start transaction;
窗口1:insert into tbl1 values (4,'lily'); select * from tbl1; 显示id=4
窗口2:select * from tbl1; 没有id=4
窗口1:commit;
窗口2:select * from tbl1; 别人提交了,但仍然没有id=4,可重复读--幻读
此时,自己再添加id=4,则会冲突,底层已经变化
窗口2:commit; select * from tbl1; 自己提交了,才会有数据变化显示id=4
设置为第四级别--串行化
窗口1和窗口2:set @@session.tx_isolation='serializable';
窗口1和窗口2:start transaction;
窗口2:select * from tbl1; 显示id=4存在(省略此步骤,否则会造成缓存)
窗口1:delete from tbl1 where id=4; select * from tbl1; id=4消失
窗口2:select * from tbl1; 显示id=4仍在;应该被阻塞才对,有缓存的原因
窗口1:commit;
窗口2:select * from tbl1; 没有缓存的情况下,别人提交后,显示id=4消失
窗口2:commit;
vim /etc/my.cnf.d/server.cnf
在[mysqld]中添加以下信息
skip_name_resolve = ON 跳过反解,不使用IP解析为主机名
重启才会生效
mysql
use mydb
select current_user(); 显示当前登陆的用户账号
create user test@'192.168.%.%' identified by 'testpass';
set password for 'test'@'192.168.%.%' = password('qianggedu'); 更改用户密码
flush privileges; 更新权限表,使之生效
desc mysql.user;
select user,host,password from mysql.user; 查看用户密码表
update mysql.user set password=password('testpass') where user='test' and host='192.168.%.%';
更新表,where一定要加,host不能忘了,不会立即生效 更改用户密码
flush privileges; 需要重载权限文件
连接上mysql然后操作的命令都可以使用mysqladmin在命令行操作
命令行操作,不用连接mysql
man mysqladmin
mysqladmin -uroot -hlocalhost ping 显示alive--正常
mysqladmin -uroot -hlocalhost flush-privileges
mysqladmin -uroot -hlocalhost create testdb
mysql -uroot -hlocalhost -e 'show databases'
(mysqladmin -uroot -hlocalhost drop databases 删除数据库/一定思虑再三)
(mysqladmin -uroot -hlocalhost -p password 'new_pass' 没有密码时/可直接设定)
忘记mysql管理员密码
update mysql.user set password=password('qiang') where user='root';
flush privileges;
mysql 不能登陆了
假设忘记管理员密码
systemctl stop mariadb.service
vim /usr/lib/systemd/system/mariadb.service
在ExecStart后面添加2个选项
ExecStart=/usr/bin/mysqld_safe --basedir=/usr --skip-grant-tables --skip-networking
systemctl daemon-reload 重载配置文件
systemctl start mariadb.service
mysql 连接上了,此时没读授权表,不能使用"set password"更改密码
update mysql.user set password='' where user='root'; 设置root密码为空
select user,host,password from mysql.user; 验证是否更改
exit 更改完,退出即可,不用flush,因为没读授权表
systemctl stop mariadb.service
vim /usr/lib/systemd/system/mariadb.service
删除后面添加的两个选项"--skip-grant-tables --skip-networking"
ExecStart=/usr/bin/mysqld_safe --basedir=/usr
systemctl daemon-reload
systemctl start mariadb.service
mysql 登陆,此时读取了授权表
窗口1
mysql
show grants; 查询自己拥有的权限
show grants for 'test'@'192.168.%.%'; 查询test拥有的权限
USAGE--普通权限--information_schema和test--不能create/...
窗口2
mysql -utest -ptestpass -h 192.168.1.7
show databases;
create database mytest; 没有权限,不能create
窗口1
grant create on mytest.* to 'test'@'192.168.%.%';
flush privileges;
窗口2
create database mytest; 可以create
use mytest
create table tbl1 (id int); 可以
select * from tbl1; 没有查看权限
窗口1
grant select on mytest.tbl1 to 'test'@'192.168.%.%'; 授权test,只能查看这一张表
show grants for 'test'@'192.168.%.%'; 查询test用户拥有的权限
窗口2
create table tbl2 (id int,name char(20),age tinyint);
insert into tbl2 values (1,'tom',13); 没有权限,禁止操作
窗口1
grant insert(id,name) on mytest.tbl2 to 'test'@'192.168.%.%';
授权test只能对mytest库的tbl2表插入某些字段--id,name
窗口2
insert into tbl2 values (1,'tom',13); 还是不行,只能在id和name字段处插入数据
insert into tbl2(id,name) values (1,'tom'); ok,字段集权限
索引
systemctl start mariadb.service
mysql
use mydb
mydb使用的字符集和排序规则要合适 使用中文--要更改默认使用的字符集为utf8
先创建数据
create table students (stuid int unsigned auto_increment primary key,name varchar(200),age tinyint unsigned,gender enum('f','m'),major varchar(200));
也可使用char定长(不足固定长度--自动补充内容),可提高查询性能,但会浪费空间
insert into students (name,age,gender,major) values ('Jia Baoyu',17,'m','Pixiejian'),('Lin Chong',37,'m','Xianglongzhang'),('Ximen Qing',31,'m','Kuihuabaodian'),('Li Mochou',27,'f','Wuxianggong');
数据少--用不用索引都行
另一个窗口--命令行操作:批量创建用户数据
for i in {1001..2000};do mysql -e "insert into mydb.students values ('$i','stu$i',$[$RANDOM%100+1],'m','major$i')";done
select * from students;
select name,age from students where age >= 15;
explain select name,age from students where age >= 15;
explain select * from students where name = 'stu1002';
rows显示全表扫描,其他信息含义--参考文档
select count(stuid) from students; 查询stuid的总行数
help create index
create index name on students(name);
show indexes from students; indexes可以变为index
explain select * from students where name = 'stu1002';
rows显示1行--索引起作用了,其他的信息也发生变化
explain select * from students where name like 'stu100%';
rows显示9行
explain select * from students where name like '%stu100%';
rows显示全表扫描--B TREE索引--左前缀索引(%只能放在右侧,否则全表扫描)
create index name_and_age on students(name,age); 组合索引
explain select * from students where name like 'stu100%';
possible_keys显示两个索引--重复索引,name/name_and_age索引,副作用
drop index name on students; 删除name索引
show indexes from students;
explain select * from students where name like 'stu100%';
rows显示9行,possible_keys显示name_and_age索引
explain select * from students where age >= 50;
name_and_age索引的最左边一个字段是name,不能跳过字段找下一个
但可以查询--name/name and age
所以possible_keys显示为空,没有可用索引,即全表扫描
explain select * from students where name like 'stu%' and age >= 50;
possible_keys显示name_and_age索引,但key为空--没用索引,匹配行数量太多
explain select * from students where name like 'stu100%' and age >= 50;
possible_keys显示name_and_age索引,key为name_and_age,使用了索引
语句写法不同--可导致--是否使用索引/如何使用索引
explain select * from students where age >= 98 union select * from students where name like 'stu100%';
select搜索来自两个不同的表的字段才有意义
explain select * from students where stuid=4;
type和ref显示const--性能最好
explain select * from students where stuid in (1,77,1009,1200);
ref为空--使用的是一个集合(显示结果为多行内容)--范围查询range
主从复制
image.png日志存储
image.png日志
mysql
use mysql
show tables;
查询日志--general_log
show global variables like 'general%';
show global variables like 'log_output'; 日志输出至何处
set global general_log=on; 开启查询日志
show global variables like 'general%'; 显示on
select * from mydb.students where stuid=3;
ls /var/lib/mysql/centos7.log 生成查询日志
tail /var/lib/mysql/centos7.log 显示执行过的查询语句
set @@global.log_output='TABLE'; 输出位置更改为表
show global variables like 'log_output';
select * from mysql.general_log; 显示执行的查询语句
set @@global.general_log=off; 关闭查询日志
show tables;
慢查询--slow_log
select @@global.long_query_time; 默认10s
show global variables like '%slow%';
set @@global.slow_query_log=on; 开启慢查询
log_slow_queries/slow_query_log 两个版本/兼容,更改其中一个,两个都会更改
show global variables like '%slow%';
show global variables like 'log_output';
set @@global.log_output='FILE'; 记录文件中
错误日志
show global variables like '%error%';
tail /var/log/mariadb/mariadb.log
二进制日志
show global variables like 'binlog_format%'; 二进制日志的格式
不支持运行时修改
exit
vim /etc/my.cnf.d/server.cnf
[mysqld]
log_bin=master.log log_bin或log-bin
systemctl restart mariadb.service
mysql
show global variables like '%log%bin%';
show master logs; 显示master.000001
show master status; 显示当前正在使用的文件--master.000001
flush logs; 滚动
show master logs; 显示master.000001/2
show master status; 当前正在使用master.000002
use mydb
select * from students;
show master status; Position未变化
delete from students where stuid=1986;
show master status; Position改变
show binlog events; 默认看master.000001文件中的事件
show binlog events in 'master.000002'; 看master.000002
xid--事务编号 Pos End_log_pos
max_binlog_size=1073741824(字节) 1g 二进制日志达到此大小就滚动;
测试时,临时关闭二进制文件,不记录
set @@session.sql_log_bin=off;
delete from students where stuid=2000;
show binlog events in 'master.000002'; 无变化,未记录日志
select * from students; 没有stuid=2000,数据被删除但未记录
set @@session.sql_log_bin=on;
delete from students where stuid=1999;
show binlog events in 'master.000002'; 数据被删除并被记录
show binlog events in 'master.000002' from 440; 从440位置开始
show binlog events in 'master.000002' from 440 limit 2; 只显示两行
ls /var/lib/mysql/master.000001
cat /var/lib/mysql/master.index 显示master.000001/2/...
cd /var/lib/mysql/; mysqlbinlog master.000001 查看文件
show processlist; 线程列表
mysqlbinlog --start-position 440 master.000002 从440位置开始
mysqlbinlog --start-position 440 --stop-position=508 master.000002 440-508(结束)
增量和差异备份
image.png备份和恢复
备份时,要启动二进制日志
centos7.4
man mysqldump
备份一个库
mysqldump mydb|less 输出至屏幕
mysqldump mydb > /tmp/mydb-fullback-$(date +%F-%H-%M-%S)
备份文件名称:库名-备份类型-日期
ls /tmp/
mysql
create database txdb;
exit
mysql txdb < /tmp/mydb-fullback-2018-05-07-21-35-41
mysql
use txdb
show tables;
select * from students;
exit
ll -h /var/lib/mysql/ 生成很多日志
线上系统备份时必须加锁
-x 锁定所有库的所有表,读锁
-l 锁定指定库所有表
备份多个库
mysqldump --databases mydb txdb mysql > /tmp/mydb-txdb-mysql-fullback-$(date +%F-%H-%M-%S)
less /tmp/mydb-txdb-mysql-fullback-2018-05-07-22-11-03
与创建一个库的区别是:会自动添加"create database"语句
centos7.4-2
yum -y install mariadb-server
systemctl start mariadb.service
mysql
grant all on *.* to 'admin'@'192.168.%.%' identified by 'admin';
grant all on *.* to 'admin'@'%.fgq.com' identified by 'admin';
flush privileges;
exit
centos7.4
mysql -uadmin -h192.168.1.8 -padmin < /tmp/mydb-txdb-mysql-fullback-2018-05-07-22-11-03
centos7.4-2
mysql
show databases;
mysql协议明文--不安全--ssl/vpn
centos7.4
mysql
use mydb
show table status\G 看当前库的存储引擎
show table status where engine='innodb'\G 当前库存储引擎是innodb的表
show table status where engine!='innodb'\G 当前库存储引擎不是innodb的表
exit
mysqldump --single-transaction --databases mydb
仅适用于InnoDB存储引擎;支持热备;适合线上系统;
备份后自动提交事务;自动释放事务锁
以上是无脑备份
完整备份+binlog(模拟增量/差异备份)
假设备份所有库
mysql
flush tables with read lock; 锁定所有表
flush logs; 滚动一下数据库的二进制日志(sql--新变化--文件开始处)
show master logs; 看日志文件有几个
show master status; 看现在处于哪个日志文件哪个位置(重放binlog的开始位置)
sql语句执行完成,形成最终数据结果,sql语句记录在二进制日志中
二进制日志和数据库--备份其中之一
恢复:
备份的数据库(即数据最终结果)+二进制日志重放(开始位置:最后一次备份结束位置)
exit
备份所有库--使用选项--简便操作
mysqldump -x -R -E --triggers --all-databases --master-data=2 --flush-logs > /tmp/alldatabases-fullback-$(date +%F-%H-%M-%S)
参考文档
-x 锁定所有库的所有表,读锁
-R 存储历程;备份指定库的存储过程和存储函数;
--triggers 备份指定库的触发器;
-E 备份指定库的调度器
--master-data[=#] 备份时处于哪个日志文件哪个位置,1--未注释,2--注释
--flush-logs 锁定表完成后,即进行日志刷新操作;
less /tmp/alldatabases-fullback-2018-05-08-00-01-47
mysql
use mydb
create table teachers (tid int unsigned primary key auto_increment,name varchar(200));
insert into teachers (name) values ('Ouyang Feng'),('Song Jiang');
show master status;
exit
systemctl stop mariadb.service 模拟故障
cd /var/lib/mysql/
mysqlbinlog master.000007 > /tmp/alldatabases-binlog-$(date +%F-%H-%M-%S)
rm -rf ./* 模拟故障
备份放在--非本机设备上/本机上与原数据不同的硬盘上
假设准备了一台新主机(仍是此centos7.4)
systemctl start mariadb.service
mysql
show databases;
set @@session.sql_log_bin=off; 关闭二进制日志--从备份中恢复,不需要记录二进制日志
或者
vim /etc/my.cnf.d/server.cnf
[mysqld]
#log_bin=master.log 注释掉此行
systemctl restart mariadb.service
\. /tmp/alldatabases-fullback-2018-05-08-00-01-47 加载备份的所有数据库数据
use mydb
show tables;
\. /tmp/alldatabases-binlog-2018-05-08-00-16-34 加载备份的二进制文件
show tables;
或者借助另一台主机centos7.4-2(不操作--了解写法)
假设和down掉的主机centos7.4有一样的数据库和一样的二进制文件
centos7.4上需要授权用户
mysql
grant all on *.* to 'admin'@'192.168.%.%' identified by 'admin';
grant all on *.* to 'admin'@'%.fgq.com' identified by 'admin';
flush privileges;
vim /etc/my.cnf.d/server.cnf
[mysqld]
#log_bin=master.log 注释掉此行
systemctl restart mariadb.service
centos7.4-2上需要连接centos7.4--192.168.1.7
mysql -uadmin -h192.168.1.7 -padmin < /tmp/alldatabases-fullback-2018-05-08-00-01-47
mysql -uadmin -h192.168.1.7 -padmin < /tmp/alldatabases-binlog-2018-05-08-00-16-34
centos7.4
mysql
show databases;
use mydb
show tables;
mysqldump备份--总有些内容没有顾及到,较麻烦--更好的方式用Xtrabackup
Xtrabackup
https://www.percona.com/
--Software--MySQL Database Software--Percona XtraBackup
--Feature Comparison版本比较
--Download Percona XtraBackup Now下载--选择合适的version和software
表空间管理系统--自管理的文件系统--自管理空间划分为盘区--每盘区/每修改/有一个日志序列号lsn: log sequence number
盘区1插入1行数据--lsn=1
盘区2插入1行数据--lsn=2
盘区1修改1行数据--lsn=3
......
假设lsn:1-1000
完全备份:根据lsn进行1-1000的备份
新修改的数据变化:
增量备份:lsn:第一次1001-1002 第二次lsn:1003-1007 第三次lsn:1008-1019
差异备份:lsn:第一次1001-1002 第二次lsn:1001-1007 第三次lsn:1001-1019
Xtrabackup备份出的数据集,用于做还原前,先做prepare(准备)操作,后做recover操作:mysqldump无此功能
prepare(准备)操作:
若此备份后,无其他增量备份:已提交的事务做同步,未提交的事务做回滚
若此备份后,有其他增量备份:已提交的事务做同步,未提交的事务保持原状(下次增量备份可能会提交)
完全备份--增量备份--修改部分内容--down机
恢复时:
完全备份+增量备份+binlog的时间点还原
完全备份+差异备份+binlog的时间点还原
完全备份--同步
增量备份(第一次增量--最后一次增量)--同步
最后是未同步--回滚
全部合并在一起,复制到mysql的数据目录(datadir)下,修改权限即可使用
二进制日志文件--时间点还原
前提--备份alldatabases 若是备份部分库--还原部分库即可
完全备份--备份所有库
InnoDB--热备--可读写;MyISAM--温备--只读
增量备份
InnoDB--热备--增量;MyISAM--温备--(另外一次)完全(MyISAM不支持增量)
centos7.4
rz 上传包文件(~)
yum -y install ./percona-xtrabackup-24-2.4.11-1.el7.x86_64.rpm
rpm -qa |grep percona 程序包没问题
rpm -ql percona-xtrabackup-24
man innobackupex
cd /var/lib/mysql/
mkdir -pv /mydata/xbdata
innobackupex --user=root --host=localhost /mydata/xbdata/
无密码,就不用写了,完全备份 显示completed OK!
ls /mydata/xbdata/; ls /mydata/xbdata/2018-05-08_16-47-58/
cd /mydata/xbdata/2018-05-08_16-47-58/
less backup-my.cnf 备份时所依赖的关键配置(非所有内容)
less xtrabackup_binlog_info 备份时处于哪个日志文件的哪个位置
less xtrabackup_checkpoints 备份类型/lsn的开始和结束/
less xtrabackup_info 程序文件信息--uuid/备份工具/命令/版本号/时间始末/二进制文件名称和位置/加密/压缩/增量/部分备份
没有增量--仅完全备份的还原--无binlog
systemctl stop mariadb.service 模拟故障
cd /var/lib/mysql; rm -rf ./*
准备
cd /mydata/xbdata/2018-05-08_16-47-58/
innobackupex --apply-log ./ 显示completed OK!
还原
innobackupex --copy-back ./ 显示completed OK!
ll /var/lib/mysql/ 属主和属组不对
chown -R mysql.mysql /var/lib/mysql/
systemctl start mariadb.service; ss -ntl
mysql
show databases;
exit
全量+增量/差异+binlog
最小权限
create user 'backup'@'localhost' identified by 'backup';
grant reload,lock tables,replication client,process on *.* to 'backup'@'localhost';
flush privileges;
exit
准备 全量备份
窗口1
innobackupex --user=backup --host=localhost --password=backup /mydata/xbdata/
显示completed OK!
ls /mydata/xbdata
cat /mydata/xbdata/2018-05-08_18-02-45/xtrabackup_checkpoints
backup_type = full-backuped
to_lsn = 1884712 日志序列号:1884712
mysql
use mydb
delete from students where stuid=1300;
delete from students where stuid=1400;
delete from students where stuid=1500;
不用退出--热备即可
窗口2
第一次增量备份
innobackupex --incremental /mydata/xbdata --incremental-basedir=/mydata/xbdata/2018-05-08_18-02-45
--incremental 当前备份的增量
--incremental-basedir 基于谁做增量
cat /mydata/xbdata/2018-05-08_18-20-37/xtrabackup_checkpoints
backup_type = incremental
from_lsn = 1884712
to_lsn = 1888446
窗口1
insert into teachers (name) values ('Jiao Da');
select * from teachers;
窗口2
第二次增量备份
ll /mydata/xbdata/
innobackupex --incremental /mydata/xbdata --incremental-basedir=/mydata/xbdata/2018-05-08_18-20-37
cat /mydata/xbdata/2018-05-08_18-34-24/xtrabackup_checkpoints
backup_type = incremental
from_lsn = 1888446
to_lsn = 1888734
窗口1
delete from teachers where tid=1;
select * from teachers;
窗口2
二进制日志文件备份
mkdir /mydata/binlogs/
cat /mydata/xbdata/2018-05-08_18-34-24/xtrabackup_info
mysqlbinlog -j 2088 /var/lib/mysql/master.000001 > /mydata/binlogs/2018-05-08_18-34-24-binlog
systemctl stop mariadb.service 模拟故障
rm -rf /var/lib/mysql/* 模拟故障
cd /mydata/xbdata/2018-05-08_18-02-45/ 进入全量备份文件夹中
仅作同步--redo,不做回滚--undo
innobackupex --apply-log --redo-only ./ 全量恢复
innobackupex --apply-log --redo-only ./ --incremental-dir=/mydata/xbdata/2018-05-08_18-20-37
全量备份和第一次增量备份合并
cat xtrabackup_checkpoints
backup_type = log-applied
last_lsn = 1888446 第一个增量结束位置
innobackupex --apply-log --redo-only ./ --incremental-dir=/mydata/xbdata/2018-05-08_18-34-24
全量+第一次增量+第二次增量合并
cat xtrabackup_checkpoints
last_lsn = 1888734 第二个(最后一个)增量结束位置
回滚操作
innobackupex --apply-log ./ 把未提交的事务回滚
还原
innobackupex --copy-back ./ 显示completed OK!
ll /var/lib/mysql/ 数据文件恢复,但属主和属组要更改
chown -R mysql.mysql /var/lib/mysql/*
systemctl start mariadb.service; ss -ntl
mysql
use mydb
select * from students where stuid=1300; 第一次修改删除了,显示无
select * from teachers; 第二次修改,添加了"Jiao Da"
第二次增量备份后,Ouyang Feng被删除,但仍有--使用binlog
set @@session.sql_log_bin=off; 使用binlog恢复时,要关闭二进制日志文件
\. /mydata/binlogs/2018-05-08_18-34-24-binlog 重放二进制日志
select * from teachers; "Jiao Da"没有了--恢复故障前的那一刻了
set @@session.sql_log_bin=on; 开启二进制日志
接下来赶紧做一下全量备份/上线后再做全量备份
备份部分库--参考文档
生产中--策略:每月1号--全量;非1号--增量;
恢复时--手工操作--监控每一步都不能出错;
备份后--输出的内容已邮件形式保存到邮箱;
图1:主从复制
image.png图2:级联复制
image.png图3:双主模型1
image.png图4:多主模型2
image.png图5:一从多主模型
image.png图6:不同的主从集群模型--基于奇偶
image.png图7:shard分片冗余
image.png超过系统的承载能力--需要扩展
向上--性价比低
向外--多增加主机
主节点down了--冗余/从节点代替
主节点无法承载写请求--高可用
主从复制 如上图1
一主多从
异步:从节点从主节点复制更新数据时有延迟(有时间窗)
读写分离器(read write splitter)
将用户的请求分发至合适的位置
读请求--平均分发出去;
写请求--一点没有少--对写请求没有负载均衡
有效利用时间差
drop误删库,有延迟,拔网线,从节点还未删除;或从节点删除,我们还有备份
主节点--只写
从节点--只读+从主节点复制写操作
如果主节点只写,还是压力大,解决方案:级联复制 如上图2
双主模型--互为主从 如上图3
多主模型 如上图4
一从多主模型 如上图5
基于奇偶范围/列表查询 如上图6
shard分片冗余 如上图7
主从复制
centos7.4 主节点 192.168.1.5
centos7.4-2 从节点 192.168.1.6
1 时间同步
2 安装mariadb-server
yum -y install mariadb-server
3 主节点centos7.4
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 1
log-bin = master-log 最好放在非/var/lib/myqsl路径下或者不同的磁盘上
skip_name_resolve = on centos6不用写on,只需要把参数写在此处即可
systemctl start mariadb.service
mysql
show master status; 位置245
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
最小权限--192.168.1.6
flush privileges;
show master status; 位置变化497
show binlog events in 'master-log.000003';
show binlog events in 'master-log.000003'\G
主节点创建拥有复制权限的用户账号时,从节点不需要同步,从497开始复制即可
4 从节点centos7.4-2
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 7
relay-log = relay-log
skip_name_resolve = on
systemctl start mariadb.service
mysql
help change master to 查看用法
change master to master_host='192.168.1.5',master_user='repluser',master_password='replpass',master_log_file='master-log.000003',master_log_pos=497;
ll /var/lib/mysql 生成几个新文件
cat /var/lib/mysql/master.info 执行的命令
cat /var/lib/mysql/relay-log.info 开始和结束位置
show slave status\G
help start slave 查看用法
start slave; IO_THREAD | SQL_THREAD都开启
start slave io_thread; 只复制不重放
show slave status\G
Slave_IO_Running: Yes
Slave_SQL_Running: Yes
Relay_Log_File: relay-log.000002 Relay_Log_Pos: 530 变化--做了初始化
Read_Master_Log_Pos: 497 没有变化
5 测试
主节点centos7.4
create database mydb;
show master status; 580位置
从节点centos7.4-2
show slave status\G
Read_Master_Log_Pos: 580 已经复制过来
Seconds_Behind_Master: 0 没有落后主节点
show databases; 显示mydb已经创建
主节点centos7.4
use mydb
create table tbl1 (id int,name char(50));
insert into tbl1 values (1,'Ouyang Feng');
从节点centos7.4-2
show slave status\G
Read_Master_Log_Pos: 882 数据已经复制过来
Seconds_Behind_Master: 0
use mydb
show tables;
select * from tbl1; 数据ok
6 恢复初始状态
centos7.4和centos7.4-2
systemctl stop mariadb.service
rm -rf /var/lib/mysql/*
主主复制 互为主从 双主复制
centos7.4 192.168.1.5 node1
centos7.4-2 192.168.1.6 node2
centos7.4
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 1
log-bin = master-log
relay-log = relay-log
skip_name_resolve = on
auto_increment_offset = 1 从几增长
auto_increment_increment = 2 加几
systemctl start mariadb.service
mysql
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
flush privileges;
show master status; 507位置
centos7.4-2
[mysqld]
server-id = 7
log-bin = master-log
relay-log = relay-log
skip_name_resolve = on
auto_increment_offset = 2
auto_increment_increment = 2
systemctl start mariadb.service
mysql
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
flush privileges;
show master status; 507位置
centos7.4-2
node1是node2的主
change master to master_host='192.168.1.5',master_user='repluser',master_password='replpass',master_log_file='master-log.000003',master_log_pos=507;
show slave status\G
centos7.4
node1是node2的从
change master to master_host='192.168.1.6',master_user='repluser',master_password='replpass',master_log_file='master-log.000003',master_log_pos=507;
show slave status\G
centos7.4和centos7.4-2
start slave;
show slave status\G
Slave_IO_Running: Yes
Slave_SQL_Running: Yes
tail /var/log/mariadb/mariadb.log 启动的线程出现在错误日志中
centos7.4
create database mydb;
centos7.4-2
show databases;
use mydb
create table tbl1 (id int unsigned auto_increment primary key,name char(50));
centos7.4
use mydb
show tables;
desc tbl1;
insert into tbl1 (name) values ('Jia Baoyu'),('Sun Erniang');
select * from tbl1; 显示id为1和3
centos7.4-2
select * from tbl1; 显示id为1和3
insert into tbl1 (name) values ('Lin Chong'),('Sun Houzi');
select * from tbl1; 显示id为1/3/4/6;跳过了id=2,出现间隙
centos7.4
select * from tbl1; 跳过了id=2,也出现间隙
centos7.4和centos7.4-2
systemctl stop mariadb.service
rm -rf /var/lib/mysql/*
恢复初始状态
主从复制 从节点添加读锁--不允许写操作
主节点centos7.4
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 1
log-bin = master-log
skip_name_resolve = on
systemctl start mariadb.service
mysql
show master status; 位置245
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
最小权限--192.168.1.6
flush privileges;
select @@global.read_only; 显示0--off
show master status; 位置497
从节点centos7.4-2
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 7
relay-log = relay-log
skip_name_resolve = on
read_only = on 只读选项
systemctl restart mariadb.service
mysql
show global variables like 'read_only'; 显示on
从节点centos7.4-2
change master to master_host='192.168.1.5',master_user='repluser',master_password='replpass',master_log_file='master-log.000003',master_log_pos=497;
start slave;
show slave status\G
主节点centos7.4
create database mydb;
use mydb
create table tbl1 (id int unsigned,name char(30));
从节点centos7.4-2
use mydb
show tables;
desc tbl1;
主节点centos7.4
grant select,update,create,drop on testdb.* to 'test'@'192.168.1.%' identified by 'testpass';
flush privileges;
mysql -utest -ptestpass -h192.168.1.5
create database testdb; 主节点上可修改数据
use testdb
create table t1 (name char(30));
从节点centos7.4-2
use testdb
show tables;
主节点centos7.4
mysql -utest -ptestpass -h192.168.1.6 连接至从节点ok
show databases;
use testdb
show tables;
insert into t1 values ('Hello');
显示"running with the --read-only option so it cannot execute this statement"
select * from t1; 连接至从节点上--写不可以,读可以(非super权限的账号)
图1
image.png
半同步复制 如上图1
需要安装插件来实现半同步复制
主节点centos7.4
rpm -ql mariadb-server
/usr/lib64/mysql/plugin/semisync_master.so 半同步主节点插件
/usr/lib64/mysql/plugin/semisync_slave.so 半同步从节点插件
设置为同步的从节点必须安装
设置为异步的从节点不安装
mysql
show plugins; 启用的插件
help install plugin
install plugin rpl_semi_sync_master soname 'semisync_master';
rpl_semi_sync_master 插件名
soname 模块名
show plugins; 显示rpl_semi_sync_master
show global variables like 'rpl_semi_%';
set @@global.rpl_semi_sync_master_enabled=on;
show global variables like 'rpl_semi_%'; 显示为on
rpl_semi_sync_master_timeout 从节点同步时长超过此时间(ms),即降级为异步
从节点centos7.4-2
mysql
install plugin rpl_semi_sync_slave soname 'semisync_slave';
show plugins; 显示rpl_semi_sync_slave
show global variables like 'rpl_semi_%';
set @@global.rpl_semi_sync_slave_enabled=on;
show global variables like 'rpl_semi_%'; 显示为on
主节点centos7.4
show global status like 'rpl_semi_%';
Rpl_semi_sync_master_clients 有几个半同步的客户端
从节点centos7.4-2
stop slave io_thread;
start slave io_thread;
主节点centos7.4
show global status like 'rpl_semi_%';
Rpl_semi_sync_master_clients 显示为1
非事务型
Rpl_semi_sync_master_net_avg_wait_time 平均等待时长
Rpl_semi_sync_master_net_wait_time 等待时长
Rpl_semi_sync_master_net_waits 等待几次
事务型
Rpl_semi_sync_master_tx_avg_wait_time
Rpl_semi_sync_master_tx_wait_time
Rpl_semi_sync_master_tx_waits
use mydb
show tables;
desc tbl1;
insert into tbl1 values (1,'Yang Guo'),(2,'Xiao Longnv');
insert into tbl1 values (3,'Xu Zhu'),(4,'Qiao Feng');
show global status like 'rpl_semi_%'; 数值发生变化
可以看出为了实现半同步复制,需要付出的时间代价
Rpl_semi_sync_master_net_wait_time 包含 Rpl_semi_sync_master_tx_wait_time
Rpl_semi_sync_master_net_wait_time 整体的时长
Rpl_semi_sync_master_tx_wait_time 事务的时长
从节点centos7.4-2
use mydb
show tables;
select * from tbl1;
10个从节点--2个设置为半同步--根据需要:同步客户端越少越好
同一个机柜内的设置为半同步,跨机柜做异步;
带宽充足--做同步,其他做异步;
复制过滤器
主服务器上过滤--可能丢失数据
从服务器上过滤--io增大--建议
参考文档
从节点centos7.4-2
show slave status\G
Replicate_Do_DB:
Replicate_Ignore_DB:
Replicate_Do_Table:
Replicate_Ignore_Table:
Replicate_Wild_Do_Table:
Replicate_Wild_Ignore_Table:
vim /etc/my.cnf.d/server.cnf
[mysqld]中添加选项
replicate_do_db = hidb 多个表用逗号或空格隔开
systemctl restart mariadb.service
show slave status\G 显示Replicate_Do_DB: hidb,线程自动启动(可以设置为关闭)
主节点centos7.4
create database hidb; 有延迟
从节点重启后,rpl_semi_sync_slave_enabled参数为off
从节点centos7.4-2
select @@global.rpl_semi_sync_slave_enabled; 显示为0
show databases; 显示hidb
主节点centos7.4
use mydb
show tables;
create table tbl2 (name varchar(30));
show tables; 显示tbl2
从节点centos7.4-2
show tables; 未显示tbl2,过滤后,仅同步hidb到从节点
偶尔会用到过滤
图1:PXC:Percona XtraDB Cluster
image.png复制的监控和维护--更多内容,参考文档
主节点centos7.4
help purge
PURGE BINARY LOGS TO 'mysql-bin.010'; 某文件(序号)之前的内容都清除
PURGE BINARY LOGS BEFORE '2008-04-02 22:46:26'; 某时间点之前的内容都清除
show binary logs; 显示master-log.000001/2/3
如果master-log.000003之前的内容都不需要了,就清理掉
purge binary logs to 'master-log.000003'; 只显示master-log.000003,1和2被清理了
如果都清理掉了,就恢复不了;
一定要复制一份,移到其他磁盘保存下来,以备不时之需;
purge命令不能随便尝试
ls /var/lib/mysql/ master-log.000003之前的内容被清理了
cat /var/lib/mysql/master-log.index 只有"./master-log.000003"
PXC:Percona XtraDB Cluster 如上图1
复制集群 多主节点集群 主从复制架构 不依赖二进制日志
参考文档
mariadb-cluster 也有类似功能--但是需要第三方插件--需要下载,系统不自带
图1:ProxySQL
image.png主从复制的读写分离
其他中间件参考文档,此处仅介绍ProxySQL
ProxySQL
下载:http://www.proxysql.com/
centos7.4--主节点--192.168.1.5
centos7.4-2--从节点1--192.168.1.6
centos7.4-3--从节点2--192.168.1.7
centos7.4-4--ProxySQL节点--192.168.1.8
1 同步时间
2 安装mariadb-server
centos7.4/centos7.4-2/centos7.4-3
yum -y install mariadb-server (centos7.4-4先不安装)
3 centos7.4--主节点
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 1
log-bin = master-log
skip_name_resolve = on
innodb_file_per_table = on
sync_binlog = 1
systemctl start mariadb.service; ss -ntl
mysql
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
flush privileges;
show master status;
4 centos7.4-2--从节点1和centos7.4-3--从节点2
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 2/3 2--从节点1;3--从节点2;
relay-log = relay-log
skip_name_resolve = on
innodb_file_per_table = on
read_only = on
systemctl start mariadb.service; ss -ntl
mysql
change master to master_host='192.168.1.5',master_user='repluser',master_password='replpass',master_log_file='master-log.000003',master_log_pos=497;
start slave;
show slave status\G
5 测试
centos7.4--主节点
create database hidb;
centos7.4-2--从节点1和centos7.4-3--从节点2
show databases; 出现hidb
6 安装ProxySQL
授权用户
centos7.4--主节点
grant all on *.* to 'proxysql'@'192.168.1.%' identified by 'proxypass';
flush privileges;
centos7.4-2--从节点1和centos7.4-3--从节点2
show grants for 'proxysql'@'192.168.1.%'; 已经同步过来
配置ProxySQL
centos7.4-4--ProxySQL节点
rz 上传proxysql-1.3.6-1-centos7.x86_64.rpm
yum -y install ./proxysql-1.3.6-1-centos7.x86_64.rpm
rpm -ql proxysql
cp /etc/proxysql.cnf{,.bak}
vim /etc/proxysql.cnf
admin_variables中定义
mysql_ifaces="127.0.0.1:6032;/tmp/proxysql_admin.sock" 去掉注释
refresh_interval=2000 去掉注释
debug=true 去掉注释
mysql_variables中定义
interfaces="0.0.0.0:3306;/tmp/mysql.sock" mysql.sock在/tmp下
因为是代理mysql的,所以监听在3306上,更易于访问
default_schema="hidb"
mysql_servers中的定义
{
address = "192.168.1.5"
port = 3306
hostgroup = 0
status = "ONLINE"
weight = 1
compression = 0
},
{
address = "192.168.1.6"
port = 3306
hostgroup = 1
status = "ONLINE"
weight = 1
compression = 0
},
{
address = "192.168.1.7"
port = 3306
hostgroup = 1
status = "ONLINE"
weight = 1
compression = 0
}
mysql_users中的定义
{
username = "proxysql"
password = "proxysqlpass"
default_hostgroup = 0
active = 1
}
mysql_replication_hostgroups中定义
{
writer_hostgroup=0
reader_hostgroup=1
comment="repl cluster 1"
}
service proxysql start 可使用service命令;ss -ntl 3306端口--4个
yum -y install mariadb-server
mysql 不能连接,mysql.sock文件在/tmp目录下(/etc/proxysql.cnf配置文件定义)
ls /tmp
mysql -S /tmp/mysql.sock -uproxysql -pproxypass
show databases;
use hidb
create table t1 (id int,name char(30));
show tables;
insert into t1 values (1,'tom');
insert into t1 values (2,'jerry');
select * from t1;
centos7.4和centos7.4-2和centos7.4-3
show tables from hidb; 都有
select * from hidb.t1; 都有
centos7.4-2
create database db2;
centos7.4-3
create database db3;
centos7.4-4
show databases; 无内容--配置文件中默认是0组
vim /etc/proxysql.cnf
mysql_users中的定义
{
username = "proxysql"
password = "proxysqlpass"
default_hostgroup = 1 0改为1
active = 1
}
service proxysql restart
mysql -S /tmp/mysql.sock -uproxysql -pproxypass
show databases; 还是没有node2/3db,仍是以主节点为主
service proxysql status;service proxysql stop 为MHA准备
chkconfig proxysql off
图1:减轻主节点的负载(写操作)
image.png图2:DRBD:分布式的复制块设备
image.png图3:管理节点和代理(数据)节点
image.png图4:管理节点可管理多个主从复制集群
image.png主节点down机--高可用
解决方案1--如上图1
解决方案2--如上图2 drbd:Distributed Replicated Block Device--分布式的复制块设备
解决方案3--如上图3 MHA 详情参考文档
从节点1提升为新的主节点--但仅有一部分数据
从节点1--需要把从其他节点同步过来的数据合并起来--避免数据不一致
故障主节点--使用"漂移IP"--主节点故障,IP漂移到新的主节点
各个从节点"change master to..."要指向"漂移IP"
前端--读写分离器配置--也要使用"漂移IP"
判定谁代替主节点(优先级提升)+监测主节点down机+IP漂移至从节点(脚本)
MHA--无IP漂移功能--keepalived可代替
配置1主n备
管理节点和代理(数据)节点 如上图3
如何获取合并数据
每个节点:中继日志(禁止自动清理)+启动二进制日志(很有可能成为新的主节点)+read only(被提升为主节点/管理节点通过agent将read only自动关闭)
管理节点--可管理多个主从复制集群--可为每个集群提供一个单独的定义--如上图4
一个application--代表一个集群
从节点切换为主节点时,需要有权限读取各个从节点的中继日志,且ssh无密钥连接
不能有认证
某个节点生成一对密钥--复制给其他节点--即可互通了
MHA
centos7.4--主节点--192.168.1.5
centos7.4-2--从节点1--192.168.1.6
centos7.4-3--从节点2--192.168.1.7
centos7.4-4--管理节点--192.168.1.8
根据前面的ProxySQL实验做一下调整即可
vim /etc/hosts 确保可通过主机名解析
192.168.1.5 centos7.4.fgq.com
192.168.1.6 centos7.4-2.fgq.com
192.168.1.7 centos7.4-3.fgq.com
192.168.1.8 centos7.4-4.fgq.com
centos7.4--主节点
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 1
log-bin = master-log
relay-log = relay-log 添加中继日志
skip_name_resolve = on
innodb_file_per_table = on
sync_binlog = 1
systemctl restart mariadb.service;ss -ntl
centos7.4-2和centos7.4-3--从节点
vim /etc/my.cnf.d/server.cnf
[mysqld]
server-id = 2
log-bin = master-log 启动二进制日志
relay-log = relay-log
skip_name_resolve = on
innodb_file_per_table = on
read_only = on
relay_log_purge = 0 启动清理中继日志
systemctl restart mariadb.service;ss -ntl
centos7.4--主节点
创建管理权限的用户账号
mysql
grant all on *.* to 'mhaadmin'@'192.168.1.%' identified by 'mhapass';
flush privileges;
centos7.4-2和centos7.4-3--从节点
mysql
show grants for 'mhaadmin'@'192.168.1.%'; 从节点自动同步管理权限的用户账号
centos7.4-4--管理节点
安装MHA
管理节点安装MHA的manager和node
主/从节点安装MHA的node
下载
https://github.com/yoshinorim/mha4mysql-manager
rpm文件夹--.spec文件--根据.spec文件自定义rpm包
https://github.com/yoshinorim/mha4mysql-manager/wiki/Downloads
直接下载rpm包
当前节点需要安装manager和node(非关键/可能用到其中的工具)
rz 上传mha4mysql-manager-0.56-0.el6.noarch.rpm和mha4mysql-node-0.56-0.el6.noarch.rpm
yum -y install ./mha4mysql-*.rpm 依赖epel很多模块/确保仓库ok
scp mha4mysql-node-0.56-0.el6.noarch.rpm centos7.4.fgq.com:/root/
for i in {-2,-3};do scp mha4mysql-node-0.56-0.el6.noarch.rpm centos7.4$i.fgq.com:/root/;done
centos7.4和centos7.4-2和centos7.4-3
yum -y install ./mha4mysql-node-0.56-0.el6.noarch.rpm
配置ssh互信--没有密码可互相通信
在一个主机上生成一对密钥,完成自己主机的认证,后将其复制到其他主机上
centos7.4-4--管理节点
ssh-keygen -t rsa -P '' 生成一对密钥
ssh-copy-id -i .ssh/id_rsa.pub root@centos7.4-4.fgq.com
ssh centos7.4-4.fgq.com 显示已连接
exit
复制密钥和认证文件给其他节点
centos7.4-2和centos7.4-3
mkdir .ssh centos7.4有此文件夹,就不要创建,否则就创建
centos7.4-4--管理节点
scp .ssh/id_rsa .ssh/authorized_keys centos7.4.fgq.com:/root/.ssh
for i in {-2,-3};do scp -p .ssh/id_rsa .ssh/authorized_keys root@centos7.4$i.fgq.com:/root/.ssh/;done
ssh centos7.4-3.fgq.com
ssh centos7.4-2.fgq.com
ssh centos7.4.fgq.com 不需要密码即可登陆
cat /etc/ssh/ssh_config
centos7.4
ssh centos7.4.fgq.com 第一次连接需要回答yes
cat /etc/ssh/ssh_config; man ssh
ssh -o StrictHostKeyChecking=no centos7.4-2.fgq.com 第一次直接连接/不回答yes
确保连接任何一个节点都ok,包括连接自己
定义集群
centos7.4-4
mkdir /etc/masterha 自己写配置文件
vim /etc/masterha/app1.cnf
[server default]
user=mhaadmin
password=mhapass
manager_workdir=/data/masterha/app1 此目录可自动创建
manager_log=/data/masterha/app1/manager.log
remote_workdir=/data/masterha/app1
ssh_user=root
repl_user=repluser 之前实验创建过的复制用户
repl_password=replpass
ping_interval=1
[server1]
hostname=192.168.1.5
ssh_port=22
candidate_master=1
[server2]
hostname=192.168.1.6
ssh_port=22
candidate_master=1
[server3]
hostname=192.168.1.7
ssh_port=22
candidate_master=1
检测是否可正常连接
masterha_check_ssh --conf=/etc/masterha/app1.cnf
检测集群是否可正常使用
masterha_check_repl --conf=/etc/masterha/app1.cnf
显示Not OK--User repluser does not exist
之前实验时,主节点创建repluser,没有让从节点同步该sql语句
需要在主节点再创建一次,从节点会自动同步
centos7.4
grant replication client,replication slave on *.* to 'repluser'@'192.168.1.%' identified by 'replpass';
show grants for 'repluser'@'192.168.1.%';
centos7.4-2和centos7.4-3
show grants for 'repluser'@'192.168.1.%'; 已经同步过来了
centos7.4-4
masterha_check_repl --conf=/etc/masterha/app1.cnf 显示集群OK
[warning] master_ip_failover_script is not defined
自己写脚本--主节点down机,把主节点IP地址down掉,在新的主节点上把IP加上
注意设置主从时,需要change to 到漂移的IP上
[warning] shutdown_script is not defined
脚本--停止原来的主节点或把主节点切换为从节点,避免脑裂
启动服务
masterha_manager --conf=/etc/masterha/app1.cnf
ps -aux 显示perl /usr/bin/masterha_manager...当前处于运行状态
masterha_check_status --conf=/etc/masterha/app1.cnf 当前集群状态是否ok
故障测试
centos7.4
killall mysqld mysqld_safe
ps aux |grep msyqld 已经kill掉了
rm -rf /var/lib/mysql/*
centos7.4-4
执行"masterha_manager --conf=/etc/masterha/app1.cnf"命令的窗口会显示信息并退出
架构已经改变,需要重新设定并启动
masterha_check_repl --conf=/etc/masterha/app1.cnf
显示Not OK,显示Current Alive Master: 192.168.1.6 已经切换
centos7.4-2--192.168.1.6
show global variables like 'read_only'; 显示off,变为主节点后,自动关闭只读限制
故障的主节点要修复
启动--在新的主节点上做一次备份,恢复到centos7.4--node1上
在node1上,指向centos7.4-2--node2(此时为主节点),node1为从节点
再次启动MHA:masterha_manager --conf=/etc/masterha/app1.cnf
centos7.4-2 新主节点
mysqldump -x -R -E --triggers --all-databases --master-data=2 --flush-logs > /tmp/alldatabases.sql
centos7.4 故障主节点
vim /etc/my.cnf.d/server.cnf
在[mysqld]中添加信息:read_only = on
systemctl start mariadb.service
centos7.4-2
scp /tmp/alldatabases.sql centos7.4.fgq.com:/root/
centos7.4
mysql < /root/alldatabases.sql
mysql
show databases; 数据恢复
命令行:head -30 /root/alldatabases.sql 备份时,处于哪个日志文件的哪个位置
显示CHANGE MASTER TO MASTER_LOG_FILE='master-log.000002', MASTER_LOG_POS=245;
change master to change master to master_host='192.168.1.6',master_user='repluser',master_password='replpass',master_log_file='master-log.000002',master_log_pos=245;
start slave;
show slave status\G
centos7.4-4 管理节点
检测集群是否ok
masterha_check_repl --conf=/etc/masterha/app1.cnf
显示OK 192.168.1.6(192.168.1.6:3306) (current master)
masterha_manager --conf=/etc/masterha/app1.cnf
nohup masterha_manager --conf=/etc/masterha/app1.cnf &> /data/masterha/app1/manager.log &
&--后台运行,nohup--当前终端关闭,此程序也不关闭
如果主节点down机,此程序会关闭
ps aux; jobs -l
centos7.4-2 新主节点down机
killall mysqld mysqld_safe
centos7.4-4
回车几次,就可以看到nohup程序关闭
masterha_check_repl --conf=/etc/masterha/app1.cnf 显示Not OK
网友评论