灯下哥谭 灯下哥谭
首页
关于
  • Hermes Agent 平台
  • Claude Code
  • OpenClaw
  • GPU 推理节点运维
  • DeepSeek Harness
  • MySQL 运维知识地图
  • Elasticsearch 运维知识地图
  • Redis 运维知识地图
  • TiDB 体系
  • DBA 常用 SQL 与命令
  • Nginx 运维知识地图
  • Prometheus 监控
  • Docker
  • Systemd
  • Iptables
  • Firewalld
  • Sshd
  • MySQL8 运维 SOP 手册
  • MySQL 实战 45 讲(读书笔记)
  • 分类
  • 标签
  • 归档
GitHub (opens new window)

灯下哥谭

灯还亮着
首页
关于
  • Hermes Agent 平台
  • Claude Code
  • OpenClaw
  • GPU 推理节点运维
  • DeepSeek Harness
  • MySQL 运维知识地图
  • Elasticsearch 运维知识地图
  • Redis 运维知识地图
  • TiDB 体系
  • DBA 常用 SQL 与命令
  • Nginx 运维知识地图
  • Prometheus 监控
  • Docker
  • Systemd
  • Iptables
  • Firewalld
  • Sshd
  • MySQL8 运维 SOP 手册
  • MySQL 实战 45 讲(读书笔记)
  • 分类
  • 标签
  • 归档
GitHub (opens new window)
  • MySQL8-SOP

  • 课程笔记

    • MySQL实战45讲

      • MySQL45讲学习笔记
      • MySQL基础架构
      • MySQL日志系统 (Redo Log 与 Binlog)
      • MySQL事务隔离级别的实现原理
      • MySQL索引原理与优化
      • MySQL锁机制详解
      • MySQL事务与MVCC机制
      • MySQL普通索引与唯一索引的选择
      • MySQL优化器如何选择索引
      • MySQL字符串字段索引优化
      • MySQL抖动刷脏页
      • 表空间管理与回收
      • COUNT函数详解
      • 日志索引
      • orderby工作原理
      • 随机排序实现
      • SQL性能差异函数与转换
      • 慢查询分析锁与版本
      • 幻读与间隙锁
      • 加锁规则分析
      • 应急性能优化方法
      • 数据持久化保证
      • 主备一致性原理
      • 高可用架构与切换
      • 备库延迟分析与优化
      • 主备切换GTID
        • 1. GTID基础概念
          • 1.1 GTID的定义
          • 1.2 GTID的工作原理
          • 1.3 GTID的优势
        • 2. GTID在主备切换中的作用
          • 2.1 GTID切换流程
          • 2.2 GTID切换的优势
        • 3. GTID切换的具体步骤
          • 3.1 故障切换准备
          • 3.2 从库提升为主库
          • 3.3 重新配置其他从库
        • 4. GTID切换的高级技巧
          • 4.1 GTID集合操作
          • 4.2 GTID一致性检查
          • 4.3 GTID故障恢复
        • 5. GTID切换常见问题及解决方案
          • 5.1 GTID冲突问题
          • 5.2 GTID不一致问题
          • 5.3 GTID切换后数据丢失
        • 6. GTID切换的最佳实践
          • 6.1 切换前准备工作
          • 6.2 安全切换流程
          • 6.3 切换后验证
        • 7. GTID与不同架构的适配
          • 7.1 一主一备架构
          • 7.2 一主多从架构
          • 7.3 双主架构
        • 8. GTID监控与告警
          • 8.1 GTID状态监控
          • 8.2 GTID异常告警
        • 9. GTID切换的性能考虑
          • 9.1 切换时间优化
          • 9.2 内存和IO优化
        • 10. 总结
      • 读写分离实践与问题
      • 数据库健康检查
      • 锁与死锁
      • 数据误删恢复
      • Kill命令详解
      • 查询与内存使用分析
      • Join原理与选择
      • 临时表原理与应用
      • 内部临时表详解
      • Memory引擎详解
      • 自增ID详解
      • Insert加锁分析
      • 表复制方法比较
      • Grant与权限管理
      • 分区表详解
      • SQL语句中的Join问题
      • 自增ID用尽问题
  • 专题系列
  • 课程笔记
  • MySQL实战45讲
灯下哥谭
2024-07-27
目录

主备切换GTID

# 主备切换GTID

全球事务标识(GTID)是MySQL 5.6引入的重要特性,它极大地简化了主备复制架构中的主备切换过程。本文将深入探讨GTID在主备切换中的应用和最佳实践。

