演讲回顾|Apache Pulsar 在腾讯云上的高可用性最佳实践

本文整理自 Mingze Han 在Community Over Code Asia 2025 上的主题演讲。

韩明泽,腾讯云高级工程师,负责 TDMQ for Pulsar 产品的商业化开发;深度参与了 Apache Pulsar、Kafka、RocketMQ 等主流消息中间件的开发与运维;Apache Pulsar Committer,为BookKeeper、ZooKeeper等底层组件贡献过代码,同时也是RoP(RocketMQ on Pulsar)项目的维护者。

本次分享基于腾讯云的大规模生产实践,系统性地阐述了构建 Apache Pulsar(下称 Pulsar)高可用架构的核心思路与具体方案。内容主要围绕三大模块展开:可用区内的高可用设计(多机房容灾)、跨地域的高可用保障(多集群容灾),以及 ZK(ZooKeeper)弱依赖架构。

1

可用区高可用

在云计算的语境下,高可用设计的第一道防线位于可用区(Availability Zone)层级。一个地域(Region)通常由多个物理隔离的可用区构成,每个可用区可视作一个独立的机房。可用区高可用的目标是确保Pulsar集群能够容忍单个甚至多个可用区的故障。

  1. 机架感知

实现跨可用区容灾,首要任务是让数据分布感知物理拓扑。Pulsar 使用 Broker、BookKeeper 和ZooKeeper 三组件协同工作。其中,BookKeeper 作为持久化存储层,其数据副本的分布策略至关重要。BookKeeper 的机架感知(Rackaware)策略是实现容灾目标的基础。

具体配置上,必须显式开启bookkeeperClientRackawarePolicyEnabled=true参数,并为每一个 BookKeeper 节点准确标注其所属的机架或可用区信息(例如 zone-1、zone-2)。同时,通过设置 bookkeeperClientMinNumRacksPerWriteQuorum=2,可以强制规定每一次写操作(Quorum)必须至少覆盖 2 个不同的可用区。这样,系统在为某个主题(Topic)的 Ledger 选择 BookKeeper 节点存储副本时,便会依据这些机架信息,自动将多个副本分散到不同的可用区中,从根源上避免了数据全集中在单一机房的风险。

  1. 跨机房分布

仅有副本的物理分布还不够,副本的配置参数直接决定了系统在故障发生后的行为与恢复能力。这里存在一个关键的恢复公式:当发生部分节点或机房故障后,剩余的可用副本数必须满足 剩余副本 >= W - A + 1。其中,W是写入副本数(Ensemble Size),A是写入确认副本数(Write Quorum)。

这个公式是理解许多故障场景的钥匙。例如,一个常见的误区是在两个可用区中采用 2-2-1 配置(即W=2, A=2)。一旦某个可用区整体故障,剩余副本数为 1。代入公式,恢复要求为 2-2+1=1,看似满足。然而,此时数据仅存一份,已无任何冗余,处于极度脆弱的状态,任何进一步的问题都将导致数据永久丢失,因此这种配置在实践中是危险的。更安全的做法是,即使在两个可用区,也应采用如 3-2-1 的配置。同理,在三个可用区下,4-3-2 配置在任意两个可用区故障时,剩余副本数可能无法满足公式要求。基于大量实践经验,推荐生产环境采用三可用区部署,并配置为 3-3-2,这在容灾能力和存储成本间取得了最佳平衡。

在读取侧,默认的跨副本轮询读取策略在遇到故障节点时,会导致大量请求因超时而失败,造成读性能剧烈抖动。为了解决这个问题,引入了粘性读取(Sticky Reads) 优化。通过配置 bookkeeperEnableStickyReads=true,客户端在首次从某个健康副本成功读取后,会在后续一段时间内"粘"在该副本上,避免轮询到故障副本。只有当当前粘定的副本发生故障时,客户端才会平滑地切换到另一个健康副本,从而在故障期间依然能保持稳定、高性能的读取,这对于"追赶读"(Catch-up Read)等历史数据读取场景尤为重要。

2

地域级高可用

即便在单一地域内采用了最优的多可用区部署,仍可能因底层计算资源、网络设备或电力等基础设施的整体性故障,导致整个地域的集群不可用。因此,跨地域容灾是保障业务连续性的终极解决方案。

