MySQL5.6 semi-synchronous master-slave replication configuration

Before talking about this feature, let's take a look at the derivation of MySQL's replication architecture.

In 2000, MySQL version 3.23.15 introduced Replication. Replication is widely used as a quasi-real-time synchronization method. The implementation of Replicaton at this time involves two threads, one in the Master and one in the Slave. The I/O and SQL functions of the Slave are used as a thread to directly apply the event after getting the event from the Master, and there is no relay log. In this way, the speed of reading events will be slowed down by the Slave replay speed. When there is a large delay in the master and backup, a large number of binary logs will not be backed up to the slave.

In 2002, MySQL version 4.0.2 separates slave-side event reading and execution into two threads (IO thread and SQL thread), and introduces relay log. The IO thread reads the event and writes it to the relay log, and the SQL thread reads the event from the relay log and executes it. In this way, even if the execution of the SQL thread is slow, the binary log of the Master will be synchronized to the Slave as much as possible. When the Master goes down and switches to the Slave, there will be no massive data loss.

This asynchronous replication method was used until MySQL 5.5 in 2010. The transaction execution of the main database does not control the synchronization progress of the standby database. If the standby database falls behind and the main database crashes unfortunately, data loss will result. Therefore, in MySQL 5.5, semi-synchronous replication was introduced naturally. The main library needs to ensure that at least one slave library receives and writes it to the relay log before responding to the transaction submitted by the client. So can semi-synchronous replication be done without data loss? Analysis below.

In 2016, MySQL introduced a brand new technology in 5.7.17 called InnoDB Group Replication. At present, the official MySQL 5.7.17 full synchronization technology based on Group replication has come out, and the full synchronization technology brings more data consistency guarantees. It is believed to be an important direction of future synchronization technology and is worth looking forward to. MySQL 5.7 Group Replication


Semi-synchronous mechanism:

1. When the semi-synchronous replication function is enabled on the Master , at least one Slave should enable its function. At this point, a thread submitting a transaction on the Master will be blocked until it learns that a Slave that has enabled semi-synchronous replication has received all events for this transaction, or waits for a timeout. 

2. When the slave host is connected to the master , it can check whether it is in a semi-synchronous replication mechanism. 

3. When the events of a transaction have been written to its relay-log and have been flushed to disk, the Slave will notify that it has been received. 

4. If the wait times out, that is, the Master is not notified that it has been received, then the Master will automatically convert to the asynchronous replication mechanism. When at least one semi-synchronous slave catches up, the master and its slave automatically switch to a semi-synchronous replication mechanism.  

5. The semi-synchronous replication function must be enabled on both the Master and the Slave , and the semi-synchronous replication will work; otherwise, only one side will be enabled, and it will still be asynchronous replication.  


Due to the full synchronization introduced in versions after 5.7, testing semi-synchronization must be performed with version 5.6.

1.配置半同步的主从复制必须先配置好异步的主从复制,先检查一下异步的主从是否完好。

master:

mysql> mysql> show master status;
+------------------+----------+--------------+------------------+-------------------+
| File             | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set |
+------------------+----------+--------------+------------------+-------------------+
| mysql_bin.000013 |      601 |              |                  |                   |
+------------------+----------+--------------+------------------+-------------------+
1 row in set (0.00 sec)

slave:

mysql> show slave status\G
*************************** 1. row ***************************
               Slave_IO_State: Waiting for master to send event
                  Master_Host: 172.17.61.131
                  Master_User: repl
                  Master_Port: 3306
                Connect_Retry: 60
              Master_Log_File: mysql_bin.000013
          Read_Master_Log_Pos: 601
               Relay_Log_File: mysqld-relay-bin.000002
                Relay_Log_Pos: 374
        Relay_Master_Log_File: mysql_bin.000013
             Slave_IO_Running: Yes
            Slave_SQL_Running: Yes
           ...
          Exec_Master_Log_Pos: 601
              Relay_Log_Space: 548
              Until_Condition: None
             ...
             Master_Server_Id: 10000
                  Master_UUID: 82acea94-3e6f-11e8-b4a7-000c29d02daa
             Master_Info_File: /u01/mysql/master.info
                    SQL_Delay: 0
          SQL_Remaining_Delay: NULL
      Slave_SQL_Running_State: Slave has read all relay log; waiting for the slave I/O thread to update it
           Master_Retry_Count: 86400
           ...
1 row in set (0.00 sec)