# 1. GTID基础概念

# 1.1 GTID的定义

全局事务标识(Global Transaction Identifier)是MySQL中用于唯一标识事务的标识符,格式为:

GTID = server_uuid:gno
-- 例如:GTID=12345678-1234-1234-1234-123456789012:100
1
2

其中:

  • server_uuid:服务器唯一标识符
  • gno:事务编号(全局序号)

# 1.2 GTID的工作原理

-- 启用GTID
SET GLOBAL gtid_mode = ON;
SET GLOBAL enforce_gtid_consistency = ON;

-- 查看GTID状态
SHOW GLOBAL VARIABLES LIKE 'gtid_mode';
SHOW MASTER STATUS;
SHOW SLAVE STATUS\G
1
2
3
4
5
6
7
8

# 1.3 GTID的优势

  1. 简化主备切换:无需手动查找位点
  2. 自动处理重复:避免重复应用事务
  3. 增强可靠性:提供更强的数据一致性保障
  4. 简化故障恢复:快速定位缺失的事务

# 2. GTID在主备切换中的作用

# 2.1 GTID切换流程

-- 主备切换基本流程
1. 停止从库复制
STOP SLAVE;

2. 检查从库状态
SHOW SLAVE STATUS\G

3. 确认主备同步状态
SELECT @@gtid_executed;
SELECT @@gtid_purged;

4. 提升从库为主库
SET GLOBAL read_only = OFF;

5. 重新配置其他从库
CHANGE MASTER TO 
MASTER_HOST='new_master_host',
MASTER_PORT=3306,
MASTER_USER='repl_user',
MASTER_PASSWORD='repl_password',
MASTER_AUTO_POSITION=1;

6. 启动复制
START SLAVE;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24

# 2.2 GTID切换的优势

-- 传统切换方式(基于位点)
CHANGE MASTER TO
MASTER_HOST='master_host',
MASTER_PORT=3306,
MASTER_USER='repl_user',
MASTER_PASSWORD='repl_password',
MASTER_LOG_FILE='master-bin.000001',
MASTER_LOG_POS=12345;

-- GTID切换方式(简化)
CHANGE MASTER TO
MASTER_HOST='master_host',
MASTER_PORT=3306,
MASTER_USER='repl_user',
MASTER_PASSWORD='repl_password',
MASTER_AUTO_POSITION=1;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

# 3. GTID切换的具体步骤

# 3.1 故障切换准备

-- 1. 检查当前状态
SHOW MASTER STATUS\G
SHOW SLAVE STATUS\G

-- 2. 查看GTID信息
SELECT @@gtid_executed;
SELECT @@gtid_purged;
SELECT @@gtid_mode;

-- 3. 确保主库状态稳定
FLUSH TABLES WITH READ LOCK;
-- 确保所有事务都已提交
UNLOCK TABLES;
1
2
3
4
5
6
7
8
9
10
11
12
13

# 3.2 从库提升为主库

-- 1. 停止从库复制
STOP SLAVE;

-- 2. 检查从库同步状态
SHOW SLAVE STATUS\G

-- 3. 确认从库已完全同步
SELECT Seconds_Behind_Master FROM INFORMATION_SCHEMA.SLAVE_STATUS;

-- 4. 提升从库为主库
SET GLOBAL read_only = OFF;
SET GLOBAL super_read_only = OFF;

-- 5. 验证主库状态
SELECT @@read_only;
SELECT @@super_read_only;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

# 3.3 重新配置其他从库

-- 1. 停止从库复制
STOP SLAVE;

-- 2. 清理复制配置
RESET SLAVE ALL;

-- 3. 使用GTID重新配置
CHANGE MASTER TO
MASTER_HOST='new_master_host',
MASTER_PORT=3306,
MASTER_USER='repl_user',
MASTER_PASSWORD='repl_password',
MASTER_AUTO_POSITION=1;

-- 4. 启动复制
START SLAVE;

-- 5. 检查复制状态
SHOW SLAVE STATUS\G
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19

# 4. GTID切换的高级技巧

# 4.1 GTID集合操作

-- 查看GTID集合
SELECT @@gtid_executed;
SELECT @@gtid_purged;

-- GTID集合的比较
SELECT GTID_SUBSET('12345678-1234-1234-1234-123456789012:1-100', 
                   '12345678-1234-1234-1234-123456789012:1-50');

