mysql的半同步複製:
mysql的異步複製:mysql默認使用異步方式進行同步,master在執行客戶端提交的事務後會將結果返回給客戶端,表示客戶端的操作已經生效,同時會將該操作的binlog通過dumper通知slave來取,再正常情況下,slave會將該binlog寫入本地,並通過sql語句寫入從庫中與主庫同步數據,master對從庫是否寫入不負任何責任。
主和從的複製過程是由三個線程參與完成的,其中有兩個線程(sql語句和I/O線程在slave端),一個I/O線程在master端。
mysql的同步複製:這是一個偏執狂,客戶端向主庫提交數據,主庫寫入數據只有從庫將數據寫入本地後,返回給主庫一個回執,主庫向客戶端返回消息,表示已經成功受理該任務。
mysql半同步:在master的dumper線程通知salve,同時增加了一個ack,mysql5.7支持在事務提交前等待ack,當slave沒有返回給master ack時,將會自動降級爲異步複製。
半同步通過rpl_semi_sync_master_wait_point參數來控制半同步下,master事務提交前的方式
mysql中的半同步參數after_sync,master 將每個事務寫入binlog傳遞到slave刷新到磁盤relay log,master等待slave反饋接收到的ack後在提交事務並返回提交成功給客戶端。
半同步的部署:
半同步基於mysql的異步複製,所以要先搭建好環境。環境搭建參考我的博客:http://12237658.blog.51cto.com/12227658/1907018
測試:
主:master
安裝半同步插件:
mysql> INSTALL PLUGIN rpl_semi_sync_master SONAME 'semisync_master.so';
Query OK, 0 rows affected (0.08 sec)
查看插件是否安裝成功:
mysql> show plugins;會在最後發現:
| ngram | ACTIVE | FTPARSER | NULL | GPL |
| rpl_semi_sync_master | ACTIVE | REPLICATION | semisync_master.so | GPL |
+----------------------------+----------+--------------------+--------------------+---------+
表明成功。
從:slave
安裝插件:
mysql> INSTALL PLUGIN rpl_semi_sync_slave SONAME 'semisync_slave.so';
Query OK, 0 rows affected (0.11 sec)
使用:show plugins;或:
mysql> SELECT PLUGIN_NAME, PLUGIN_STATUS FROM INFORMATION_SCHEMA.PLUGINS WHERE PLUGIN_NAME LIKE '%semi%';
如果發現
| rpl_semi_sync_slave | ACTIVE | REPLICATION | semisync_slave.so | GPL |
+----------------------------+----------+--------------------+-------------------+-----
即爲成功。
啓動半同步:
主:master
mysql> SET GLOBAL rpl_semi_sync_master_enabled = 1;
Query OK, 0 rows affected (0.00 sec)
mysql> show status like 'Rpl_semi_sync_master_status';
+-----------------------------+-------+
| Variable_name | Value |
+-----------------------------+-------+
| Rpl_semi_sync_master_status | ON |
+-----------------------------+-------+
1 row in set (0.00 sec)
從:slave
mysql> SET GLOBAL rpl_semi_sync_slave_enabled = 1;
Query OK, 0 rows affected (0.00 sec)
mysql> show status like 'Rpl_semi_sync_slave_status';
+----------------------------+-------+
| Variable_name | Value |
+----------------------------+-------+
| Rpl_semi_sync_slave_status | ON |
+----------------------------+-------+
1 row in set (0.00 sec)
最後重新啓動一下I/O線程:
mysql> STOP SLAVE IO_THREAD;
mysql> START SLAVE IO_THREAD;
測試:
在不關閉slave的情況下創建數據庫,主從庫會很快寫入
主:
mysql> show status like 'Rpl_semi_sync_master_status';
+-----------------------------+-------+
| Variable_name | Value |
+-----------------------------+-------+
| Rpl_semi_sync_master_status | ON |
+-----------------------------+-------+
1 row in set (0.00 sec)
mysql> create database ginkgo;
Query OK, 1 row affected (0.05 sec)
從:
mysql> show status like 'Rpl_semi_sync_slave_status';
+----------------------------+-------+
| Variable_name | Value |
+----------------------------+-------+
| Rpl_semi_sync_slave_status | ON |
+----------------------------+-------+
1 row in set (0.00 sec)
mysql> show databases;
+--------------------+
| Database |
+--------------------+
| information_schema |
| ginkgo |
| mysql |
| performance_schema |
| sys |
+--------------------+
5 rows in set (0.00 sec)
將從上的slave關閉:
mysql> drop database ginkgo;
Query OK, 0 rows affected (10.06 sec)
mysql> show status like 'Rpl_semi_sync_master_status';
+-----------------------------+-------+
| Variable_name | Value |
+-----------------------------+-------+
| Rpl_semi_sync_master_status | OFF |
+-----------------------------+-------+
1 row in set (0.00 sec)
slave長時間不給ack迴應,被迫轉化爲異步,時間也較長,主要是等待時間。
從上肯定沒有數據變化。
**注意,寫數據庫時一定要在配置文件中確定自己是允許那個庫同步,不要瞎建庫奧。