2.master安装半同步模块并启动(此模块就在/usr/local/mysql/lib/plugin/semisync_master.so)

PS:如果想卸载异步模块就使用uninstall即可。

mysql> show global variables like '%semi%';
Empty set (0.00 sec)

mysql> install plugin rpl_semi_sync_master soname 'semisync_master.so';
Query OK, 0 rows affected (0.06 sec)

mysql>  show global variables like '%semi%';
+------------------------------------+-------+
| Variable_name                      | Value |
+------------------------------------+-------+
| rpl_semi_sync_master_enabled       | OFF   |
| rpl_semi_sync_master_timeout       | 10000 |
| rpl_semi_sync_master_trace_level   | 32    |
| rpl_semi_sync_master_wait_no_slave | ON    |
+------------------------------------+-------+
4 rows in set (0.00 sec)

rpl_semi_sync_master_enabled参数是指是否已启动半同步

rpl_semi_sync_master_timeout参数连接salve超时的时间,单位为毫秒,默认为10秒

在配置文件中修改这两个参数并重启数据库

[root@qht131 ~]# cat /etc/my.cnf
。。。
[mysqld]
。。。
rpl_semi_sync_master_enabled = 1
rpl_semi_sync_master_timeout = 2000
[root@qht131 ~]# service mysql restart
Shutting down MySQL....                                    [  OK  ]
Starting MySQL..                                           [  OK  ]

mysql>  show global variables like '%semi%';
+------------------------------------+-------+
| Variable_name                      | Value |
+------------------------------------+-------+
| rpl_semi_sync_master_enabled       | ON    |
| rpl_semi_sync_master_timeout       | 2000  |
| rpl_semi_sync_master_trace_level   | 32    |
| rpl_semi_sync_master_wait_no_slave | ON    |
+------------------------------------+-------+
4 rows in set (0.00 sec)

3.slave安装半同步模块

mysql> install plugin rpl_semi_sync_slave soname 'semisync_slave.so';
Query OK, 0 rows affected (0.03 sec)

mysql> show global variables like '%semi%';
+---------------------------------+-------+
| Variable_name                   | Value |
+---------------------------------+-------+
| rpl_semi_sync_slave_enabled     | OFF   |
| rpl_semi_sync_slave_trace_level | 32    |
+---------------------------------+-------+
2 rows in set (0.00 sec)

修改配置文件打开半同步

[root@qht132 backup]# cat /etc/my.cnf
。。。
[mysqld]
。。。。
rpl_semi_sync_slave_enabled=1
[root@qht132 backup]# service mysql restart
Shutting down MySQL..                                      [  OK  ]
Starting MySQL..                                           [  OK  ]

mysql> show global variables like '%semi%';
+---------------------------------+-------+
| Variable_name                   | Value |
+---------------------------------+-------+
| rpl_semi_sync_slave_enabled     | ON    |
| rpl_semi_sync_slave_trace_level | 32    |
+---------------------------------+-------+
2 rows in set (0.00 sec)

需要重新连接master服务器,半同步才会生效:

mysql> stop slave io_thread;
Query OK, 0 rows affected (0.00 sec)

mysql> start slave io_thread;
Query OK, 0 rows affected (0.00 sec)

3.检查一下半同步是否完成

mysql> show global status like 'rpl%';
+--------------------------------------------+-------+
| Variable_name                              | Value |
+--------------------------------------------+-------+
| Rpl_semi_sync_master_clients               | 1     |
| Rpl_semi_sync_master_net_avg_wait_time     | 0     |
| Rpl_semi_sync_master_net_wait_time         | 0     |
| Rpl_semi_sync_master_net_waits             | 0     |
| Rpl_semi_sync_master_no_times              | 0     |
| Rpl_semi_sync_master_no_tx                 | 0     |
| Rpl_semi_sync_master_status                | ON    |
| Rpl_semi_sync_master_timefunc_failures     | 0     |
| Rpl_semi_sync_master_tx_avg_wait_time      | 0     |
| Rpl_semi_sync_master_tx_wait_time          | 0     |
| Rpl_semi_sync_master_tx_waits              | 0     |
| Rpl_semi_sync_master_wait_pos_backtraverse | 0     |
| Rpl_semi_sync_master_wait_sessions         | 0     |
| Rpl_semi_sync_master_yes_tx                | 0     |
+--------------------------------------------+-------+
14 rows in set (0.03 sec)