-- GTID集合的差集计算
SELECT GTID_SUBTRACT('12345678-1234-1234-1234-123456789012:1-100', 
                     '12345678-1234-1234-1234-123456789012:1-50');
1
2
3
4
5
6
7
8
9
10
11

# 4.2 GTID一致性检查

-- 检查主备GTID一致性
SELECT 
    @@gtid_executed as executed_gtid_set,
    @@gtid_purged as purged_gtid_set;

-- 确保从库的GTID集合是主库的子集
SELECT GTID_SUBSET(@@gtid_executed, (SELECT @@gtid_executed FROM master));
1
2
3
4
5
6
7

# 4.3 GTID故障恢复

-- 1. 如果从库GTID丢失,需要重新初始化
STOP SLAVE;
RESET SLAVE ALL;

-- 2. 重新从主库获取数据
-- 可以使用mysqldump或物理备份

-- 3. 使用GTID重新配置
CHANGE MASTER TO
MASTER_HOST='master_host',
MASTER_PORT=3306,
MASTER_USER='repl_user',
MASTER_PASSWORD='repl_password',
MASTER_AUTO_POSITION=1;

START SLAVE;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16

# 5. GTID切换常见问题及解决方案

# 5.1 GTID冲突问题

-- 问题:GTID冲突
-- 解决方案1:跳过特定GTID
SET GLOBAL sql_slave_skip_counter = 1;
START SLAVE;

-- 解决方案2:使用GTID跳过
SELECT @@gtid_executed;
-- 手动跳过特定GTID
SELECT GTID_SUBTRACT(@@gtid_executed, '12345678-1234-1234-1234-123456789012:100');
1
2
3
4
5
6
7
8
9

# 5.2 GTID不一致问题

-- 问题:主备GTID不一致
-- 解决方案:使用purge清理
SET GLOBAL gtid_purged = '12345678-1234-1234-1234-123456789012:1-50';

-- 或者重新初始化
STOP SLAVE;
RESET SLAVE ALL;
-- 重新进行数据同步
1
2
3
4
5
6
7
8

# 5.3 GTID切换后数据丢失

-- 预防措施:在切换前检查数据完整性
SELECT COUNT(*) FROM important_table;

-- 切换后验证数据
SELECT COUNT(*) FROM important_table;

-- 检查GTID执行情况
SELECT @@gtid_executed;
1
2
3
4
5
6
7
8

# 6. GTID切换的最佳实践

# 6.1 切换前准备工作

-- 1. 检查系统状态
SHOW STATUS LIKE 'Threads_connected';
SHOW STATUS LIKE 'Questions';
SHOW STATUS LIKE 'Com_select';

-- 2. 检查GTID配置
SHOW VARIABLES LIKE 'gtid_mode';
SHOW VARIABLES LIKE 'enforce_gtid_consistency';

-- 3. 检查复制状态
SHOW SLAVE STATUS\G
SELECT Seconds_Behind_Master FROM INFORMATION_SCHEMA.SLAVE_STATUS;
1
2
3
4
5
6
7
8
9
10
11
12

# 6.2 安全切换流程

-- 安全切换流程
BEGIN;

-- 1. 停止应用层写入
-- 2. 确认当前事务提交
SELECT @@autocommit;

-- 3. 停止从库复制
STOP SLAVE;

-- 4. 检查从库状态
SHOW SLAVE STATUS\G

-- 5. 提升从库为主库
SET GLOBAL read_only = OFF;

-- 6. 重新配置其他从库
CHANGE MASTER TO 
MASTER_AUTO_POSITION=1;

-- 7. 验证新主库状态
SELECT @@read_only;
SHOW MASTER STATUS\G

COMMIT;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25

# 6.3 切换后验证

-- 1. 验证复制状态
SHOW SLAVE STATUS\G
SELECT Seconds_Behind_Master FROM INFORMATION_SCHEMA.SLAVE_STATUS;

-- 2. 验证数据一致性
SELECT COUNT(*) FROM test_table;
SELECT @@gtid_executed;

-- 3. 测试基本功能
INSERT INTO test_table (name) VALUES ('test');
SELECT * FROM test_table WHERE name = 'test';
DELETE FROM test_table WHERE name = 'test';
1
2
3
4
5
6
7
8
9
10
11
12

# 7. GTID与不同架构的适配

# 7.1 一主一备架构

