編寫mysql虛擬機主從複製

 

MySQL主從複製概念

  • Mysql內建的複製功能是構建大型,高性能應用程序的基礎。將Mysql的數據分佈到多個系統上去,這種分佈的機制,是通過將Mysql的某一臺主機的數據複製到其它主機(slaves)上,並重新執行一遍來實現的。複製過程中一個服務器充當主服務器,而一個或多個其它服務器充當從服務器。主服務器將更新寫入二進制日誌文件,並維護文件的一個索引以跟蹤日誌循環。這些日誌可以記錄發送到從服務器的更新。當一個從服務器連接主服務器時,它通知主服務器從服務器在日誌中讀取的最後一次成功更新的位置。從服務器接收從那時起發生的任何更新,然後封鎖並等待主服務器通知新的更新。

  • 注:在進行mysql複製時,所有對複製中的表的更新必須在主服務器上進行。否則必須要小心,以避免用戶對主服務器上的表進行的更新與對從服務器上的表所進行的更新之間的衝突。

MySQL主從複製原理

(1)MySQL支持複製類型

  • 基於語句的複製: 在主服務器上執行的SQL語句,在從服務器上執行同樣的語句。MySQL默認採用基於語句的複製,效率比較高。一旦發現沒法精確複製時,會自動選着基於行的複製。
  • 基於行的複製:把改變的內容複製過去,而不是把命令在從服務器上執行一遍. 從mysql5.0開始支持
  • 混合類型的複製: 默認採用基於語句的複製,一旦發現基於語句的無法精確的複製時,就會採用基於行的複製。

(2)MySQL主從複製過程

  • MySQL主從複製基本流程圖:

MySQL服務器主從複製服務詳解

  • 複製過程詳解:

  • 1、在每個事物更新數據完成之前,master主服務器在二進制日誌記錄這些改變,寫入二進制日誌完成後,master通知存儲引擎提交事物。
  • 2、slave將master主服務器的二進制日誌Binary log 複製到其中繼日誌Relay log,首先slave(從服務器)開始一個工作線程——I/O線程,I/O線程在master上打開一個普通的連接,然後開始Binlog dump process,該進程從master的二進制日誌中讀取事件,如果已經跟上master,它會睡眠並等待master產生新的事件,而I/O線程將這些事件寫入中繼日誌。
  • 3、SQLslave thread(SQL從線程)處理該過程的最後一步,SQL線程從中繼日誌中讀取事件,並重放其中的事件而更新salve數據,使其與master中數據保持一致,只要該線程與I/O線程保持一致,中繼日誌通常會位於OS緩存中(也就是內存當中),所以中繼開銷很小。

(3)主從複製注意點

  • 1、master將操作語句記錄到binlog日誌中,然後授予slave遠程連接的權限(master一定要開啓binlog二進制日誌功能;通常爲了數據安全考慮,slave也開啓binlog功能)。
  • 2、slave開啓兩個線程:IO線程和SQL線程。其中:IO線程負責讀取master的binlog內容到中繼日誌relay log裏;SQL線程負責從relay log日誌裏讀出binlog內容,並更新到slave的數據庫裏,這樣就能保證slave數據和master數據保持一致了。
  • 3、Mysql複製至少需要兩個Mysql的服務,當然Mysql服務可以分佈在不同的服務器上,也可以在一臺服務器上啓動多個服務。
  • 4、Mysql複製最好確保master和slave服務器上的Mysql版本相同(如果不能滿足版本一致,那麼要保證master主節點的版本低於slave從節點的版本)。
  • 5、master和slave兩節點間時間需同步。

MySQL主從服務部署

實驗環境

服務器 服務器系統 IP地址 所需服務
MySQL主服務器 centos7.3 192.168.144.128 ntp,mysql5.7
MySQL從服務器 centos7.3 192.168.144.129 ntp,mysql5.7

MySQL主服務器

  • 設置主服務器爲本地時鐘源
    安裝時間同步軟件:

yum install ntp -y 
vim /etc/ntp.conf

末行添加:

