Mysql-Replication

硬重啟導致 MySQL 複製中斷

  • August 27, 2015

我的複制設置遇到問題。在正常情況下,它按預期執行,但如果遇到硬重啟(我拉電源線),它就會中斷。

設置

該設置由兩個伺服器組成,server-1server-2。複製設置是循環複製。兩台伺服器都是從另一台主機複製的從機,就好像它是主機一樣。

軟體

  • 紅帽 6.5
  • MySQL 5.1.73-3
  • MySQL 庫 5.1.73-3
  • MySQL 伺服器 5.1.73-3

冗餘配置

server-1的複製配置如下,並為server-2鏡像:

GRANT REPLICATION SLAVE ON *.* TO 'replicant';
FLUSH TABLES WITH READ LOCK;"

#Use "SHOW MASTER STATUS \G;" to determine log position and log file

UNLOCK TABLES;

# set status on slave server using the values retieved earlier
CHANGE MASTER TO MASTER_HOST='server-2', MASTER_USER='replicant', MASTER_LOG_FILE='[log file]', MASTER_LOG_POS=[log pos];"

START SLAVE;

錯誤資訊

當server-2遇到硬重啟並且複制中斷時,將檢索此資訊。

server-1 從屬狀態

*************************** 1. row ***************************
              Slave_IO_State: Waiting for master to send event
                 Master_Host: server-2
                 Master_User: replicant
                 Master_Port: 3306
               Connect_Retry: 60
             Master_Log_File: bin.000004
         Read_Master_Log_Pos: 37550
              Relay_Log_File: relay.000427
               Relay_Log_Pos: 245
       Relay_Master_Log_File: bin.000004
            Slave_IO_Running: Yes
           Slave_SQL_Running: Yes
             Replicate_Do_DB: 
         Replicate_Ignore_DB: 
          Replicate_Do_Table: 
      Replicate_Ignore_Table: 
     Replicate_Wild_Do_Table: 
 Replicate_Wild_Ignore_Table: 
                  Last_Errno: 0
                  Last_Error: 
                Skip_Counter: 0
         Exec_Master_Log_Pos: 37550
             Relay_Log_Space: 529
             Until_Condition: None
              Until_Log_File: 
               Until_Log_Pos: 0
          Master_SSL_Allowed: No
          Master_SSL_CA_File: 
          Master_SSL_CA_Path: 
             Master_SSL_Cert: 
           Master_SSL_Cipher: 
              Master_SSL_Key: 
       Seconds_Behind_Master: 0
Master_SSL_Verify_Server_Cert: No
               Last_IO_Errno: 0
               Last_IO_Error: 
              Last_SQL_Errno: 0
              Last_SQL_Error: 

server-2 從屬狀態

*************************** 1. row ***************************
              Slave_IO_State: 
                 Master_Host: server-1
                 Master_User: replicant
                 Master_Port: 3306
               Connect_Retry: 60
             Master_Log_File: bin.000002
         Read_Master_Log_Pos: 7208
              Relay_Log_File: relay.000010
               Relay_Log_Pos: 245
       Relay_Master_Log_File: bin.000002
            Slave_IO_Running: No
           Slave_SQL_Running: No
             Replicate_Do_DB: 
         Replicate_Ignore_DB: 
          Replicate_Do_Table: 
      Replicate_Ignore_Table: 
     Replicate_Wild_Do_Table: 
 Replicate_Wild_Ignore_Table: 
                  Last_Errno: 0
                  Last_Error: 
                Skip_Counter: 0
         Exec_Master_Log_Pos: 7208
             Relay_Log_Space: 529
             Until_Condition: None
              Until_Log_File: 
               Until_Log_Pos: 0
          Master_SSL_Allowed: No
          Master_SSL_CA_File: 
          Master_SSL_CA_Path: 
             Master_SSL_Cert: 
           Master_SSL_Cipher: 
              Master_SSL_Key: 
       Seconds_Behind_Master: NULL