-- 一主一备切换示例
-- 主库故障时
STOP SLAVE ON slave;
SET GLOBAL read_only = OFF;  -- 提升从库为主库
-- 重新配置其他从库指向新主库
1
2
3
4
5

# 7.2 一主多从架构

-- 一主多从切换示例
-- 1. 选择一个从库提升为主库
STOP SLAVE ON slave;
SET GLOBAL read_only = OFF;

-- 2. 重新配置其他从库
CHANGE MASTER TO MASTER_AUTO_POSITION=1;
START SLAVE;

-- 3. 更新应用连接配置
1
2
3
4
5
6
7
8
9
10

# 7.3 双主架构

-- 双主切换示例
-- 需要更复杂的协调机制
-- 1. 确保两个主库数据一致性
-- 2. 选择一个主库作为新的主库
-- 3. 重新配置另一个主库
1
2
3
4
5

# 8. GTID监控与告警

# 8.1 GTID状态监控

-- 创建GTID监控脚本
DELIMITER //
CREATE PROCEDURE monitor_gtid_status()
BEGIN
    DECLARE executed_gtid VARCHAR(1000);
    DECLARE purged_gtid VARCHAR(1000);
    DECLARE delay_seconds INT;
    
    SELECT @@gtid_executed INTO executed_gtid;
    SELECT @@gtid_purged INTO purged_gtid;
    SELECT Seconds_Behind_Master INTO delay_seconds 
    FROM INFORMATION_SCHEMA.SLAVE_STATUS;
    
    -- 记录监控信息
    INSERT INTO gtid_monitor_log (timestamp, executed_gtid, purged_gtid, delay_seconds) 
    VALUES (NOW(), executed_gtid, purged_gtid, delay_seconds);
END //
DELIMITER ;
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18

# 8.2 GTID异常告警

-- GTID异常检测
SELECT 
    @@gtid_executed as executed_gtid,
    @@gtid_purged as purged_gtid,
    Seconds_Behind_Master as delay_seconds,
    CASE 
        WHEN Seconds_Behind_Master > 30 THEN 'HIGH_DELAY'
        WHEN Seconds_Behind_Master > 10 THEN 'MEDIUM_DELAY'
        ELSE 'NORMAL'
    END as delay_status
FROM INFORMATION_SCHEMA.SLAVE_STATUS;
1
2
3
4
5
6
7
8
9
10
11

# 9. GTID切换的性能考虑

# 9.1 切换时间优化

-- 优化切换时间的配置
SET GLOBAL slave_net_timeout = 60;
SET GLOBAL slave_parallel_workers = 8;
SET GLOBAL slave_parallel_type = 'LOGICAL_CLOCK';

-- 查看并行复制状态
SHOW VARIABLES LIKE 'slave_parallel%';
1
2
3
4
5
6
7

# 9.2 内存和IO优化

-- 优化IO性能
SET GLOBAL innodb_flush_log_at_trx_commit = 2;
SET GLOBAL sync_binlog = 100;
SET GLOBAL innodb_io_capacity = 2000;

-- 优化内存使用
SET GLOBAL tmp_table_size = 256*1024*1024;
SET GLOBAL max_heap_table_size = 256*1024*1024;
1
2
3
4
5
6
7
8

# 10. 总结

GTID技术的引入极大简化了MySQL主备切换的复杂性,提供了更可靠的事务一致性保障。通过合理使用GTID,可以:

  1. 简化切换流程:无需手动查找和定位位点
  2. 提高切换效率:自动处理事务重复和缺失
  3. 增强可靠性:提供更强的数据一致性保障
  4. 降低维护成本:减少人为操作错误

在实际应用中,应该:

  • 在生产环境启用GTID
  • 建立完善的监控体系
  • 制定详细的切换预案
  • 定期演练切换流程
  • 做好数据备份和恢复准备

通过这些措施,可以确保在主备切换过程中最小化业务影响,保障系统的高可用性和数据安全性。

#学习笔记#MySQL
上次更新: 9/11/2026

← 备库延迟分析与优化 读写分离实践与问题→

最近更新
01
DeepSeek Harness 实战 06|学习笔记:插件、工具、技能不在同一个维度上 原创
09-11
02
DeepSeek Harness 实战 05|让两个编码 Agent 共用一份长期记忆 原创
09-09
03
DeepSeek Harness 实战 04|学习笔记:从「已知限制」里读出三处设计张力 原创
09-08
更多文章>
Theme by Vdoing
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式