server 127.127.144.0                    //設置本地是時鐘源,注意自己所在網段是144段
fudge 127.127.144.0 stratum 8          //設置時間層級爲8(限制在15內)

service ntpd start 
service iptables stop 
setenforce 0

  • 安裝MySQL軟件

這裏在centos7上安裝MySQL5.7版本,詳細過程請參見MySQL5.7安裝

  • 安裝好MySQL後:

vim /etc/my.cnf

[mysqld]
user = mysql
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
port = 3306
character_set_server=utf8
pid-file = /usr/local/mysql/mysqld.pid
socket = /usr/local/mysql/mysql.sock
server-id = 10              //設置主從服務器身份唯一標識
log-bin=master-bin          //開啓二進制日誌
log-slave-updates=true      //開啓主從功能

systemctl restart mysqld.service

mysql -u root -p

GRANT REPLICATION SLAVE ON *.* TO 'myslave'@'192.168.144.%' IDENTIFIED BY '123456';  //將從服務器權限賦予賬號myslave,可以在192.168.144.0網段登錄,密碼爲123456 

FLUSH PRIVILEGES;     //刷新狀態

show master status;  //查看主服務器狀態
  • 切記主服務器狀態!

MySQL服務器主從複製服務詳解

MySQL從服務器

  • 安裝ntp時間同步軟件,由於主服務器已經設置了時間源,從服務器只需打開時間同步服務,並跟主服務器同步即可。

yum install ntp -y 
systemctl restart mysqld.service 
systemctl stop firewalld/service 
setenforce 0 
/usr/sbin/ntpdate 192.168.144.128 //進行時間同步//

  • 安裝MySQL軟件

vim /etc/my.cnf

[mysqld]
user = mysql
basedir = /usr/local/mysql
datadir = /usr/local/mysql/data
port = 3306
character_set_server=utf8
pid-file = /usr/local/mysql/mysqld.pid
socket = /usr/local/mysql/mysql.sock
server-id = 20              //設置唯一身份標識
relay-log=relay-log-bin     //打開中繼日誌功能
relay-log-index=slave-relay-bin.index   //定義relay-log的位置和名稱
  • 進入數據庫

mysql -u root -p //

change master to master_host='192.168.144.128',master_user='myslave',master_password='123456',master_log_file='master-bin.000001',master_log_pos=604;   //切記根據主服務器狀態更改相應二進制日誌文件和偏移量;

start slave;    //開啓從服務器狀態

show slave status\G;     //查看狀態

MySQL服務器主從複製服務詳解

驗證主從結果

  • 當選擇在主MySQL服務器中創建數據,從服務器中也會同步更新數據文件。

MySQL服務器主從複製服務詳解

MySQL服務器主從複製服務詳解

會遇到的問題:

數據庫已搭建完成,各種配置均已完成,但是在start slave ;的時候,報錯:

ERROR 1200 (HY000): The server is not configured as slave; fix in config file or with CHANGE MASTER TO
這裏說,我沒有配置爲從機,但我明明配置過的啊。

MySQL版本:5.6.19

主:master IP  :  172.17.210.199
從:slave    IP :172.17.206.138 
先看看從機172.17.206.138的my.cnf

[root@liuyazhuang ~]# vi /etc/my.cnf
[mysqld]
datadir=/usr/local/mysql/data
socket=/tmp/mysql.sock
skip-grant-tables
user=mysql
# Disabling symbolic-links is recommended to prevent assorted security risks
symbolic-links=0
tmpdir=/tmp
[mysqld_safe]
log-error=/usr/local/data/mysqld.log
pid-file=/usr/local/mysql/data/mysqld.pid
###############以下是添加主從的配置
server_id = 2
log-bin = /usr/local/mysql/log/solve-bin.log
master-host = 172.17.210.199
master-user = test
master-pass = 123456
master-port = 3306
master-connect-retry = 60
這是MySQL主機172.17.210.199的my.cnf
[root@liuyazhuang ~]$ cat /etc/my.cnf
[mysqld]
log-bin = /u01/mysql/log/masters-bin.log
read-only = 0
basedir = /u01/mysql
datadir = /u01/mysql/data
port = 3306
server_id = 1
socket = /tmp/mysql.sock
join_buffer_size = 128M
sort_buffer_size = 2M
read_rnd_buffer_size = 2M