Master_SSL_Verify_Server_Cert: No
               Last_IO_Errno: 0
               Last_IO_Error: 
              Last_SQL_Errno: 0
              Last_SQL_Error: 

來自 server-2 mysql-log-error.log 的相關資訊

這些日誌來自導致複製失敗的引導

150821 12:52:35 mysqld_safe Starting mysqld daemon with databases from /var/lib/mysql
150821 12:52:35  InnoDB: Initializing buffer pool, size = 8.0M
150821 12:52:35  InnoDB: Completed initialization of buffer pool
InnoDB: The log sequence number in ibdata files does not match
InnoDB: the log sequence number in the ib_logfiles!
150821 12:52:35  InnoDB: Database was not shut down normally!
InnoDB: Starting crash recovery.
InnoDB: Reading tablespace information from the .ibd files...
InnoDB: Restoring possible half-written data pages from the doublewrite
InnoDB: buffer...
InnoDB: Last MySQL binlog file position 0 106, file name /var/lib/mysql/bin.000002
150821 12:52:35  InnoDB: Started; log sequence number 0 259987
150821 12:52:35 [Note] Recovering after a crash using /var/lib/mysql/bin
150821 12:52:35 [Note] Starting crash recovery...
150821 12:52:35 [Note] Crash recovery finished.
150821 12:52:35 [ERROR] log  listed in the index, but failed to stat
150821 12:52:35 [ERROR] Error counting relay log space
150821 12:52:35 [ERROR] Failed to initialize the master info structure
150821 12:52:35 [Note] Event Scheduler: Loaded 0 events
150821 12:52:35 [Note] /usr/libexec/mysqld: ready for connections.
Version: '5.1.73-log'  socket: '/var/lib/mysql/mysql.sock'  port: 3306  Source distribution  

複製訪問

為了收集資訊和解決問題,我嘗試的其中一項是嘗試代表複製使用者從**server-2訪問****server-1 。**那次嘗試沒有成功,我收到了“拒絕訪問”消息。

因此,我查看了server-2上的授權,並獲得了以下資訊。

SHOW GRANTS FOR "replicant"@"server-1";
ERROR 1141 (42000) at line 1: There is no such grant defined for user 'replicant' on host 'server-1;'

我尋找解決方案的嘗試

到目前為止,我試圖解決這個問題的嘗試都沒有結果。無論我嘗試什麼,我總是從 MySQL 得到相同的答案。

ERROR 1201 (HY000) at line 1: Could not initialize master info structure; more error messages can be found in the MySQL error log

當我嘗試“ START SLAVE; ”或“ CHANGE MASTER TO … ”以再次進行複制時,我嘗試過的任何配置、FLUSH、RESET 或日誌操作都會導致此錯誤消息。

複製 server-1

使server-2成為****server-1的副本是有希望的。我讓server-2工作,但server-1無法從server-2複製。我使用以下步驟複製伺服器。

  1. 停止server-2上的 mysqld 服務
  2. 清除server-2上的*/var/lib/mysql/*
  3. rsync */var/lib/mysql/*從server-1server-2
  4. 將server-2上的 master 主機更改為server-1
  5. 在server-2上啟動 mysqld 服務

看起來這可以解決server-2 的問題,但server-1無法從server-2複製。我在server-1的從屬狀態中看到以下內容:

 Slave_IO_state: Waiting to reconnect after a failed master even read
Slave_IO_Running: No

我在server-1的錯誤日誌中找到了這個

[Note] Slave I/O thread: Failed reading log event, reconnecting to retry, log 'FIRST' at position 4
[ERROR] Error reading packet from server: Access denied; you need the REPLICATION SLAVE privilege for this operation ( server_errno=1227)

我已經檢查了兩台伺服器上複製使用者的授權,它們沒有改變。

mysql> SHOW GRANTS FOR 'replicant';
+---------------------------------------------------+
| Grants for replicant@%                            |
+---------------------------------------------------+
| GRANT REPLICATION SLAVE ON *.* TO 'replicant'@'%' |
+---------------------------------------------------+
1 row in set (0.00 sec)

似乎server-1在訪問****server-2上的日誌時遇到問題。我嘗試了以下方法來解決這個問題。

  • 復位主;+*重置奴隸;**在兩台伺服器上,然後使用CHANGE MASTER TO …*再次設置從屬伺服器;.
  • 在rsync之前更改server-1上的MASTER_LOG_FILEMASTER_LOG_POS以匹配****server-1的主狀態。
  • 嘗試我能想到的MASTER_LOG_FILEMASTER_LOG_POS操作的每一種排列。

我繼續解決這個問題,並製定了一個對我有用的解決方案。

解決方案

此解決方案假定server-2是複制中斷的伺服器。如果server-1是損壞的伺服器,則需要鏡像此解決方案。

  1. 禁用兩台伺服器上的傳入連接
  • 顯示完整的處理程序;應該只顯示具有“顯示完整程序列表”狀態的**本地主機連接,也許還有一些**系統使用者**條目

  • 實現此目的的一種方法是為 mysql 服務分配一個新埠,該埠不是預設的 3306,或者如果您正在指定一個埠,請將其更改為其他埠。

    • 例如添加“ port=33060 ”到**$$ mysqld $$**/etc/my.cnf中的部分
  1. 防止複制從屬程序在伺服器啟動時啟動,在兩台伺服器上

  2. 將“ skip-slave-start ”添加到**$$ mysqld $$**/etc/my.cnf中的部分

  3. 重啟mysql伺服器

    • 服務 mysqld 重啟
  4. 重置server-1上的從屬和主配置

  • 復位從機;
  • 復位主;
  1. 在server-1上創建數據庫的副本,並將其複製到server-2

  2. 帶讀鎖的刷新表;

  3. mysqldump –數據庫$$ replicated database $$… > ./dump.sql

  4. 解鎖表;

  5. scp ./dump.sql$$ user $$@server-2:/home/$$ user $$/

  6. 將數據導入到server-2上的數據庫中

  • 以 root 身份,mysql < /home/$$ user $$/dump.sql
  1. 在server-2上重置從屬和主配置
  • 復位從機;
  • 復位主;
  1. 在兩台伺服器上配置複製從屬
  • server-1上:將MASTER 更改為 MASTER_HOST=‘server-2’, MASTER_USER=‘replicant’, MASTER_LOG_FILE=“bin.000001”, MASTER_LOG_POS=1;
  • server-2上:將MASTER 更改為 MASTER_HOST=‘server-1’, MASTER_USER=‘replicant’, MASTER_LOG_FILE=“bin.000001”, MASTER_LOG_POS=1;
  1. 如果您在server-2上收到以下錯誤:錯誤 1201 (HY000): 無法初始化主資訊結構;更多錯誤資訊可以在 MySQL 錯誤日誌中找到
  • 刪除relay mysql 中繼文件,然後再次嘗試步驟67
  • rm -rf /var/lib/relay*
  1. 在兩台伺服器上啟用傳入連接
  • 還原步驟1

  • 重啟mysql伺服器

    • 服務 mysqld 重啟
  1. 在兩台伺服器上啟動複製從屬
  • 啟動奴隸;
  1. 複製現在應該可以工作了。在兩台伺服器上驗證其執行狀況
  • 顯示從屬狀態\G;
    • Slave_IO_State不應指示錯誤
    • Slave_IO_RunningSlave_SQL_Running應該都處於Yes狀態
  1. 清理
  • 從兩台伺服器上

的*/etc/my.cnf*中刪除skip-slave-start條目 + 不需要重啟mysql伺服器

  • 刪除兩台伺服器上的dump.sql文件

引用自:https://serverfault.com/questions/715849