Beginning with MySQL 5.7.5, GTIDs are stored in a table named gtid_executed, in the mysql database. A row in this table contains, for each GTID or set of GTIDs that it represents, the UUID of the originating server, and the starting and ending transaction IDs of the set; for a row referencing only a single GTID, these last two values are the same. 也就是說gtid_executed表是Gtid持久化的一個工具,如前文所描述Gtid_state中的get_executed_gtids/get_lost_gtids/get_gtids_only_in_table/get_previous_gtids_logged這些數(shù)據(jù)都是存儲在內(nèi)存中的,那么在數(shù)據(jù)庫重啟后需要進行初始化,那么這需要讀取Gtid持久化的介質(zhì),我們可以發(fā)現(xiàn)gtid_executed是一個innodb表建表語句如下,并且我們可以手動更改它,但是千萬不要這么干:
Table: gtid_executed Create Table: CREATE TABLE `gtid_executed` ( `source_uuid` char(36) NOT NULL COMMENT 'uuid of the source where the transaction was originally executed.', `interval_start` bigint(20) NOT NULL COMMENT 'First number of interval.', `interval_end` bigint(20) NOT NULL COMMENT 'Last number of interval.', PRIMARY KEY (`source_uuid`,`interval_start`) ) ENGINE=InnoDB DEFAULT CHARSET=utf8 STATS_PERSISTENT=0 那么在5.7.5以前沒有gtid_executed表不是也沒有問題嗎?其實除了gtid_executed表以外我們還有一個Gtid持久化的介質(zhì)那就是binlog中的Gtid event。所以總結(jié)一下Gtid持久化介質(zhì):
Step 3: Restart both servers with GTIDs enabled. To enable binary logging with global transaction identifiers, each server must be started with GTID mode, binary logging, slave update logging enabled, and with statements that are unsafe for GTID-based replication disabled. In addition, you should prevent unwanted or accidental updates from being performed on either server by starting both in read-only mode. This means that both servers must be started with (at least) the options shown in the following invocation of mysqld_safe: shell> mysqld_safe --gtid_mode=ON --log-bin --log-slave-updates --enforce-gtid-consistency & 開啟binlog同時設置設置log_slave_updates=ture必然造成一個問題,實際上從庫很多時候我們是不需要做級聯(lián)slave,設置log_slave_updates=ture會造成需要額外的空間和性能開銷。自然這種情況下我們需要另外的一種Gtid持久化介質(zhì),而并不是binlog中的Gtid event。為了解決這個問題,5.7中gtid_executed表應運而生了。然而gtid_executed表是否需要實時更新呢?顯然在slave端不開啟binlog或者開啟binlog不設置log_slave_updates=ture的情況下它需要實時更新,因為I/O thread執(zhí)行過得Gtid是必須持久化的,而在主庫上因為有binlog的Gtid event的存在他是不需要實時更新的,這樣不同的對待方式也能夠減輕負擔提高性能。 同時在官方文檔上也有相關描述它分為是否開始binlog進行描述,但是其描述并不是最詳細的。所以這部分在后面我會進行詳細描述。
When binlog_gtid_simple_recovery=TRUE, which is the default in MySQL 5.7.7 and later, the server iterates only the oldest and the newest binary log files and the values of gtid_purged and gtid_executed are computed based only on Previous_gtids_log_event or Gtid_log_event found in these files. This ensures only two binary log files are iterated during server restart or when binary logs are being purged 當然這部分也會在后面進行詳細的描述,這里只是簡單提一下。那么我們通過mysqlbinlog 和infobin工具分別確認這一點。
5.6. 26 不開啟Gtid mysqlbinlog:
*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=1*/; /*!50003 SET @OLD_COMPLETION_TYPE=@@COMPLETION_TYPE,COMPLETION_TYPE=0*/; DELIMITER /*!*/; # at 4 #171211 16:20:10 server id 20155 end_log_pos 120 CRC32 0x12617db7 Start: binlog v 4, server v 5.6.26-74.0-log created 171211 16:20:10 # Warning: this binlog is either in use or was not closed properly. # at 120 #171211 16:20:14 server id 20155 end_log_pos 192 CRC32 0x696752cb Query thread_id=30 infobin:
/*!50530 SET @@SESSION.PSEUDO_SLAVE_MODE=1*/; /*!50003 SET @OLD_COMPLETION_TYPE=@@COMPLETION_TYPE,COMPLETION_TYPE=0*/; DELIMITER /*!*/; # at 4 #171211 16:26:49 server id 1 end_log_pos 123 CRC32 0xf9a36298 Start: binlog v 4, server v 5.7.14-7-debug-log created 171211 16:26:49 # Warning: this binlog is either in use or was not closed properly. # at 123 #171211 16:26:49 server id 1 end_log_pos 194 CRC32 0x5865633f **Previous-GTIDs** # da267088-9c22-11e7-ab56-5254008768e3:1-32 # at 194 infobin: