Patroni 中的 Watch Dog 机制
1. 前言
首先先说为什么要有 watchdog ,一个正常运行的数据库主备集群,如果我们的系统在运行是出现问题,节点 PG1 失效了,无论是网络的问题,还是主机本身的问题,此时都是要进行重新选举,此时问题就产生在开始选举新的 leader 的时候。
对于 loop_wait,ttl,retry_timeout 三个配置,都有默认值。
已默认值来说一个节点的切换 10+ 30 + 10 是最大的时间, 但实际上会有另一个问题,在选举中,此时所有节点包含失效的节点,都会出现一个问题,此时没有节点是 leader, 在此时数据写入的需求是怎么处理的问题,为了避免脑裂,Patroni 需要确认 postgresql 不能在 leader 键值在 DCS 过期后继续接受事务的 commit, 在 patroni 无法进行 leader lock 后,则 patroni 将开始试图停止 postgresql 的方式来保证此期间的不会有脑裂的问题。
watchdog 的主要产生的原因是,如果 patroni 无法在此刻关闭 postgresql 怎么办? 因为 patroni 也不是"孙悟空",也是人肉一枚, 如果由于各种原因导致 patroni 本身无法工作,watch dog 将尝试从新启动系统,如果工作后,无论怎样 patroni 还是无法正常工作,则 watchdog 模式如果设置成 required 则这个所在的问题节点是不能成为 leader 的。当整体选举 leader 成功后, patroni 将会让 watchdog 进入休眠的状态。
但在设计 watchdog 时会有一个问题,因为设计时差的问题,导致 watch dog 本身无法获得 patroni 发送的信息,最终在这个工作周期,无法激活 watch dog。 这个时间的设定较 safety margin。 官方给出的建议并不明确,只提到了 watchdog timeout 调整到 ttl 的一半的时间, 确保 watchdog 能受到信息,从对 loop_wait 和 retry_timeout 入手。
2. 机制详解
2.1 什么时候 Watch Dog 机制
在 PostgreSQL 高可用集群中,Watchdog(看门狗)是一种防止脑裂(split-brain)问题的安全机制。当多个 PostgreSQL 实例同时作为主节点运行时,可能导致数据不一致和事务丢失。Patroni 通过 Watchdog 设备提供了额外的保护层,确保在主节点失去领导权时能够正确关闭或重置系统。
2.2 为什么需要 Watch Dog
Patroni 通常通过停止 PostgreSQL 服务来防止脑裂,但在某些情况下可能失效:
- Patroni 进程意外崩溃或被终止。
- PostgreSQL 关闭过程耗时过长。
- 系统负载过高导致 Patroni 无法正常运行。
- 虚拟机被 hypervisor 暂停。
Watchdog 作为硬件或软件的监控机制,会在指定时间内未收到心跳信号时强制重置整个系统,为集群提供最终的安全保障。
2.3 Watch Dog 的工作原理
Patroni 在将 PostgreSQL 提升为主节点前会尝试激活 Watchdog,其工作流程如下:
- 激活阶段:在节点成为主节点前激活 Watchdog。
- 运行阶段:定期发送心跳信号保持 Watchdog 活跃。
- 失效处理:当无法更新领导锁时,Watchdog 会在超时后触发系统重置。
- 降级阶段:节点降级为备节点时禁用 Watchdog。
2.4 关键配置参数
Patroni 中与 Watchdog 相关的重要配置参数包括:
- ttl:领导锁的存活时间(默认 30 秒)。
- loop_wait:主循环等待时间(默认 10 秒)。
- safety_margin:安全时间余量(默认 5 秒)。
- retry_timeout:DCS 访问超时时间(默认 10 秒)。
Watchdog 的超时时间计算公式为:ttl - safety_margin,默认情况下为 25 秒(30-5)。
安全时间余量的重要性:
safety_margin 参数决定了 Watchdog 触发时间与领导锁过期时间之间的缓冲期。为了确保绝对安全,可以将 safety_margin 设置为-1,此时 Watchdog 超时时间将变为 ttl // 2(即 TTL 的一半)。
2.5 Linux 软件 Watchdog 配置指南
Patroni 目前仅支持 Linux 系统的 Watchdog 设备接口。以下是配置软件 Watchdog 的步骤:
- 加载 Linux 内核的 softdog 模块:
sudo modprobe softdog
- 设置设备权限(以 postgres 用户为例):
sudo chown postgres /dev/watchdog
- (可选)测试模式下禁用实际重启:
sudo modprobe softdog soft_noboot=1
在测试模式下,Watchdog 触发时仅会在内核日志中记录信息,可通过 dmesg 命令查看。
2.6 总结
- 对于生产环境,建议使用硬件 Watchdog 以获得更高可靠性。
- 根据系统负载情况适当调整 ttl 和 loop_wait 参数。
- 定期检查 Patroni 日志确认 Watchdog 状态。
- 在高可用性要求极高的场景,考虑设置 safety_margin=-1。
Patroni 的 Watchdog 机制为 PostgreSQL 高可用集群提供了最后一道防线,确保在各种异常情况下都能避免脑裂问题的发生。通过合理配置 Watchdog 参数,可以构建更加健壮的数据库高可用架构。