1. 程式人生 > >FAQ系列 | 如何保證主從復制數據一致性(轉)

FAQ系列 | 如何保證主從復制數據一致性(轉)

主從 relay_log 磁盤 沒有 mysql主從 ignore checksum sla 多節點

導讀

MySQL主從復制環境中,如何才能保證主從數據的一致性呢?

關於主從復制

現在常用的MySQL高可用方案,十有八九是基於 MySQL的主從復制(replication)來設計的,包括常規的一主一從、雙主模式,或者半同步復制(semi-sync replication)。

我們常常把MySQL replication說成是MySQL同步(sync),但事實上這個過程是異步(async)的。大概過程是這樣的:

  1. 在master上提交事務後,並且寫入binlog,返回事務成功標記;
  2. 將binlog發送到slave,轉儲成relay log;
  3. 在slave上再將relay log讀取出來應用。

步驟1和步驟3之間是異步進行的,無需等待確認各自的狀態,所以說MySQL replication是異步的。

MySQL semi-sync replication在之前的基礎上做了加強完善,整個流程變成了下面這樣:

  1. 首先,master和至少一個slave都要啟用semi-sync replication模式;
  2. 某個slave連接到master時,會主動告知當前自己是否處於semi-sync模式;
  3. 在master上提交事務後,寫入binlog後,還需要通知至少一個slave收到該事務,等待寫入relay log並成功刷新到磁盤後,向master發送“slave節點已完成該事務”確認通知;
  4. master收到上述通知後,才可以真正完成該事務提交,返回事務成功標記;
  5. 在上述步驟中,當slave向master發送通知時間超過rpl_semi_sync_master_timeout設定值時,主從關系會從semi-sync模式自動調整成為傳統的異步復制模式。

半同步復制看起來很美好有木有,但如果網絡質量不高,是不是出現抖動,觸發上述第5條的情況,會從半同步復制降級為普通復制;此外,采用半同步復制,會導致master上的tps性能下降非常嚴重,最嚴重的情況下可能會損失50%以上。

這樣來看,除非需要非常嚴格保證數據一致性等迫不得已的場景,就不太建議使用半同步復制了。當然了,事實上我們也可以通過加強程序端的邏輯控制,來避免主從數據不一致時發生邏輯錯誤,比如說如果在從上讀取到的數據和主不一致的話,那麽就觸發主從間的一次數據修復工作。或者,我們也可以用 pt-table-checksum & pt-table-sync 兩個工具來校驗並修復數據,只要運行頻率適當,是可行的。

真想要提高多節點間的數據一致性,可以考慮采用PXC方案。現在已知用PXC規模較大的有qunar、sohu,如果團隊裏初期沒有人能比較專註PXC的話,還是要謹慎些,畢竟和傳統的主從復制差異很大,出現問題時需要花費更多精力去排查解決。

如何保證主從復制數據一致性

上面說完了異步復制、半同步復制、PXC,我們回到主題:在常規的主從復制場景裏,如何能保證主從數據的一致性,不要出現數據丟失等問題呢?

在MySQL中,一次事務提交後,需要寫undo、寫redo、寫binlog,寫數據文件等等。在這個過程中,可能在某個步驟發生crash,就有可能導致主從數據的不一致。為了避免這種情況,我們需要調整主從上面相關選項配置,確保即便發生crash了,也不能發生主從復制的數據丟失。

1. 在master上修改配置

innodb_flush_log_at_trx_commit = 1
sync_binlog = 1

上述兩個選項的作用是:保證每次事務提交後,都能實時刷新到磁盤中,尤其是確保每次事務對應的binlog都能及時刷新到磁盤中,只要有了binlog,InnoDB就有辦法做數據恢復,不至於導致主從復制的數據丟失。

2. 在slave上修改配置

master_info_repository = "TABLE"
relay_log_info_repository = "TABLE"
relay_log_recovery = 1

上述前兩個選項的作用是:確保在slave上和復制相關的元數據表也采用InnoDB引擎,受到InnoDB事務安全的保護,而後一個選項的作用是開啟relay log自動修復機制,發生crash時,會自動判斷哪些relay log需要重新從master上抓取回來再次應用,以此避免部分數據丟失的可能性。

通過上面幾個選項的調整,就可以確保主從復制數據不會發生丟失了。但是,這並不能保證主從數據的絕對一致性,因為,有可能設置了ignore\do\rewrite等replication規則,或者某些SQL本身存在不確定因素,或者人為在slave上修改數據,最終導致主從數據不一致。這種情況下,可以采用pt-table-checksum 和 pt-table-sync 工具來進行數據的校驗和修復。

FAQ系列 | 如何保證主從復制數據一致性(轉)