共计 18843 个字符,预计需要花费 48 分钟才能阅读完成。
本文介绍了 Group Replication 的两种工作模式的架构介绍。
并详细介绍了 Single-Master Mode 的部署过程,以及如何切换到Multi-Master Mode。
当然,文末给出了 Group Replication 的配置要求和一些限制。
〇 结构介绍
在 2016 年 12 月发布的 5.7.17 版本的 MySQL,甲骨文宣布 Group Replication 已经 GA。
Group Replication(下简称 GR)有两个工作模式,分别为 S ingle-Master Mode 与 Multi-Master Mode:
Single-Master Mode 的failover 图:
只有 primary 成员 可读写,而其他的节点为只读,在 primary 成员发生故障时,将会有其他成员顶替成 primary。
Multi-Master Mode的 failover 图:
所有的成员均可读可写。
关于脑裂问题,可发现 MySQL Group Replication 与 MongoDB Relicate Set有相似之处:
和 MongoDB 的 Relicate Set 相近,其读写库 类似于 Primary,只读库类似于Secondary。
(下图来自 MySQL 官方)
(下图来自 MongoDB 3.4 Manual)
〇 部署
测试实例数量:3 台
版本:MySQL 5.7.17
安装(此处用的是二进制包安装)
mysql-5.7.17-linux-glibc2.5-x86_64.tar.gz
创建数据目录及日志目录:
- mkdir –p /data/mysql57/mysql3306
- mkdir –p /data/mysql57/mysql3307
- mkdir –p /data/mysql57/mysql3308
- mkdir –p /data/mysql57/logs/3306
- mkdir –p /data/mysql57/logs/3307
- mkdir –p /data/mysql57/logs/3308
解压二进制包并将其设置为 basedir:
- mv mysql–5.7.17–linux–glibc2.5–x86_64.tar.gz /data/mysql57
- cd /data/mysql57
- tar zxvf mysql–5.7.17–linux–glibc2.5–x86_64.tar.gz
- mv mysql–5.7.17–linux–glibc2.5–x86_64 mysql–basedir
〇 添加第一台实例:
添加 3306 实例的配置文件:
- vim /data/mysql57/mysql3306/3306.cnf
- [client]
- prompt = “(\u@\h) [\d]> “
- [mysqld]
- server_id = 3306
- user = mysql
- port = 3306
- socket = /tmp/mysql3306.sock
- basedir = /data/mysql57/mysql-basedir
- datadir = /data/mysql57/mysql3306
- pid-file = /data/mysql57/mysql3306/3306.pid
- log–error = /data/mysql57/logs/3306/error-log
- log–bin = /data/mysql57/logs/3306/binlog
- log–bin–index = /data/mysql57/logs/3306/binlog.index
- relay-log = /data/mysql57/logs/3306/relaylog
- relay-log–index = /data/mysql57/logs/3306/relaylog.index
- master_info_repository = TABLE
- relay_log_info_repository = TABLE
- log_slave_updates = ON
- binlog_checksum = NONE
- binlog_format = ROW
- transaction_isolation = READ-COMMITTED
- gtid_mode = ON
- enforce_gtid_consistency = ON
- # GR 配置项 其中 loose 前缀表示若 Group Replication plugin 未加载 mysql server 仍继续启动
- transaction_write_set_extraction = XXHASH64
- loose-group_replication_group_name = “aaaaaaaa-aaaa-aaaa-aaaa-aaaaaaaaaaaa“ # 组名,此处可拿 select uuid(); 生成
- loose-group_replication_start_on_boot = off # 在 mysqld 启动时不自动启动组复制
- loose-group_replication_local_address = “127.0.0.1:24901“
- loose-group_replication_group_seeds = “127.0.0.1:24901,127.0.0.1:24902,127.0.0.1:24903“
- loose-group_replication_bootstrap_group = off
初始化 3306 实例 datadir:
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3306.cnf ––initialize–insecure
启动 3306实例:
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3306.cnf &
通过 MySQL Client 进入第一个实例(密码为空)
- /data/mysql57/mysql–basedir/bin/mysql –uroot –p –S /tmp/mysql3306.sock
创建复制用户与授权,并让其 作为 group 的第一个成员:
- SET SQL_LOG_BIN=0;
- CREATE USER repl@‘%’;
- GRANT REPLICATION SLAVE ON *.* TO repl@‘%’ IDENTIFIED BY ‘repl@123’;
- FLUSH PRIVILEGES;
- SET SQL_LOG_BIN=1;
- CHANGE MASTER TO MASTER_USER=‘repl’, MASTER_PASSWORD=‘repl@123’ FOR CHANNEL ‘group_replication_recovery’;
安装 GR 插件:
- (root@localhost) [(none)]> INSTALL PLUGIN group_replication SONAME ‘group_replication.so’;
- Query OK, 0 rows affected (0.07 sec)
可以检查一下是否安装成功:
- (root@localhost) [(none)]> SELECT * FROM information_schema.plugins WHERE PLUGIN_NAME LIKE ‘%group%’\G
- *************************** 1. row ***************************
- PLUGIN_NAME: group_replication
- PLUGIN_VERSION: 1.0
- PLUGIN_STATUS: ACTIVE
- PLUGIN_TYPE: GROUP REPLICATION
- PLUGIN_TYPE_VERSION: 1.1
- PLUGIN_LIBRARY: group_replication.so
- PLUGIN_LIBRARY_VERSION: 1.7
- PLUGIN_AUTHOR: Oracle
- PLUGIN_DESCRIPTION: Group Replication (1.0.0)
- PLUGIN_LICENSE: GPL
- LOAD_OPTION: ON
- 1 row in set (0.00 sec)
开启第一个组复制:
- (root@localhost) [(none)]> SET GLOBAL group_replication_bootstrap_group=ON;
- Query OK, 0 rows affected (0.00 sec)
- (root@localhost) [(none)]> START GROUP_REPLICATION;
- Query OK, 0 rows affected (1.20 sec)
- # 启动组复制之后将 group_replication_bootstrap_group 设置为 OFF
- # This option must only be set on one server and only when starting the group for the first time or restarting the entire group. After the group has been bootstrapped, set this option to OFF. It should be set to OFF both dynamically and in the configuration files
- (root@localhost) [(none)]> SET GLOBAL group_replication_bootstrap_group=OFF;
- Query OK, 0 rows affected (0.01 sec)
检查一下组复制成员,其中 member_id 就是 @@server_uuid 的值
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 | ONLINE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 1 row in set (0.00 sec)
添加测试数据:
- (root@localhost) [(none)]> CREATE DATABASE test;
- Query OK, 1 row affected (0.00 sec)
- (root@localhost) [(none)]> USE test;
- Database changed
- (root@localhost) [test]> CREATE TABLE tb_test(id int PRIMARY KEY, name varchar(20)) CHARACTER SET utf8;
- Query OK, 0 rows affected (0.04 sec)
- (root@localhost) [test]> INSERT INTO tb_test VALUES(1,‘ 风暴之灵 ’);
- Query OK, 1 row affected (0.00 sec)
- (root@localhost) [test]> INSERT INTO tb_test VALUES(2,‘ 影之灵龛 ’);
- Query OK, 1 row affected (0.01 sec)
- (root@localhost) [test]> UPDATE tb_test SET name=‘ 斯嘉蒂之眼 ’ WHERE id=2;
- Query OK, 1 row affected (0.02 sec)
- Rows matched: 1 Changed: 1 Warnings: 0
- (root@localhost) [test]> SELECT * FROM tb_test;
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 风暴之灵 |
- | 2 | 斯嘉蒂之眼 |
- +––––+–––––––––––––––––+
- 2 rows in set (0.00 sec)
〇 添加第二个实例(3307)
修改 3307 配置文件,将 3306 改成 3307,并且将 loose-group_replication_local_address 的端口从 24901 改成 24902:
- cp /data/mysql57/3306.cnf /data/mysql57/3307.cnf
- sed –i “s/3306/3307/g” /data/mysql57/3307.cnf
- sed –i “s/24901\”/24902\“/g” 3307.cnf
初始化 3307 实例:
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3307.cnf ––initialize–insecure
启动 3307 实例:
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3307.cnf &
通过 MySQL Client 进入 3307 实例:
- /data/mysql57/mysql–basedir/bin/mysql –uroot –p –S /tmp/mysql3307.sock
重复在 3306 实例的操作:
- SET SQL_LOG_BIN=0;
- CREATE USER repl@‘%’;
- GRANT REPLICATION SLAVE ON *.* TO repl@‘%’ IDENTIFIED BY ‘repl@123’;
- FLUSH PRIVILEGES;
- SET SQL_LOG_BIN=1;
- CHANGE MASTER TO MASTER_USER=‘repl’, MASTER_PASSWORD=‘repl@123’ FOR CHANNEL ‘group_replication_recovery’;
在 3307 实例上安装 GR 插件,开启组复制:
- (root@localhost) [(none)]> INSTALL PLUGIN group_replication SONAME ‘group_replication.so’;
- Query OK, 0 rows affected (0.00 sec)
- (root@localhost) [(none)]> START GROUP_REPLICATION;
- Query OK, 0 rows affected (5.61 sec)
检查一下成员状态:
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 | ONLINE |
- | group_replication_applier | 6bddae0d-eca1-11e6-b9d5-000c297f23b7 | sAno1y | 3307 | RECOVERING |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 2 rows in set (0.00 sec)
过了一阵子再检查,仍然是 RECOVERING。
再过一阵子检查,发现 member_state 被置为 ERROR:
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 6bddae0d-eca1-11e6-b9d5-000c297f23b7 | sAno1y | 3307 | ERROR |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 1 row in set (0.01 sec)
此时检查 3306 实例的组复制情况,发现检查不到另一个实例的信息了:
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 | ONLINE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 1 row in set (0.00 sec)
开多一个终端,检查 3307 实例的 error log 发现:
- 2017–02–07T12:06:21.674093Z 47 [ERROR] Slave I/O for channel ‘group_replication_recovery’: error connecting to master ‘repl@sAno1y:3306’ – retry–time: 60 retries: 1, Error_code: 2005
应该是解析的问题,修改 hosts 文件,在末尾加上主机名:
- [root@sAno1y 3307]# hostname
- sAno1y
- [root@sAno1y 3307]# cat /etc/hosts
- 127.0.0.1 localhost localhost.localdomain localhost4 localhost4.localdomain4 sAno1y
- ::1 localhost localhost.localdomain localhost6 localhost6.localdomain6 sAno1y
重新操作 3307 实例:
- (root@localhost) [(none)]> STOP GROUP_REPLICATION;
- Query OK, 0 rows affected (0.00 sec)
- (root@localhost) [(none)]> START GROUP_REPLICATION;
- Query OK, 0 rows affected (7.80 sec)
检查组复制状态,发现两个实例的状态均为 ONLINE 了:
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 | ONLINE |
- | group_replication_applier | 6bddae0d-eca1-11e6-b9d5-000c297f23b7 | sAno1y | 3307 | ONLINE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 2 rows in set (0.00 sec)
在 3307 上检查一下同步状态:
- (root@localhost) [(none)]> SELECT * FROM test.tb_test;
- +—-+—————–+
- | id | name |
- +—-+—————–+
- | 1 | 风暴之灵 |
- | 2 | 斯嘉蒂之眼 |
- +—-+—————–+
- 2 rows in set (0.00 sec)
〇添加 3308 实例:
修改 3308 配置文件:
- cp /data/mysql57/3306.cnf /data/mysql57/3308.cnf
- sed –i “s/3306/3308/g” 3308.cnf
- sed –i “s/24901\”/24093\“/g” 3308.cnf
然后初始化并启动 3308 实例:
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3308.cnf ––initialize–insecure
- /data/mysql57/mysql–basedir/bin/mysqld ––defaults–file=/data/mysql57/3308.cnf &
同样进入 3308 实例:
- /data/mysql57/mysql–basedir/bin/mysql –uroot –p –S /tmp/mysql3308.sock
在 3308 实例上重复操作:
- SET SQL_LOG_BIN=0;
- CREATE USER repl@‘%’;
- GRANT REPLICATION SLAVE ON *.* TO repl@‘%’ IDENTIFIED BY ‘repl@123’;
- FLUSH PRIVILEGES;
- SET SQL_LOG_BIN=1;
- CHANGE MASTER TO MASTER_USER=‘repl’, MASTER_PASSWORD=‘repl@123’ FOR CHANNEL ‘group_replication_recovery’;
继续重复操作,安装 GR 插件并启动它:
- INSTALL PLUGIN group_replication SONAME ‘group_replication.so’;
- START GROUP_REPLICATION;
最后再检查一下组复制成员的状态:
- (root@localhost) [(none)]> SELECT * FROM performance_schema.replication_group_members;
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- | group_replication_applier | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 | ONLINE |
- | group_replication_applier | 6bddae0d-eca1-11e6-b9d5-000c297f23b7 | sAno1y | 3307 | ONLINE |
- | group_replication_applier | 6ce8c980-ed4a-11e6-bf00-000c297f23b7 | sAno1y | 3308 | ONLINE |
- +–––––––––––––––––––––––––––+––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+––––––––––––––+
- 3 rows in set (0.00 sec)
当然在 3308 实例上也已将 3306 的事务 apply 过来了:
- (root@localhost) [(none)]> SELECT * FROM test.tb_test;
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 风暴之灵 |
- | 2 | 斯嘉蒂之眼 |
- +––––+–––––––––––––––––+
- 2 rows in set (0.00 sec)
root@localhost 用户在上述操作中为空密码,可以给 root@localhost 加个密码……
因为三个实例都在一个 GR 组里,所以对 3306 实例操作就行了:
- /data/mysql57/mysql–basedir/bin/mysql –uroot –p –S /tmp/mysql3306.sock –e “ALTER USER root@localhost IDENTIFIED BY ‘root123’;”
当然 ALTER 操作会被记录到 3306 的 binlog 里,并 同步到 3307 和 3308 实例上。
可以查看一下三台实例的 read_only 和 super-read-only 值:
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3306.sock -e “SELECT @@read_only, @@super_read_only“;
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +–––––––––––––+–––––––––––––––––––+
- | @@read_only | @@super_read_only |
- +–––––––––––––+–––––––––––––––––––+
- | 0 | 0 |
- +–––––––––––––+–––––––––––––––––––+
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3307.sock -e “SELECT @@read_only, @@super_read_only“;
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +–––––––––––––+–––––––––––––––––––+
- | @@read_only | @@super_read_only |
- +–––––––––––––+–––––––––––––––––––+
- | 1 | 1 |
- +–––––––––––––+–––––––––––––––––––+
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3308.sock -e “SELECT @@read_only, @@super_read_only“;
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +–––––––––––––+–––––––––––––––––––+
- | @@read_only | @@super_read_only |
- +–––––––––––––+–––––––––––––––––––+
- | 1 | 1 |
- +–––––––––––––+–––––––––––––––––––+
可以发现只有 3306 实例也就是第一个实例属于可写实例,而 3307 和 3308 均为 read-only 模式。
决定因素为第一个加入该 GR 组的成员,之后加入该 GR 组的均为 ro,在该模式与 MongoDB Replicate Set 很相似。
当然如果要确定哪一个成员是 primary,可以在三个成员中的任意一个执行:
- SELECT b.member_id, b.member_host, b.member_port
- FROM performance_schema.global_status a
- JOIN performance_schema.replication_group_members b
- ON a.variable_value = b.member_id
- WHERE a.variable_name= ‘group_replication_primary_member’;
- # 输出结果:
- +––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+
- | member_id | member_host | member_port |
- +––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+
- | 3dc9cf4a-ec61-11e6-bdf3-000c297f23b7 | sAno1y | 3306 |
- +––––––––––––––––––––––––––––––––––––––+–––––––––––––+–––––––––––––+
- 1 row in set (0.00 sec)
至此,Group Replication 默认的 single-master mode 已经搭建完毕。
〇 将 S ingle-Master Mode 修改为 Multi-Master Mode
如果要将 Single-Master Mode 修改为 Multi-Master Mode,也比较简单。
考虑到此时的 Primary 成员是 3306,并且假定 3306 实例在对外提供写服务,我这边的操作如下:
首先停掉两个 secondary 的组复制, 在 3307 和 3308 实例上操作:
- STOP GROUP_REPLICATION;
- SET GLOBAL group_replication_single_primary_mode=FALSE;
- SET GLOBAL group_replication_enforce_update_everywhere_checks=TRUE;
再在 3306 实例上重复以上操作:
- STOP GROUP_REPLICATION;
- SET GLOBAL group_replication_single_primary_mode=FALSE;
- SET GLOBAL group_replication_enforce_update_everywhere_checks=TRUE;
然后在 3306 上作为第一个成员启动组复制:
- (root@localhost) [(none)]> SET GLOBAL group_replication_bootstrap_group=on;
- Query OK, 0 rows affected (0.00 sec)
- (root@localhost) [(none)]> START GROUP_REPLICATION;
- Query OK, 0 rows affected (1.05 sec)
- (root@localhost) [(none)]> SET GLOBAL group_replication_bootstrap_group=off;
- Query OK, 0 rows affected (0.00 sec)
在停启组复制的 过程中,3306 实例仍对外提供服务,此处模拟修改:
- (root@localhost) [(none)]> UPDATE test.tb_test SET name=‘ 灵魂守卫 ’ WHERE id=1;
- Query OK, 1 row affected (0.02 sec)
- Rows matched: 1 Changed: 1 Warnings: 0
- (root@localhost) [(none)]> INSERT INTO test.tb_test VALUES(3,‘ 幻影斧 ’);
- Query OK, 1 row affected (0.00 sec)
- (root@localhost) [(none)]> SELECT * FROM test.tb_test;
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 灵魂守卫 |
- | 2 | 斯嘉蒂之眼 |
- | 3 | 幻影斧 |
- +––––+–––––––––––––––––+
- 3 rows in set (0.00 sec)
再 3307 和 3308 两个实例上分别开启组复制:
- START GROUP_REPLICATION;
并 检查 3307 和 3308是否将 3306 的事务应用过来:
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3307.sock -e “START GROUP_REPLICATION;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- [root@sAno1y mysql57]#
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3308.sock -e “START GROUP_REPLICATION;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3307.sock -e “SELECT * FROM test.tb_test;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 灵魂守卫 |
- | 2 | 斯嘉蒂之眼 |
- | 3 | 幻影斧 |
- +––––+–––––––––––––––––+
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3308.sock -e “SELECT * FROM test.tb_test;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 灵魂守卫 |
- | 2 | 斯嘉蒂之眼 |
- | 3 | 幻影斧 |
- +––––+–––––––––––––––––+
当然可以看到,在 3306 上做的修改,在 3307 和 3308 开启组复制之后也已经同步过来了。
那么再检查一下 3307 和 3308 是否可写:
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3307.sock -e “SELECT @@read_only, @@super_read_only;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +–––––––––––––+–––––––––––––––––––+
- | @@read_only | @@super_read_only |
- +–––––––––––––+–––––––––––––––––––+
- | 0 | 0 |
- +–––––––––––––+–––––––––––––––––––+
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3308.sock -e “SELECT @@read_only, @@super_read_only;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +–––––––––––––+–––––––––––––––––––+
- | @@read_only | @@super_read_only |
- +–––––––––––––+–––––––––––––––––––+
- | 0 | 0 |
- +–––––––––––––+–––––––––––––––––––+
显然和 Single-Master Mode 不一样的是,除了 3306 实例,另外两个成员也就是 3307 和 3308 实例均为可写成员了。
也就是所谓的Multi-Master Mode。
当然可以测试一下:
在 3307 实例上做 insert,在 3308 实例上 update,最后在 3306 上查询:
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3307.sock -e “INSERT INTO test.tb_test VALUES(4,‘ 吸血面具 ’)“;
- mysql: [Warning] Using a password on the command line interface can be insecure.
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3308.sock -e “UPDATE test.tb_test SET name=‘ 撒旦之邪力 ’ WHERE id=4;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- [root@sAno1y mysql57]# /data/mysql57/mysql-basedir/bin/mysql -uroot -proot123 -S /tmp/mysql3306.sock -e “SELECT * FROM test.tb_test;“
- mysql: [Warning] Using a password on the command line interface can be insecure.
- +––––+–––––––––––––––––+
- | id | name |
- +––––+–––––––––––––––––+
- | 1 | 灵魂守卫 |
- | 2 | 斯嘉蒂之眼 |
- | 3 | 幻影斧 |
- | 4 | 撒旦之邪力 |
- +––––+–––––––––––––––––+
至此,已经成功将 Single-Master Mode 修改为 Multi-Master Mode。
P.S. 在多主模式中,已经不能通过下述 SQL 来查询 primary member 是哪一台实例了……虽然不明白为毛,可能在后续版本会改进???(猜测)
但总之在多主模式中,每一台status 为online 的成员都是 primary。
- SELECT b.member_id, b.member_host, b.member_port
- FROM performance_schema.global_status a
- JOIN performance_schema.replication_group_members b
- ON a.variable_value = b.member_id
- WHERE a.variable_name= ‘group_replication_primary_member’;
总之……看起来很好用的样子。
从零开始搭建 Multi-Master Mode 的 GR 同样也很简单,可以参考:
http://mysqlhighavailability.com/mysqlha/gr/doc/getting_started.html
两种工作模式在配置参数上的核心差别为:
- loose–group_replication_single_primary_mode=FALSE
- loose–group_replication_enforce_update_everywhere_checks=TRUE
- (single–master mode 这俩个参数的值为 TRUE 和 FALSE)
〇 要求和限制
仅可用于 InnoDB 存储引擎(需要事务的支持和行级锁)
表必须有主键(创建无主键的表不会报错,但在插入数据的时候会抛出:ERROR 3098 (HY000): The table does not comply with the requirements by an external plugin.)
必须启用 GTID
必须开启二进制日志,并且其格式必须为 ROW(binlog_format=row)
冲突 DDl、DML 只能在同一成员上执行成功
在多主结构中,不完全支持外键(单主结构中是没有问题的)
不支持 serializable 的事务隔离级别
只支持 IPv4,并且需要低延迟,高带宽的网络环境
GR 最大支持 9 个成员
复制信息元数据必须存在系统表(master-info-repository=TABLE、relay-log-info-repository=TABLE)
二进制日志 checksums 必须关闭(binlog-checksum=NONE)
不支持 savepoint 的使用
〇 参考文档:
MySQL 5.7 Reference Manual – 19.2 Group Replication
马楚成 – 使用群组复制实现 MySQL 高可用性 (https://www.mysql.com/news-and-events/web-seminars/mysql-cluster-ha-group-replication2-zh/)
mysqlha 组文档 Docs ? Requirements and Limitations
本文永久更新链接地址:http://www.linuxidc.com/Linux/2017-03/142378.htm