现在半同步已经正常工作了,主要看Rpl_semi_sync_master_clients是否不为0,Rpl_semi_sync_master_status是否为ON。如果Rpl_semi_sync_master_status为OFF,说明出现了网络延迟或Slave IO线程延迟。

4.那么可以验证一下半同步超时,是否会自动降为异步工作。可以在Slave上停掉半同步协议,然后在Master上创建数据库看一下能不能复制到Slave上。

slave上先关闭半同步:

mysql> set global rpl_semi_sync_slave_enabled = 0 ;
Query OK, 0 rows affected (0.00 sec)

mysql> stop slave io_thread;
Query OK, 0 rows affected (0.00 sec)

mysql> start slave io_thread;
Query OK, 0 rows affected (0.00 sec)

master:

mysql> create database dbtest;
Query OK, 1 row affected (2.01 sec)

mysql> create database dbtest2;
Query OK, 1 row affected (0.00 sec)
创建第一个数据库花了 2.01 秒,而我们前面设置的超时时间是 2 秒,而创建第二个数据库花了 0.01 秒,由此得出结论是超时转换为异步传送。可以在Master上查看半同步相关的参数值 Rpl_semi_sync_master_clients和Rpl_semi_sync_master_status是否正常。


mysql> show global status like '%semi%';
+--------------------------------------------+-------+
| Variable_name                              | Value |
+--------------------------------------------+-------+
| Rpl_semi_sync_master_clients               | 0     |
| Rpl_semi_sync_master_net_avg_wait_time     | 0     |
| Rpl_semi_sync_master_net_wait_time         | 0     |
| Rpl_semi_sync_master_net_waits             | 0     |
| Rpl_semi_sync_master_no_times              | 1     |
| Rpl_semi_sync_master_no_tx                 | 2     |
| Rpl_semi_sync_master_status                | OFF   |
| Rpl_semi_sync_master_timefunc_failures     | 0     |
| Rpl_semi_sync_master_tx_avg_wait_time      | 0     |
| Rpl_semi_sync_master_tx_wait_time          | 0     |
| Rpl_semi_sync_master_tx_waits              | 0     |
| Rpl_semi_sync_master_wait_pos_backtraverse | 0     |
| Rpl_semi_sync_master_wait_sessions         | 0     |
| Rpl_semi_sync_master_yes_tx                | 0     |
+--------------------------------------------+-------+
14 rows in set (0.03 sec)

Rpl_semi_sync_master_clients已为0,Rpl_semi_sync_master_status已为OFF,现在主从复制已是异步状态。

5.还有一个问题,slave开启半同步后,master能自动开启半同步吗?

slave:

mysql> set global rpl_semi_sync_slave_enabled = 1;
Query OK, 0 rows affected (0.00 sec)

mysql> stop slave io_thread;
Query OK, 0 rows affected (0.01 sec)

mysql> start slave io_thread;
Query OK, 0 rows affected (0.00 sec)

master:

mysql> show global status like '%semi%';
+--------------------------------------------+-------+
| Variable_name                              | Value |
+--------------------------------------------+-------+
| Rpl_semi_sync_master_clients               | 1     |
| Rpl_semi_sync_master_net_avg_wait_time     | 0     |
| Rpl_semi_sync_master_net_wait_time         | 0     |
| Rpl_semi_sync_master_net_waits             | 0     |
| Rpl_semi_sync_master_no_times              | 1     |
| Rpl_semi_sync_master_no_tx                 | 2     |
| Rpl_semi_sync_master_status                | ON    |
| Rpl_semi_sync_master_timefunc_failures     | 0     |
| Rpl_semi_sync_master_tx_avg_wait_time      | 0     |
| Rpl_semi_sync_master_tx_wait_time          | 0     |
| Rpl_semi_sync_master_tx_waits              | 0     |
| Rpl_semi_sync_master_wait_pos_backtraverse | 0     |
| Rpl_semi_sync_master_wait_sessions         | 0     |
| Rpl_semi_sync_master_yes_tx                | 0     |
+--------------------------------------------+-------+
14 rows in set (0.00 sec)
当Slave开启半同步后,或者当主从之间网络延迟恢复正常的时候,半同步复制会自动从异步复制又转为半同步复制,还是相当智能的。


参考:http://www.ywnds.com/?p=7023

Guess you like

Origin http://43.154.161.224:23101/article/api/json?id=324530564&siteId=291194637