Mysql主從同步的實現原理與配置實戰
1、什麼是mysql主從同步?
當master(主)庫的資料發生變化的時候,變化會實時的同步到slave(從)庫。
2、主從同步有什麼好處?
- 水平擴充套件資料庫的負載能力。
- 容錯,高可用。Failover(失敗切換)/High Availability
- 資料備份。
3、主從同步的原理是什麼?
首先我們來了解master-slave的體系結構。如下圖:
不管是delete、update、insert,還是建立函式、儲存過程,所有的操作都在master上。當master有操作的時候,slave會快速的接收到這些操作,從而做同步。
但是,這個機制是怎麼實現的呢?在master機器上,主從同步事件會被寫到特殊的log檔案中(binary-log);在slave機器上,slave讀取主從同步事件,並根據讀取的事件變化,在slave庫上做相應的更改。
如此,就實現了主從同步了!
下面我們來詳細的瞭解。3.1主從同步事件有哪些上面說到:在master機器上,主從同步事件會被寫到特殊的log檔案中(binary-log);
主從同步事件有3種形式:statement、row、mixed。
- statement:會將對資料庫操作的sql語句寫入到binlog中。
- row:會將每一條資料的變化寫入到binlog中。
- mixed:statement與row的混合。Mysql決定什麼時候寫statement格式的,什麼時候寫row格式的binlog。
3.2在master機器上的操作
當master上的資料發生改變的時候,該事件(insert、update、delete)變化會按照順序寫入到binlog中。binlog dump執行緒
3.3在slave機器上的操作
當主從同步開啟的時候,slave上會建立2個執行緒。
- I/O執行緒。該執行緒連線到master機器,master機器上的binlog dump執行緒會將binlog的內容傳送給該I/O執行緒。該I/O執行緒接收到binlog內容後,再將內容寫入到本地的relay log。
- SQL執行緒。該執行緒讀取I/O執行緒寫入的relay log。並且根據relay log的內容對slave資料庫做相應的操作。
3.4如何在master、slave上檢視上述的執行緒?
使用SHOW PROCESSLIST命令可以檢視。如圖,在master機器上檢視binlog dump執行緒
如圖,在slave機器上檢視I/O、SQL執行緒。
接下來給大家講解mysql主從同步實戰系統環境:系統的話大同小異,都差不多,我這裡用的是ubuntu16.04+mysql5.7,用到兩臺伺服器:其中master IP:192.168.33.22,另一個slave IP:192.168.33.33
master機器上的操作
1、更改配置檔案我們找到檔案/etc/mysql/mysql.conf.d/mysqld.cnf
。
配置如下:
bind-address = 192.168.33.22 #your master ip server-id = 1 #在master-slave架構中,每臺機器節點都需要有唯一的server-id log_bin = /var/log/mysql/mysql-bin.log #開啟binlog
2、重啟mysql,以使配置檔案生效。
sudo systemctl restart mysql
3、建立主從同步的mysql user。
$ mysql -u root -p Password: ##建立slave1使用者,並指定該使用者只能在主機192.168.33.33上登入。 mysql> CREATE USER 'slave1'@'192.168.33.33' IDENTIFIED BY 'slavepass'; Query OK, 0 rows affected (0.00 sec) ##為slave1賦予REPLICATION SLAVE許可權。 mysql> GRANT REPLICATION SLAVE ON *.* TO 'slave1'@'192.168.33.33'; Query OK, 0 rows affected (0.00 sec)
4、為MYSQL加讀鎖為了主庫與從庫的資料保持一致,我們先為mysql加入讀鎖,使其變為只讀。
mysql> FLUSH TABLES WITH READ LOCK; Query OK, 0 rows affected (0.00 sec)
5、記錄下來MASTER REPLICATION LOG 的位置該資訊稍後會用到。
mysql> SHOW MASTER STATUS;
+------------------+----------+--------------+------------------+-------------------+ | File | Position | Binlog_Do_DB | Binlog_Ignore_DB | Executed_Gtid_Set | +------------------+----------+--------------+------------------+-------------------+ | mysql-bin.000001 | 613 | | | | +------------------+----------+--------------+------------------+-------------------+ 1 row in set (0.00 sec)
6、將master DB中現有的資料資訊匯出
$ mysqldump -u root -p --all-databases --master-data > dbdump.sql
7、接觸master DB的讀鎖
mysql> UNLOCK TABLES;
8、將步驟6中的dbdump.sql檔案copy到slave
scp dbdump.sql [email protected]:/home/ubuntu
slave機器上的操作
1、更改配置檔案我們找到檔案/etc/mysql/mysql.conf.d/mysqld.cnf
。
更改配置如下:
bind-address = 192.168.33.33 #your slave ip server-id = 2 #master-slave結構中,唯一的server-id log_bin = /var/log/mysql/mysql-bin.log #開啟binlog
2、重啟mysql,以使配置檔案生效
sudo systemctl restart mysql
3、匯入從master DB。匯出的dbdump.sql檔案,以使master-slave資料一致
$ mysql -u root -p < /home/ubuntu/dbdump.sql
4、使slave與master建立連線,從而同步
$ mysql -u root -p Password: mysql> STOP SLAVE; Query OK, 0 rows affected, 1 warning (0.00 sec) mysql> CHANGE MASTER TO -> MASTER_HOST='192.168.33.22', -> MASTER_USER='slave1', -> MASTER_PASSWORD='slavepass', -> MASTER_LOG_FILE='mysql-bin.000001', -> MASTER_LOG_POS=613; Query OK, 0 rows affected, 2 warnings (0.01 sec) mysql> START SLAVE; Query OK, 0 rows affected (0.00 sec) MASTER_LOG_FILE='mysql-bin.000001'與MASTER_LOG_POS=613的值,是從上面的SHOW MASTER STATUS得到的。經過如此設定之後,就可以進行master-slave同步了
~