一、什么是多源復制
MySQL 5.7發布后,在復制方面有了很大的改進和提升。比如開始支持多源復制(multi-source)以及真正的支持多線程復制了。多源復制可以使用基於二進制日志的復制或者基於事務的復制。下面我們說一說如何配置基於二進制日志的多源復制。
首先,我們要清楚幾種常見的復制模式:
- 一主一從
- 一主多從
- 級聯復制
- multi-master
MySQL 5.7 之前只能支持一主一從,一主多從或者多主多從的復制。如果想實現多主一從的復制 只能使用mariadb,但是mariadb又與官方的mysql版本不兼容。
MySQL 5.7 開始支持了多主一從的復制方式也就是多源復制。MySQL 5.7 版本相比之前的版本,無論是功能還是性能還是安全等方面都已經有了不少的提升。
首先我們要清楚multi-master OR multi-source 復制不是一樣的。multi-master復制通常是環形的復制,可以在任意的主機上將數據復制給其他的主機。如圖:

multi-source 是不同的。簡單的說,多源復制就是將多個主庫同步到一個從庫,從而增加從的利用率,節省了機器。如圖:

二、多源復制的使用場景
數據分析部門會需要各個業務部門的部分數據做數據分析,這個時候就可以使用到多源復制把各個主數據庫的數據復制到統一的數據庫中
在從服務器進行數據的匯總,如果我們的主服務器進行了分庫分表的操作,為了實現后期的一些數據的統計功能,往往要把數據匯總在一起在進行統計
在從服務器對所有主服務器的數據進行備份,在MySQL 5.7之前每個主服務器都需要一台從服務器,這樣很容易造成資源的浪費,同時也加大了DBA的維護成本,但MySQL 5.7引入的多源復制,可以把多個主服務器的數據同步到一台從服務器進行備份。
三、多源復制的必要條件
不管是使用基於二進制日志的復制或者基於事務的復制,要開啟多源復制功能必須要在從庫上設置master-info-repository AND relay-log-info-repository 這兩個參數。
這兩個參數是用來存儲同步信息的,可以設置的值為FILE和TABLE,默認是FILE。比如master-info就保存在master.info文件中,relay-log-info保存在relay-log.inf文件中服務器如果意外關閉,正確的relay-log-info沒有來的及更新帶relay-log.info文件,這樣就會造成數據的丟失。
為了數據更加安全,通常設置為TABLE。這些表都是innodb類型的,支持事務。相對文件存儲安全得多。在MySQL庫下可以看到這兩個表的信息,分別是mysql.slave_master_info AND mysql.slave_relay_log_info
這兩個參數也是可以動態調整的。
SET GLOBAL master_info_repository = 'TABLE';
SET GLOBAL relay_log_info_repository = 'TABLE';
如果要啟用enhanced multi-threaded slave(多線程復制),可以設置一下參數
slave-parallel-type=LOGICAL_CLOCK
slave-parallel-workers=8
relay_log_recovery=ON
如果SLAVE已經為開啟狀態,那么需要首先關閉SLAVE(stop slave;)
四、配置多源復制
4.1:環境准備
| hostname |
IP |
mysql |
| dev-master-01 |
192.168.1.131 |
master |
| dev_node-01 |
192.168.1.132 |
master |
| dev-node-02 |
192.168.1.133 |
slave |
4.2:安裝MySQL
具體的安裝步驟在這里:https://www.cnblogs.com/zhujingzhi/p/9609861.html 你可以選擇你想用的安裝方式進行安裝
4.3:配置配置文件my.cnf
1. 修改192.168.1.131和192.168.1.132下面的/etc/my.cnf文件,修改如下:記得修改配置參數中的server-id(192.168.1.131為1,那么192。168.1.132就得是2,每台服務器中的這個id不能一樣,切記!!!)
[mysqld] # 指定端口 不指定默認3306 #port=5603 # mysql數據存放路徑 datadir=/var/lib/mysql # mysql socker文件存放路徑 socket=/var/lib/mysql/mysql.sock # 創建符號鏈接(建議禁用符號鏈接,以防止各種安全風險。開啟將參數的值設置為1) symbolic-links=0 # 錯誤日志存放路徑 log-error=/var/log/mysqld.log # 啟動pid文件存放路徑 pid-file=/var/run/mysqld/mysqld.pid # 設置主從的時候的唯一ID 每台主機的ID不可重復 server-id=1 # #打開日志(主機需要打開),這個mysql-bin也可以自定義,這里也可以加上路徑,如:/home/www/mysql_bin_log/mysql-bin log-bin=mysql-bin # 設定mysql的復制模式(STATEMENT ROW MIXED) binlog_format=mixed # 繞過密碼驗證可直接使用root登錄(用於修改密碼) #skip-grant-tables=1 # 啟動服務器來禁用主機名緩存 skip-host-cache # 如果這個參數設為OFF,則MySQL服務在檢查客戶端連接的時候會解析主機名;如果這個參數設為ON,則MySQL服務只會使用IP,在這種情況下,授權表中的Host字段必須是IP地址或localhost。 skip-name-resolve # 網絡傳輸時單個數據包的大小 max_allowed_packet = 500M # 設置數據庫的時間 default-time-zone = '+8:00' # 內部內存臨時表的最大內存 tmp_table_size=200M # MySQL服務器用來作普通索引掃描、范圍索引掃描和不使用索引而執行全表掃描這些操作所用的緩存大小。 join_buffer_size = 32M # 每個會話執行排序操作所分配的內存大小。 sort_buffer_size = 1M # 每個客戶端線程和連接緩存和結果緩存交互,每個緩存最初都被分配大小為net_buffer_length的容量,並動態增長,直至達到max_allowed_packet參數的大小 net_buffer_length = 8K # 為每個線程對MyISAm表執行順序讀所分配的內存。如果數據庫有很多順序讀,可以增加這個參數,默認值是131072字節。 read_buffer_size = 512K # 這個參數用在MyISAM表和任何存儲引擎表隨機讀所使用的內存。 read_rnd_buffer_size = 32M # 在REPAIR TABLE、CREATE INDEX 或 ALTER TABLE操作中,MyISAM索引排序使用的緩存大小。 myisam_sort_buffer_size = 256M # 設置客戶端的並發連接數量 max_connections = 8000 # mysql關閉非交互連接前的等待時間,單位是秒 wait_timeout = 604800 # Mysql關閉交互連接前的等待時間,單位是秒 interactive_timeout = 604800 # 設定遠程用戶必須回應PORT類型數據連接的最大時間 connect_timeout = 30 # 如果客戶端嘗試連接的錯誤數量超過這個參數設置的值,則服務器不再接受新的客戶端連接。可以通過清空主機的緩存來解除服務器的這種阻止新連接的狀態,通過FLUSH HOSTS或mysqladmin flush-hosts命令來清空緩存。 max_connect_errors = 30000 # mysql關閉連接前的等待時間,單位是秒 interactive_timeout = 86400 # 慢查詢的時間設置,單位為秒 long_query_time = 20 # mysql服務緩存以重用的線程數 thread_cache_size = 120 # 為查詢結果所分配的緩存 query_cache_size = 256M # 如果一個事務需要的內存超過這個參數,就會報錯 max_heap_table_size=2097152000
2. 修改192.168.1.133也就是從庫的/etc/my.cnf 配置參數,配置如下:(記得修改server-id為3,不能和其他服務器id一樣,切記!!!)
[mysqld] # 指定端口 不指定默認3306 #port=5603 # mysql數據存放路徑 datadir=/var/lib/mysql # mysql socker文件存放路徑 socket=/var/lib/mysql/mysql.sock # 創建符號鏈接(建議禁用符號鏈接,以防止各種安全風險。開啟將參數的值設置為1) symbolic-links=0 # 錯誤日志存放路徑 log-error=/var/log/mysqld.log # 啟動pid文件存放路徑 pid-file=/var/run/mysqld/mysqld.pid # 設置主從的時候的唯一ID 每台主機的ID不可重復 server-id=1 # #打開日志(主機需要打開),這個mysql-bin也可以自定義,這里也可以加上路徑,如:/home/www/mysql_bin_log/mysql-bin log-bin=mysql-bin # 設定mysql的復制模式(STATEMENT ROW MIXED) binlog_format=mixed # 繞過密碼驗證可直接使用root登錄(用於修改密碼) #skip-grant-tables=1 # 啟動服務器來禁用主機名緩存 skip-host-cache # 如果這個參數設為OFF,則MySQL服務在檢查客戶端連接的時候會解析主機名;如果這個參數設為ON,則MySQL服務只會使用IP,在這種情況下,授權表中的Host字段必須是IP地址或localhost。 skip-name-resolve # 網絡傳輸時單個數據包的大小 max_allowed_packet = 500M # 設置數據庫的時間 default-time-zone = '+8:00' # 內部內存臨時表的最大內存 tmp_table_size=200M # MySQL服務器用來作普通索引掃描、范圍索引掃描和不使用索引而執行全表掃描這些操作所用的緩存大小。 join_buffer_size = 32M # 每個會話執行排序操作所分配的內存大小。 sort_buffer_size = 1M # 每個客戶端線程和連接緩存和結果緩存交互,每個緩存最初都被分配大小為net_buffer_length的容量,並動態增長,直至達到max_allowed_packet參數的大小 net_buffer_length = 8K # 為每個線程對MyISAm表執行順序讀所分配的內存。如果數據庫有很多順序讀,可以增加這個參數,默認值是131072字節。 read_buffer_size = 512K # 這個參數用在MyISAM表和任何存儲引擎表隨機讀所使用的內存。 read_rnd_buffer_size = 32M # 在REPAIR TABLE、CREATE INDEX 或 ALTER TABLE操作中,MyISAM索引排序使用的緩存大小。 myisam_sort_buffer_size = 256M # 設置客戶端的並發連接數量 max_connections = 8000 # mysql關閉非交互連接前的等待時間,單位是秒 wait_timeout = 604800 # Mysql關閉交互連接前的等待時間,單位是秒 interactive_timeout = 604800 # 設定遠程用戶必須回應PORT類型數據連接的最大時間 connect_timeout = 30 # 如果客戶端嘗試連接的錯誤數量超過這個參數設置的值,則服務器不再接受新的客戶端連接。可以通過清空主機的緩存來解除服務器的這種阻止新連接的狀態,通過FLUSH HOSTS或mysqladmin flush-hosts命令來清空緩存。 max_connect_errors = 30000 # mysql關閉連接前的等待時間,單位是秒 interactive_timeout = 86400 # 慢查詢的時間設置,單位為秒 long_query_time = 20 # mysql服務緩存以重用的線程數 thread_cache_size = 120 # 為查詢結果所分配的緩存 query_cache_size = 256M # 如果一個事務需要的內存超過這個參數,就會報錯 max_heap_table_size=2097152000 # mysql5.7 多源復制從庫加的配置參數 master-info-repository = table # 這個參數是必須的 relay-log-info-repository = table # 這個參數是必須的 report-port = 3306 report-host = 192.168.1.131 replicate-do-db = master1 replicate-do-db = master2 replicate_wild_do_table=master1.% replicate_wild_do_table=master2.%
4.4:重啟數據庫並且授權
重新啟動mysql服務 systemctl restart mysqld 升級mysql授權表 mysql_upgrade -uroot -p ==========================主庫執行SQL========================= 以下的執行都是在192.168.1.131和192.168.1.132的mysql中執行sql語句 登錄192.168.1.131和192.168.1.132的mysql mysql -uroot -p 創建mysql的主從授權用戶: grant replication slave on *.* to 'slave'@'192.168.1.%' identified by '2017123'; 刷新生效 FLUSH PRIVILEGES; ==========================從庫執行SQL========================= 登錄192.168.1.133的mysql執行sql語句: CHANGE MASTER TO MASTER_HOST='192.168.1.131', MASTER_USER='slave', MASTER_PORT=3306, MASTER_PASSWORD='2017123', MASTER_LOG_FILE='mysql-bin.000001', MASTER_LOG_POS=1 FOR CHANNEL 'master1'; CHANGE MASTER TO MASTER_HOST='192.168.1.132', MASTER_USER='slave', MASTER_PORT=3306, MASTER_PASSWORD='2017123', MASTER_LOG_FILE='mysql-bin.000001', MASTER_LOG_POS=1 FOR CHANNEL 'master2'; 全部顯示sql語句執行ok,然后查看主從的狀態: show slave status\G; 如果要查看單一信道的復制的詳細狀態,可以使用以下命令: SHOW SLAVE STATUS FOR CHANNEL 'master1'\G;
4.5:檢查測試
在主庫(192.168.1.131)實例創建一些數據。 create database master1; use master1; CREATE TABLE `test1` (`id` int(11) DEFAULT NULL,`count` int(11) DEFAULT NULL); insert into test1 values(1,1); 在主庫(192.168.1.132)實例創建一些數據。 create database master2; use master2; CREATE TABLE `test2` (`id` int(11) DEFAULT NULL,`count` int(11) DEFAULT NULL); insert into test2 values(1,1); 在從庫(192.168.1.133)實例檢查數據是否成功復制。 select * from master1.test1; select * from master2.test2; 列出所有的復制信道的復制狀態概況: select * from performance_schema.replication_applier_status_by_worker; 在 performance_schema 庫中,提供了復制相關的一些視圖,可供查看復制相關的信息。 use performance_schema; show tables like '%repl%'; 這些表里分別有多源通道的配置信息和多源通道的狀態信息,另外還有連接配置信息和連接狀態信息,如果配置了多線程復制的話,還會有多線程配置信息和多線程狀態信息。
五、一些其他的注意點
初次配置耗時較長,需要將各個 master 的數據 dump 下來,再 source 到 slave 上。
需要考慮各 master 數據增長頻率,slave 的數據增長頻率是這些數據的總和。如果太高,會導致大量的磁盤IO,造成數據更新延遲,最嚴重的是會影響正常的查詢。
如果多個主數據庫實例中存在同名的庫,則同名庫的表都會放到一個庫中;
如果同名庫中的表名相同且結構相同,則數據會到一起;如果結構不同,則先建的有效。