1. 集群跨地域部署的必要性

地域级高可用的核心思想,是在另一个地理上隔离的区域(例如上海)部署一个备用的 Pulsar 集群。当主地域(例如广州)发生不可抗拒的全局性故障时,能够将流量切换至备用集群,实现快速业务恢复。

2. 跨地域部署与域名切换

架构上的实现方案是"异地冷备集群"。其核心切换机制依赖于 HTTP 协议与域名。生产客户端通过一个统一的域名接入消息服务。当检测到广州主集群故障时,通过控制 DNS 解析,在极短时间内将域名指向上海备集群的 VIP 地址。由于客户端 SDK 内置了重试机制,在连接失败后会重新进行域名解析,从而无感知地连接到新的健康集群。这个过程对业务方代码是透明的,无需任何改造,是产品提供的内置高可用能力。

3. 元数据同步与故障恢复

为了保证切换后业务的连续性,需要让备集群"认识"主集群的元数据状态,包括租户、命名空间、主题、订阅关系等。通过后台服务定时将主集群的元数据同步到备集群。当故障发生并完成域名切换后,客户端在上海集群就能继续使用原有的主题和订阅进行生产和消费。

故障恢复包含两个阶段:首先是回切,即当广州主集群恢复后,可将域名切换回广州,使流量回归。其次是数据补偿,在广州集群故障期间,可能仍有部分消息只被上海集群接收而未消费。通过建立集群间安全的网络联通,将这部分"堆积"在上海集群的消息,异步地回写(补偿)到广州集群,确保消息不丢失,最终实现数据状态的一致。

4. 冷备资源与快速扩容

为了控制成本,日常状态下上海备集群可以以较低的规格(如较少的 Broker 和 BookKeeper 节点)运行,不承载生产流量,即标准的"冷备"模式。其核心价值在于"有状态":已同步元数据并保持服务就绪。一旦需要接管流量,可以利用云计算的弹性,在分钟级快速扩容备集群的资源,使其迅速具备支撑全量业务流量的能力。

更进一步,对于数据可靠性要求极高的场景,可以启用 Pulsar 的 Geo-replication 功能。该功能能近乎实时地将消息数据从主集群复制到备集群,使备集群成为一个"热备"或"准双活"集群。这不仅大幅提升了数据可靠性,也使灾备切换时的数据延迟(RPO)趋近于零。

3

ZK 弱依赖

ZooKeeper 作为 Pulsar 的元数据管理和协调中心,其稳定性至关重要。但"弱依赖"架构的目标是:即使 ZK 服务发生短期故障(如网络抖动、GC 暂停),集群存量主题的消息生产和消费功能也不应中断。这与 Kafka 的设计哲学类似,仅在创建主题、扩容等需要变更元数据的操作时才强依赖 ZK。

1. ZK 弱依赖的定义与基本要求

ZK 弱依赖的核心定义非常明确:ZK 故障期间,已经存在的主题(Topic)必须能继续提供消息收发服务。这意味着,Broker 与 BookKeeper 需要有能力在 ZK 暂时失联时,维持现有组件的运行状态和数据的读写路径。

2. Broker 与 ZK 的连接及弱依赖实现

在 Pulsar 架构中,存在几类关键的 ZK 连接:Broker 与 ZK(用于服务发现、Leader 选举)、BookKeeper 与 ZK(用于 Ledger 元数据存储)。社区版本已经为实现弱依赖做出了努力,其思路主要集中在两点:禁止 Leader切换和维持本地缓存。

当 Broker 检测到与 ZK 的连接出现问题时,会主动禁止一切触发 Leader 切换的操作。例如,某个 Broker 负载过高或心跳超时,原本需要通知 ZK 以触发所有者(Owner)重新选举,但在 ZK 故障期间,这个操作会被挂起。同时,Broker 会维持其本地缓存的元数据信息(如主题策略、Schema 等)的有效性,避免因缓存过期而无法服务。

3. 不同部署形态下的连接隔离问题

