Skip to content

KingBaseES 主备切换

主备切换是 KingBaseES 高可用架构中的重要操作,通过将备库提升为主库,实现系统的高可用性和负载均衡。本文将详细介绍 KingBaseES 主备切换的概念、原理、流程和最佳实践。

主备切换概述

概念

主备切换(Switchover)是指在主库正常运行的情况下,将备库提升为主库,同时将原主库降级为备库的操作。主备切换是一种计划性的操作,通常用于以下场景:

  • 主库维护或升级
  • 负载均衡调整
  • 灾备演练
  • 测试主备切换流程

与故障切换的区别

特性主备切换(Switchover)故障切换(Failover)
触发方式手动触发,计划性操作自动或手动触发,故障时操作
主库状态主库正常运行主库故障或不可用
数据完整性数据零丢失可能存在数据丢失风险
切换时间较长(分钟级)较短(秒级或分钟级)
操作复杂度较高较低

适用场景

  • 主库维护:主库需要进行硬件升级、操作系统升级或数据库版本升级
  • 负载均衡:调整主备库的负载,将读操作分散到多个备库
  • 灾备演练:验证主备切换流程的有效性,提高故障恢复能力
  • 测试环境:测试新功能或配置变更对主备复制的影响

主备切换原理

主备切换的基本原理是:

  1. 确保备库与主库的数据同步
  2. 停止主库的写操作
  3. 提升备库为主库
  4. 重新配置原主库为备库
  5. 恢复数据复制

切换过程中的数据一致性保证

  • 同步复制:确保备库收到并应用所有 WAL 日志后,主库才提交事务
  • WAL 日志完整性检查:切换前检查备库是否已应用所有 WAL 日志
  • 复制延迟检查:确保备库的复制延迟在可接受范围内
  • 切换锁:防止在切换过程中发生并发操作

切换前准备

环境检查

  1. 检查主备库状态

    sql
    -- 检查主库状态
    SELECT pg_is_in_recovery();
    
    -- 检查备库状态
    SELECT pg_is_in_recovery();
    
    -- 检查复制状态
    SELECT * FROM pg_stat_replication;
    
    -- 检查复制延迟
    SELECT pg_wal_lsn_diff(pg_last_wal_receive_lsn(), pg_last_wal_replay_lsn()) AS replay_lag;
  2. 检查数据库日志

    bash
    # 查看主库日志
    tail -n 100 /path/to/kingbase/master/data/log/kingbase.log
    
    # 查看备库日志
    tail -n 100 /path/to/kingbase/standby/data/log/kingbase.log
  3. 检查系统资源

    bash
    # 检查 CPU 和内存使用情况
    top
    
    # 检查磁盘空间
    df -h
    
    # 检查网络状态
    netstat -an

配置检查

  1. 检查主库配置

    sql
    -- 查看主库的 wal_level 配置
    SHOW wal_level;
    
    -- 查看主库的 max_wal_senders 配置
    SHOW max_wal_senders;
    
    -- 查看主库的 synchronous_standby_names 配置
    SHOW synchronous_standby_names;
  2. 检查备库配置

    sql
    -- 查看备库的 hot_standby 配置
    SHOW hot_standby;
    
    -- 查看备库的 primary_conninfo 配置
    SHOW primary_conninfo;

备份准备

  • 确保已完成最近的数据库备份
  • 备份主备库的配置文件
  • 记录当前主备库的状态和配置

切换流程

1. 验证主备复制状态

sql
-- 在主库上执行
SELECT application_name, state, sync_state, 
       pg_wal_lsn_diff(pg_current_wal_lsn(), sent_lsn) AS send_lag,
       pg_wal_lsn_diff(sent_lsn, write_lsn) AS write_lag,
       pg_wal_lsn_diff(write_lsn, flush_lsn) AS flush_lag,
       pg_wal_lsn_diff(flush_lsn, replay_lsn) AS replay_lag
FROM pg_stat_replication;

-- 确保所有备库的 replay_lag 为 0 或在可接受范围内

2. 停止主库的写操作