sql_mode=NO_ENGINE_SUBSTITUTION,STRICT_TRANS_TABLES
嘗試過多次 重啓主從還是報錯;
接着手動chang to 後還是一樣報錯
mysql> CHANGE MASTER TO
MASTER_HOST='172.17.210.199',
MASTER_USER='test',
MASTER_PASSWORD='123456',
MASTER_LOG_FILE='masters-bin.000003',
MASTER_LOG_POS=120;
Query OK, 0 rows affected, 2 warnings (0.04 sec) 
在從庫服務器執行START slave;命令啓動slave
mysql> START slave;
報錯:
ERROR 1200 (HY000): The server is not configured as slave; fix in config file or with CHANGE MASTER TO
於是查看日誌
1.查看SLAVE172.17.206.138上的Mysql報錯日誌,有這麼一句:
141009  6:06:29 [ERROR] Server id not set, will not start slave

意思是,slave的server-id沒有設置。
那就奇怪了,我明明在配置文件裏面指定了server-id的了,並且有重啓mysql服務,難道不起效?
分別在主從上執行命令“show variables like 'server_id';”。

-------從機上面查看端口
mysql> mysql> SHOW VARIABLES LIKE 'server_id';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| server_id     | 0     |
+---------------+-------+
1 row in set (0.00 sec)
命名設置的是2,怎麼會變成0
-------主機上面查看 

mysql> SHOW VARIABLES LIKE 'server_id';
+---------------+-------+
| Variable_name | Value |
+---------------+-------+
| server_id     | 1     |
+---------------+-------+
1 row in set (0.00 sec)
跟設置的一樣。
既然參數文件不生效,就試試在數據庫命令裏面設置:在從機 172.17.206.138上執行命令
mysql > SET GLOBAL server_id=2;
再次在從機 172.17.206.138上執行slave start和show slave status,成功了。
         注意!!!由於“SET GLOBAL server_id=;”命令會在mysql服務重啓後丟失,所以一定要寫到配置文件裏面。
但爲什麼我之前修改了my.cnf文件不起效?
仔細排查,發現配置裏面有[mysqld]和[mysqld_safe],之前將修改的配置內容基本都放在了[mysqld_safe]下面,新增的配置文件放的位置不一樣也有關係?於是我嘗試把配置文件裏修改的部分放在[mysqld]下面,於是改成這樣:
[root@liuyazhuang]# cat  /etc/my.cnf
[mysqld]
datadir=/usr/local/mysql/data
socket=/tmp/mysql.sock
skip-grant-tables
user=mysql
symbolic-links=0
tmpdir=/tmp
server_id = 2
log-bin = /usr/local/mysql/log/solve-bin.log
master-host = 172.17.210.199
master-user = test
master-pass = 123456
master-port = 3306
master-connect-retry = 60

[mysqld_safe]
log-error=/usr/local/data/mysqld.log
pid-file=/usr/local/mysql/data/mysqld.pid 
如圖,就是將圖中標註的內容從[mysqld_safe]下修改到[mysqld]下

修改之後,再次同步,成功了!

mysql>
mysql> STOP slave;
Query OK, 0 rows affected (0.05 sec)
 
mysql> START slave;
Query OK, 0 rows affected (0.00 sec) 

如何連接到

1、先 ping 一下數據庫服務器的ip 地址確認網絡暢通。
 
2、關閉數據庫服務的防火牆
    service iptables stop
 
3、 確認Mysql中已經有可以通過遠程登錄的賬戶
    select  * from mysql.user where user='li4' and host='%';
 
如果沒有用戶,先執行如下命令:
    grant all privileges on *.*  to li4@'%'  identified by '123123';
 
4、測試連接:

 
5.如果使用的是Navicat遠程工具,如果連接出錯,在my.conf配置文件的mysqld下添加以下配置
skip-name-resolve
 

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章