在已有運行實例上配置主從複製,面臨版本差異、配置文件位置、啟動腳本、數據同步等實戰挑戰。本文提供標準化 SOP,涵蓋雙機同網段環境下的完整配置、同步、驗證與常見坑點。
| 角色 | IP | Server ID | 備註 |
|---|---|---|---|
| Master (A) | 192.168.1.100 | 1 | 讀寫主庫 |
| Slave (B) | 192.168.1.101 | 2 | 只讀從庫 |
前提:同版本 MySQL、網路互通、防火牆放行 3306、my.cnf 位置已知、啟停腳本可用。
mysql -u root -p -e "
GRANT REPLICATION SLAVE ON *.* TO 'repl_user'@'192.168.1.101' IDENTIFIED BY 'ReplPass123!';
FLUSH PRIVILEGES;"
my.cnf [mysqld] 區段[mysqld]
server-id = 1
log-bin = /var/log/mysql/mysql-bin.log
binlog-format = ROW -- 推薦 ROW 格式,數據一致性最強
binlog-do-db = test -- 只同步 test 庫 (可多行)
binlog-ignore-db = mysql -- 不同步系統庫
sync_binlog = 1 -- 每次提交刷盤,最安全
innodb_flush_log_at_trx_commit = 1 -- 配合雙 1 保證不丟事務
expire_logs_days = 7 -- 自動清理 7 天前 binlog
max_binlog_size = 100M -- 單文件上限,防止過大
systemctl restart mysqld
# 驗證
mysql -u root -p -e "SHOW MASTER STATUS\G"
# 記下 File (如 mysql-bin.000001) 和 Position (如 1374)
my.cnf [mysqld][mysqld]
server-id = 2
log-bin = /var/log/mysql/mysql-bin.log -- 從庫也開啟 binlog,利於級聯/備份
relay-log = /var/log/mysql/relay-bin.log -- 獨立 relay log 路徑
read-only = 1 -- 只讀模式防誤寫
replicate-do-db = test -- 只同步 test
replicate-ignore-db = mysql -- 忽略系統庫
master-info-repository = TABLE -- 5.6+ 推薦存表,更安全
relay-log-info-repository = TABLE
systemctl restart mysqld
# 1. Master 導出 (單庫、含 GTID/位置)
mysqldump -u root -p --single-transaction --master-data=2 \
--databases test > /tmp/test_master.sql
# 2. 複製到 Slave
scp /tmp/test_master.sql 192.168.1.101:/tmp/
# 3. Slave 建庫並導入
mysql -u root -p -e "CREATE DATABASE IF NOT EXISTS test;"
mysql -u root -p test < /tmp/test_master.sql
熱備份替代方案:xtrabackup 物理備份 + --slave-info 避免鎖表,適合大數據量 (TB 級)。
mysql -u root -p -e "
CHANGE MASTER TO
MASTER_HOST='192.168.1.100',
MASTER_USER='repl_user',
MASTER_PASSWORD='ReplPass123!',
MASTER_PORT=3306,
MASTER_LOG_FILE='mysql-bin.000001', -- Master SHOW MASTER STATUS 的 File
MASTER_LOG_POS=1374, -- Master 的 Position
MASTER_CONNECT_RETRY=60;
START SLAVE;"
# Slave 狀態
mysql -u root -p -e "SHOW SLAVE STATUS\G"
# 關鍵指標:
# Slave_IO_Running: Yes
# Slave_SQL_Running: Yes
# Seconds_Behind_Master: 0
# Master_Log_File / Read_Master_Log_Pos 與 Master 一致
# Master 狀態
mysql -u root -p -e "SHOW MASTER STATUS\G"
# 執行寫入測試
mysql -u root -p -e "USE test; INSERT INTO t VALUES (NOW());"
# Slave 同步查詢
mysql -u root -p -e "USE test; SELECT * FROM t ORDER BY id DESC LIMIT 1;"
| 現象 | 原因 | 處置 |
|---|---|---|
| Slave_SQL_Running=No | 從庫誤寫、衝突、事務回滾 | 1) STOP SLAVE; SET GLOBAL SQL_SLAVE_SKIP_COUNTER=1; START SLAVE; 2) 重新同步 (見下) |
| Slave_IO_Running=No | 網路斷開、認證失敗、Master binlog 被清理 | 檢查網路/賬號/防火牆;CHANGE MASTER TO MASTER_LOG_FILE=..., MASTER_LOG_POS=...; 重新指定位置 |
| Seconds_Behind_Master=NULL | SQL 線程停止 | 同上處理 SQL 線程錯誤 |
| 主從數據不一致 | 從庫直寫、非決定性函數、binlog 格式 | pt-table-checksum 校驗 + pt-table-sync 修復;強制 binlog_format=ROW |
gtid_mode=ON + enforce_gtid_consistency=ON,CHANGE MASTER TO MASTER_AUTO_POSITION=1 免維護文件/位置。sync_binlog=1 + innodb_flush_log_at_trx_commit=1 保證零數據丟失。Seconds_Behind_Master > 300 告警、Slave_*_Running != Yes 告警、Relay_Log_Space 過大告警。MASTER_DELAY=3600 的延遲從庫,防誤刪/誤更新 1 小時內可回滾。主從複製是 MySQL 高可用與讀寫分離的基石。標準化配置、自動化部署 (Ansible/Terraform)、持續監控與定期演練切換,才能在故障發生時從容應對。