1. 程式人生 > >【20180306】MySQL關於GTID的一些隨筆

【20180306】MySQL關於GTID的一些隨筆

gtid binlog mysql.gtid_executed Previous gtid Event

關於MySQL GTID的一些信息
  1. GTID持久化介質有倆個,一個是TABLE mysql.gtid_executed 表,另外一個是binlog日誌。
  2. TABLE mysql.gtid_executed表內的gtid信息並不是實時更新的,只有在binlog二進制日誌進行切割的時候才會記錄到表mysql.gtid_executed中。
  3. binlog二進制日誌中的gtid信息是在commit之後生成的,並且這個時候還會生成last commit和seqeue number(這倆個值和MySQL的group commit以及並行復制有關系)
  4. binlog_gtid_simple_recovery 在沒有開啟這個參數的時候,MySQL重啟或者恢復都會掃描全部的binlog獲取gtid_executed信息,這樣做耗時會很長。開啟這個參數之後MySQL只會掃描第一個binlog和最後一個binlog文件。還有一個需要註意的是在中途開啟GTID的時候,也會掃描前面所有的binlog直到獲取得到
  5. sql_log_bin 支持session級別的動態修改,關閉這個參數之後,那麽在當前session並不會產生GTID。
  6. GTID主從復制。
    • 在主庫關閉binlog之後不會產生gtid;在從庫關閉binlog,那麽gtid_executed和gtid_purged和TABLE mysql.gtid_executed是實時更新的。
    • reset master 會清楚所有的binlog日誌,也會清楚所有的gtid_executed和gtid_purged信息。在set global gtid_purged信息的時候需要註意gtid_executed必須為空,並且設置的時候完成之後gtid_purged和gtid_exectued的值是一致的。
  7. Previous gtid Event是包含在每一個binlog的開頭用於描述所有以前binlog所包含的全部Gtid的一個集合(包括已經刪除的binlog)。在5.6中如果不開啟Gtid,那麽binlog是不會包含這個Previous gtid Event的,但是在5.7中不開啟Gtid也會包含這個Previous gtid Event,實際這一點的改變其意義也是非常巨大,簡單的說他為快速掃描binlog(binlog_gtid_simple_recovery=ture)獲得正確Gtid集合提供了基礎,否則將會掃描大量的binlog,從而浪費I/O性能,這是5.6中一個非常嚴重的問題。還有一個需要註意的問題就是,在沒有開啟GTID的時候,Previous gtid Event的值顯示的empty,這個時候中途開啟GTID的話,MySQL重啟讀取binlog獲取gtid_executed信息的話還是會重新讀取舊的binlog直到Previous gtid Event和獲取GTID event.
  8. gtid_mode 的值每一次在線修改都會照成binlog的切割,如果發生binlog刪除也能夠依托 Previous gtid Event快速準確的找到gtid_purged(Gtid_state.lost_gtids)
  9. show slave status 中的數據是從內存中讀取的。relay_log_info_repository 為TABLE的時候show slave status和table的數據的可能不一致。主要是因為非事務引擎還是會遵守Sync_relay_log_info寫到TABLE中的頻率。
  10. mysql.gtid_executed表示5.7.5才開始的一個優化,在沒有這個表之前gtid持久化介質就只有binlog,但是針對於復制中的slave有時候並不需要設置級聯主從,所以沒有必要開啟log_slave_update參數,沒有開啟的這個參數的話就會減少了磁盤和IO。減輕了負擔,提高了性能。

問題:

  1. 重啟或者恢復gtid_executed和gtid_purged的值是從TABLE mysql.gtid_executed中獲取得到還是從binlog二進制中獲取得到的。
    • 數據庫重啟會分別去讀取binlog和mysql.gtid_executed中信息,但是主要還是以binlog為主。
  2. mysqldump備份沒有設置--set-gtid-purged=OFF會備份的時候set @SESSION.SQL_LOG_\BIN=0,這個時候後續的所有操作都不會記錄在binlog當中去,並且也不會生成GTID;而且還會設置SET @@GLOBAL.GTID_PURGED的值。
    • 在這裏還需要註意的一點就是進行全量的備份的時候也會備份mysql.executed表的信息。這裏需要註意的有一點:在進行備份的時候並不會對binlog進行切割,但是由於mysql.gtid_executed記錄的GTID信息並不是實時的,所以導致備份恢復的時候恢復mysql.gtid_executed表內的值比實際上gtid_executed和gtid_purged值小於或者等於,這個時候有因為恢復的時候不會生成binlog,導致TABLE mysql.gtid_executed的值和實際上gtid_executed和gtid_purged的值不相同。
    • 這個時候能重啟從庫,從庫就會報錯1236錯誤。

【20180306】MySQL關於GTID的一些隨筆