在生产环境中,为了隔离故障域和便于管理,常常采用 Broker 集群和 BookKeeper 集群独立部署,且各有一套独立 ZK 集群的方案。这就带来一个复杂场景:一个 Broker 节点需要同时连接两套 ZK:Broker-ZK(B-ZK)和 Bookie-ZK(K-ZK)。

要实现完善的弱依赖,就必须对这两套 ZK 连接的故障进行隔离处理。此处的策略是,当检测到 B-ZK 连接异常时,按上述社区方案处理;当检测到 K-ZK 连接异常时,Broker 同样需要禁止任何与 BookKeeper 元数据变更相关的操作,例如 Ledger 的打开、创建等流程中的协调行为,防止因元数据不一致导致的数据错误。

4. 异常场景的兜底策略

保护策略也延伸到了资源层面。例如,通过监控发现存活的 BookKeeper 节点数低于某个安全阈值时,系统会主动禁止 Leader 切换,防止在资源不足的情况下进行可能引发雪崩的协调操作。所有这些策略的目标是一致的:在协调服务(ZK)不可靠时,优先"冻结"系统的元数据状态,全力保障最核心的数据平面(消息读写)的稳定运行,待 ZK 恢复后再处理积压的元数据变更。

Apache Pulsar 作为一个高性能、分布式的发布-订阅消息系统,正在全球范围内获得越来越多的关注和应用。如果你对分布式系统、消息队列或流处理感兴趣,欢迎加入我们!

Github:

https://github.com/apache/pulsar

扫码加入 Pulsar 社区交流群

最佳实践

互联网

腾讯BiFang | 腾讯云 | 微信 | 腾讯 | BIGO | 360 | 滴滴 | 腾讯互娱 | 腾讯游戏 | vivo| 科大讯飞 | 新浪微博 | 金山云 | STICORP | 雅虎日本 | Nutanix Beam | 智联招聘 | 达达 | 小红书

金融/计费

腾讯计费中原银行 | 平安证券 | 拉卡拉 | Qraft | 甜橙金融

电商

Flipkart | 谊品生鲜 | Narvar | Iterable

机器学习

腾讯Angel PowerFL | Discord

物联网/芯片制造

应用材料云兴科技智慧城市 | 科拓停车 | 华为云 | 清华大学能源互联网创新研究院 | 涂鸦智能

通信

江苏移动 | 移动云

教育

网易有道 | 传智教育

推荐阅读

免费可视化集群管控 | 资料合集 | 实现原理 | BookKeeper储存架构解析 | Pulsar运维 | MQ设计精要 | Pulsar vs Kafka | 从RabbitMQ 到 Pulsar | 内存使用原理 | 从Kafka到Pulsar | 跨地域复制 | Spring + Pulsar | Doris + Pulsar | SpringBoot + Pulsar

相关推荐
_运维那些事儿3 小时前
VM环境的CI/CD
linux·运维·网络·阿里云·ci/cd·docker·云计算
人间打气筒(Ada)6 小时前
k8s:CNI网络插件flannel与calico
linux·云原生·容器·kubernetes·云计算·k8s
主机哥哥12 小时前
2026年阿里云五种方案快速部署 OpenClaw(Clawdbot)详细教程
阿里云·云计算
m0_6948455712 小时前
music-website 是什么?前后端分离音乐网站部署实战
linux·运维·服务器·云计算·github
软件派12 小时前
Apache SeaTunnel从入门到精通:企业级数据集成全流程解析
apache·seatunnel
新新学长搞科研13 小时前
【智慧城市专题IEEE会议】第六届物联网与智慧城市国际学术会议(IoTSC 2026)
人工智能·分布式·科技·物联网·云计算·智慧城市·学术会议
翼龙云_cloud13 小时前
亚马逊云代理商: RDS 误删实例急救指南 5 步找回数据
服务器·云计算·aws
翼龙云_cloud13 小时前
阿里云代理商: 如何选择适合自己的阿里云 ECS 配置?
服务器·阿里云·云计算
以太浮标14 小时前
华为eNSP模拟器综合实验之- DHCP Option 43 解析
服务器·网络·华为·云计算
gaize121315 小时前
腾讯云高性价比GPU算力,开启AI时代
人工智能·腾讯云·gpu算力