bash
# 方法一:使用 pg_ctl 停止主库
pg_ctl stop -D /path/to/kingbase/master/data -m fast

# 方法二:使用 SQL 命令停止写操作
# 注意:此方法不会停止主库,只限制写操作
ALTER SYSTEM SET default_transaction_read_only = on;
SELECT pg_reload_conf();

3. 提升备库为主库

bash
# 在备库上执行
pg_ctl promote -D /path/to/kingbase/standby/data

# 或使用 SQL 命令
SELECT pg_promote();

4. 验证新主库状态

sql
-- 检查新主库状态
SELECT pg_is_in_recovery();

-- 检查新主库的 WAL 生成
SELECT pg_current_wal_lsn(), pg_walfile_name(pg_current_wal_lsn());

5. 重新配置原主库为备库

  1. 修改原主库的配置文件

    ini
    # 修改 kingbase.conf 文件
    primary_conninfo = 'host=新主库IP port=54321 user=standby_user password=standby_password application_name=old_master'
    
    # 创建 standby.signal 文件
    touch /path/to/kingbase/master/data/standby.signal
  2. 启动原主库作为备库

    bash
    pg_ctl start -D /path/to/kingbase/master/data

6. 验证新备库状态

sql
-- 检查新备库状态
SELECT pg_is_in_recovery();

-- 检查新备库的复制状态
SELECT * FROM pg_stat_wal_receiver;

-- 检查新主库的复制状态
SELECT * FROM pg_stat_replication;

切换验证

1. 功能验证

sql
-- 在新主库上执行写操作
CREATE TABLE test_switchover (id serial primary key, name varchar(50));
INSERT INTO test_switchover (name) VALUES ('test');

-- 在新备库上验证数据同步
SELECT * FROM test_switchover;

2. 性能验证

sql
-- 检查新主库的连接数
SELECT count(*) FROM pg_stat_activity;

-- 检查新主库的负载
SELECT 
    (SELECT count(*) FROM pg_stat_activity WHERE state = 'active') AS active_connections,
    (SELECT avg(load_avg) FROM pg_stat_sysinfo) AS load_avg;

3. 复制验证

sql
-- 检查复制延迟
SELECT pg_wal_lsn_diff(pg_last_wal_receive_lsn(), pg_last_wal_replay_lsn()) AS replay_lag;

-- 检查复制槽状态
SELECT * FROM pg_replication_slots;

故障处理

1. 备库提升失败

症状:执行 pg_promote() 后,备库未能成功提升为主库

排查步骤

  1. 检查备库日志

    bash
    tail -n 200 /path/to/kingbase/standby/data/log/kingbase.log
  2. 检查备库状态

    sql
    SELECT pg_is_in_recovery();
  3. 检查备库的 WAL 应用状态

    sql
    SELECT pg_last_wal_replay_lsn();

解决方案

  • 修复备库的配置错误
  • 确保备库已应用所有 WAL 日志
  • 重新尝试提升备库为主库

2. 原主库无法作为备库启动

症状:原主库无法作为备库启动,或启动后无法连接到新主库

排查步骤

  1. 检查原主库日志

    bash
    tail -n 200 /path/to/kingbase/master/data/log/kingbase.log
  2. 检查原主库的 primary_conninfo 配置

    sql
    SHOW primary_conninfo;
  3. 检查新主库的 pg_hba.conf 配置

解决方案

  • 修复原主库的 primary_conninfo 配置
  • 调整新主库的 pg_hba.conf 配置,允许原主库连接
  • 重新初始化原主库的备库关系

3. 复制延迟持续增加

症状:切换后,新备库的复制延迟持续增加

排查步骤

  1. 检查新主库的 WAL 生成速率

    sql
    SELECT 
        (pg_current_wal_lsn() - pg_wal_lsn_offset(pg_current_wal_lsn(), 60)) AS one_minute_ago_lsn,
        pg_wal_lsn_diff(pg_current_wal_lsn(), pg_wal_lsn_offset(pg_current_wal_lsn(), 60)) AS wal_generated
    FROM pg_stat_wal;
  2. 检查新备库的系统资源使用情况

    bash
    top
    iostat -x
  3. 检查新备库的恢复进程数

    sql
    SELECT count(*) FROM pg_stat_activity WHERE backend_type = 'startup';

