全同步是主从同步的增强。
因为主从同步虽可以实现一主多从,但它的局限在于只有在主数据库上写的时候从数据库才会做数据备份,而在从数据库做出改变时,主数据库不会记录相应的改变。
然而,全同步出现了,它可以是只要在一个数据库做出改变,所以其它在同组的数据库也会改变,同组的数据库没有等级之分。可以理解为“同组数据库之间数据相等”。
那么如何实现数据库的全同步复制呢?
实验环境:
redhat6.5操作系统;
主机:server1-----------172.25.254.1
server2-----------172.25.254.2
server3------------172.25.254.3
我们可以在主从复制的基础上进行此实验。(因为两者所需安装数据库的包一样)。或者自己重新安装包皆可,这里不再赘述,有兴趣者可参考主从复制具体过程:点击此处查看。
在server1主机上:
(1)停止数据库,并删除生成的文件。
[root@server1 ~]# /etc/init.d/mysqld stop
[root@server1 ~]# cd /var/lib/mysql
[root@server1 mysql]# rm -rf *
(2)修改mysql的配置文件
root@server1 mysql]# vim /etc/my.cnf
###############################################################
server_id=3
gtid_mode=ON
enforce_gtid_consistency=ON
master_info_repository=TABLE
relay_log_info_repository=TABLE
binlog_checksum=NONE
log_slave_updates=ON
log_bin=binlog
binlog_format=ROW
transaction_write_set_extraction=XXHASH64
loose-group_replication_group_name="b9e8cc0f-9c7a-11e8-ac38-52540025fd63" ##uuid 可以在数据库中用select uuid();查看
loose-group_replication_start_on_boot=off
loose-group_replication_local_address="172.25.5.3:24901"
loose-group_replication_group_seeds="172.25.5.3:24901,172.25.5.4:24901,172.25.5.5:24901"
loose-group_replication_bootstrap_group=off
loose-group_replication_single_primary_mode=off
loose-group_replication_enforce_update_everywhere_checks=on
loose-group_replication_ip_whitelist="172.25.5.0/24,127.0.0.1/8"
注意:修改配置文件结束后,应开启数据库使修改生效。
(3)以原始密码登录数据库并修改密码;
[root@server1 mysql]# grep password /var/log/mysqld.log ##查找原始密码
mysql> alter user root@localhost identified by 'Chao@199512'; #用原始密码登录后,alter命令修改数据库密码
Query OK, 0 rows affected (0.05 sec)
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| mysql |
| performance_schema |
| sys |
+--------------------+
4 rows in set (0.00 sec)
注意:用原始密码虽可以进入数据库,但不能对数据库进行操作的。需修改密码之后才可以。
(4)对数据库进行具体配置
mysql> SET SQL_LOG_BIN=0;
Query OK, 0 rows affected (0.00 sec)
mysql> GRANT REPLICATION SLAVE ON *.* TO rpl_user@'%' identified by 'Chao@199512';
Query OK, 0 rows affected, 1 warning (0.00 sec)
mysql> FLUSH PRIVILEGES;
Query OK, 0 rows affected (0.01 sec)
mysql> reset master; ###至关重要,是清空日至信息,不然会报错。
Query OK, 0 rows affected (0.45 sec)
mysql> SET SQL_LOG_BIN=1;
Query OK, 0 rows affected (0.00 sec)
mysql> CHANGE MASTER TO MASTER_USER='rpl_user', MASTER_PASSWORD='Chao@199512' FOR CHANNEL 'group_replication_recovery';
Query OK, 0 rows affected, 2 warnings (0.61 sec)
mysql> INSTALL PLUGIN group_replication SONAME 'group_replication.so';
Query OK, 0 rows affected (0.51 sec)
mysql> show plugins;
| ARCHIVE | ACTIVE | STORAGE ENGINE | NULL | GPL |
| BLACKHOLE | ACTIVE | STORAGE ENGINE | NULL | GPL |
| partition | ACTIVE | STORAGE ENGINE | NULL | GPL |
| ngram | ACTIVE | FTPARSER | NULL | GPL |
| validate_password | ACTIVE | VALIDATE PASSWORD | validate_password.so | GPL |
| group_replication | ACTIVE | GROUP REPLICATION | group_replication.so | GPL |
+----------------------------+----------+--------------------+---------------------
mysql> SET GLOBAL group_replication_bootstrap_group=ON;
Query OK, 0 rows affected (0.00 sec)
mysql> START GROUP_REPLICATION;
Query OK, 0 rows affected (1.67 sec)
mysql> SET GLOBAL group_replication_bootstrap_group=OFF;
Query OK, 0 rows affected (0.00 sec)
mysql> select * from performance_schema.replication_group_members;
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| group_replication_applier | 9c37fc1c-9cad-11e8-be36-5254006a3b48 | server1 | 3306 | ONLINE ##说明配置可用,不可用会显示recovering |
+---------------------------+--------------------------------------+-------------+-
至此server1就配置好了,我们想一个问题,既然server2,server3与server1是同组数据库,实现功能相同,那么它们的配置是否也大同小异呢?
是的,server2和server3的配置与server1极为相似。我在这里说说与server1的不同即可。不再赘述。
不同:
(1)修改的配置文件(/etc/my.cnf),3个sever端id不同,address不同.
在server2主机上:
server_id=2 ###id对应的是组中编号
loose-group_replication_local_address="172.25.5.2:24901" ##address对应的是主机iP
..............
............
........
......
....
..
以此类推,可知在server3主机上:
server_id=3 ###id对应的是组中编号
loose-group_replication_local_address="172.25.5.3:24901" ##address对应的是主机iP
(2)对mysql的具体配置不同.
mysql> SET GLOBAL group_replication_bootstrap_group=ON; ##添加一个组,ON表示开启。此步只需在第一个组员创建即可,后续的组员不用创建。这样才能确保在同一组中。
Query OK, 0 rows affected (0.00 sec)
mysql> START GROUP_REPLICATION;
Query OK, 0 rows affected (1.67 sec)
注意:设置组时只需在第一个组员中创建即可,后续的组员不用创建。这样才能确保在同一组中。不在同组中无法实现全同步。
我发现这也是很多人的问题所在,自己每台主机都创建了组,每台主机都有属于自己独立的组。这样虽然每台主机状态配置良好(都处于online)。但并不互通。
以上就是server2,server3(其它组员)和server1(第一个组员)配置的不同之处了。
online与recovering 两种状态辨析。
mysql> select * from performance_schema.replication_group_members;
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| group_replication_applier | 57b54493-81cf-11e8-8a9a-52540013d792 | server1 | 3306 | ONLINE |
| group_replication_applier | c33132d0-81d1-11e8-9ff1-525400677cc8 | server2 | 3306 | RECOVERING |
+---------------------------+--------------------------------------+-------------+-------------+--------------+
2 rows in set (0.00 sec)
###首次查看状态RECOVERING,有可能是在同步数据,可以等会再查看,
mysql> select * from performance_schema.replication_group_members;
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| CHANNEL_NAME | MEMBER_ID | MEMBER_HOST | MEMBER_PORT | MEMBER_STATE |
+---------------------------+--------------------------------------+-------------+-------------+--------------+
| group_replication_applier | 57b54493-81cf-11e8-8a9a-52540013d792 | server1 | 3306 | ONLINE |
| group_replication_applier | c33132d0-81d1-11e8-9ff1-525400677cc8 | server2 | 3306 | ONLINE |
+---------------------------+----
测试:
在server1中创建新的数据库并写入数据,看server2和server3是否都同步有相同的数据。
mysql> create database test;
Query OK, 1 row affected (0.26 sec)
mysql> use test;
Database changed
mysql> create table t1 (c1 int primary key,c2 text not null); ##插入表时需要设置主键
Query OK, 0 rows affected (1.11 sec)
mysql> insert into t1 values(1,'chaokaidi');
Query OK, 1 row affected (0.24 sec
server2和server3上查看(两者都同步有server1的数据):
mysql> show databases;
mysql> use test;
mysql> show tables;
+----------------+
| Tables_in_test |
+----------------+
| t1 |
+----------------+
1 row in set (0.00 sec)
mysql> select * from t1;
+----+---------+
| c1 | c2 |
+----+---------+
| 1 | chaokaidi |
+----+---------+
实现全复制的另一种方法是修改数据库脚本文件(/etc/init.d/mysqld)以实现全同步。
mysql脚本文件修改,注释掉密码插件。
111 ret=$?
112 #[ $ret -ne 0 ] && return $ret
113 #initfile="$(install_validate_password_sql_file)"
114 #action $"Installing validate password plugin: " /usr/sbin/mysqld --datadir= "$datadir" --user=mysql --init-file="$initfile"
115 #ret=$?
116 #rm -f "$initfile"
117 chown -R mysql:mysql "$datadir"