解决方案

  • 增加新备库的硬件资源
  • 调整新备库的恢复参数,如 max_worker_processes
  • 优化新主库的查询性能,减少 WAL 生成速率

最佳实践

1. 切换前

  • 制定切换计划:详细规划切换步骤、时间窗口和回滚策略
  • 备份数据:确保已完成最近的数据库备份
  • 通知相关团队:通知开发、测试和运维团队,协调切换时间
  • 检查主备状态:确保主备库状态正常,复制延迟在可接受范围内
  • 准备回滚方案:制定详细的回滚方案,确保在切换失败时可以快速恢复

2. 切换中

  • 严格按照流程操作:遵循预定的切换流程,避免遗漏步骤
  • 记录操作过程:详细记录切换过程中的每一步操作和结果
  • 监控系统状态:实时监控主备库的状态和性能
  • 及时处理异常:如遇到异常情况,及时执行回滚方案

3. 切换后

  • 验证系统功能:验证数据库的读写功能是否正常
  • 监控复制状态:确保新主备库之间的复制正常,复制延迟在可接受范围内
  • 更新文档:更新主备库的配置文档和监控配置
  • 总结经验:总结切换过程中的经验教训,优化切换流程

版本差异

特性V8 R6V8 R7
切换命令支持 pg_ctl promoteSELECT pg_promote()支持 pg_ctl promoteSELECT pg_promote(),新增 pg_ctl switchover 命令
切换速度较慢,需要手动执行多个步骤较快,新增自动化切换命令
切换安全性基本安全检查增强安全检查,如复制延迟检查、WAL 完整性检查
切换工具基本工具新增 KingBaseES Manager (KEM) 图形化切换工具
回滚机制手动回滚增强回滚机制,支持一键回滚

常见问题(FAQ)

1. 主备切换需要多长时间?

主备切换的时间取决于多种因素,如数据库大小、WAL 日志量、网络带宽等。一般情况下,主备切换需要几分钟到十几分钟不等。

2. 主备切换会导致数据丢失吗?

在正常情况下,主备切换不会导致数据丢失。切换前会确保备库已应用所有 WAL 日志,或使用同步复制确保数据零丢失。

3. 如何选择合适的备库提升为主库?

选择备库提升为主库时,需要考虑以下因素:

  • 备库的复制延迟:选择复制延迟最小的备库
  • 备库的硬件配置:选择硬件配置较好的备库
  • 备库的网络连接:选择网络连接稳定的备库
  • 备库的负载情况:选择负载较低的备库

4. 主备切换后,应用程序需要修改连接字符串吗?

是的,主备切换后,需要将应用程序的数据库连接字符串更新为指向新主库的 IP 地址和端口。

5. 如何自动化主备切换?

KingBaseES V8 R7 支持自动主备切换功能,可以通过以下方式实现:

  • 使用 KingBaseES Manager (KEM) 配置自动切换
  • 使用第三方高可用工具,如 Patroni、repmgr 等
  • 编写自定义脚本,实现自动切换逻辑

6. 主备切换和故障切换有什么区别?

主备切换是一种计划性的操作,主库正常运行,切换过程可控;故障切换是一种应急操作,主库故障或不可用,切换过程不可控,可能存在数据丢失风险。

7. 如何测试主备切换流程?

可以通过以下方式测试主备切换流程:

  • 在测试环境中定期执行主备切换
  • 在生产环境中进行灾备演练
  • 使用 KingBaseES Manager (KEM) 模拟主备切换场景

总结

主备切换是 KingBaseES 高可用架构中的重要操作,通过正确的切换流程和最佳实践,可以确保系统的高可用性和数据安全性。在进行主备切换时,需要充分准备、严格按照流程操作,并及时验证切换结果。

V8 R7 版本对主备切换进行了多项增强,包括新增自动化切换命令、增强安全检查、提供图形化切换工具等,建议在新部署或升级时优先考虑使用 V8 R7 版本,以获得更好的主备切换体验和安全性。