十年匠心定制 · 商业建站与技术教学双线并行 咨询热线:400-886-1026 service@lmnt.cn
ARTICLE DETAIL

资讯详情

深耕网站建设与运营推广的一线实战洞察。

advanced-java 消息队列高可用指南:从 RabbitMQ 主从架构到 Kafka 副本机制的完整剖析

advanced-java 消息队列高可用指南:从 RabbitMQ 主从架构到 Kafka 副本机制的完整剖析 advanced-java 消息队列高可用指南从 RabbitMQ 主从架构到 Kafka 副本机制的完整剖析【免费下载链接】advanced-java Core Interview Questions Answers For Experienced Java(Backend) Developers | 互联网 Java 工程师进阶知识完全扫盲涵盖高并发、分布式、高可用、微服务、海量数据处理等领域知识项目地址: https://gitcode.com/gh_mirrors/ad/advanced-javaMQ消息队列在为系统带来解耦、异步、削峰三大收益的同时也引入了MQ 挂了整套系统就崩的可用性风险。本指南以 advanced-java 项目 docs/high-concurrency 系列中的《如何保证消息队列的高可用》为核心系统讲解 RabbitMQ 的三种集群模式单机 / 普通集群 / 镜像集群与 Kafka 基于 partition replica 副本机制的天然分布式高可用设计读完你将具备向面试官完整阐述MQ 高可用如何实现以及在不同 MQ 之间对比选型的能力。阅读提示本篇是 MQ 知识体系的第二环。建议先读 为什么使用消息队列 理解 MQ 的优缺点再结合本系列中的消息可靠性传输、消息重复消费与幂等性 形成完整认知闭环。为什么要回答如何保证 MQ 的高可用在 MQ 系列的面试考察中高可用是必问项。上一讲已经明确引入 MQ 的第一个副作用就是系统可用性降低——系统引入的外部依赖越多越容易挂掉。原本 A 系统直接调用 BCD 三个系统的接口现在中间多了一个 MQ一旦 MQ 宕机整套系统都会崩溃。因此只要你在系统里用了 MQ面试官接下来必定围绕 MQ 的这些缺点追问解决方案高可用就是其中之一。一个只会在代码里调用basicPublish/send()API、从未思考过 MQ 如何部署、如何容灾的候选人很容易在追问下露怯。这个问题的巧妙之处在于它不针对某一款具体的 MQ。直接问Kafka 高可用怎么保证对没用过 Kafka 的候选人是不公平的刁难而问MQ 高可用怎么保证候选人可以从自己实际用过的 MQ 出发展开。所以本篇也延续这一思路以 RabbitMQ主从架构代表和 Kafka分布式架构代表两条主线分别讲解。RabbitMQ 的三种模式与高可用演进RabbitMQ 是比较有代表性的**基于主从非分布式**实现高可用的 MQ其高可用方案经历了三个阶段单机模式 → 普通集群模式 → 镜像集群模式。单机模式Demo 级别无可用性可言单机模式就是在一台机器上启动一个 RabbitMQ 实例一般只在本地开发、跑 Demo 时使用没有任何生产环境会采用单机模式。它不存在任何集群与冗余宕机即不可用不在高可用讨论范畴内。普通集群模式只提高吞吐量不提供高可用普通集群模式在多台机器上各启动一个 RabbitMQ 实例形成一个集群。它的核心特征是你创建的 queue只会放在一个 RabbitMQ 实例上queue 的数据只存在于该实例但每个实例都会同步 queue 的元数据元数据可以理解为 queue 的一些配置信息通过元数据可以找到 queue 所在的实例消费时如果连接到了另外一个实例那个实例会从 queue 所在实例上拉取数据过来。这种方式存在明显的固有缺陷并没有做到所谓的分布式本质上仍是一个普通集群消费路径尴尬要么消费者每次随机连接一个实例然后拉取数据要么固定连接 queue 所在实例消费。前者存在数据拉取的开销每次消费都要跨节点传输后者导致单实例性能瓶颈所有读写压力集中在一个节点上宕机即不可用如果存放 queue 的实例宕机其他实例将无法再从该实例拉取数据。此时只有开启了消息持久化让 RabbitMQ 把消息落地存储消息才不一定会丢——但必须等该实例恢复后才能继续从这个 queue 拉取数据。所以这种模式的定位很明确这方案主要是为了提高吞吐量让集群中多个节点来服务某个 queue 的读写操作而不具备所谓的高可用性。镜像集群模式RabbitMQ 的高可用方案镜像集群模式才是 RabbitMQ 真正意义上的高可用模式。与普通集群模式不同在镜像集群模式下你创建的 queue无论是元数据还是 queue 里的消息都会存在于多个实例上——每个 RabbitMQ 节点都有这个 queue 的一个完整镜像包含 queue 的全部数据。每次写消息到 queue 时都会自动把消息同步到多个实例的 queue 上。如何开启镜像集群模式实现非常简单不需要改代码只需要在 RabbitMQ 的管理控制台Management UI后台新增一个策略Policy在管理控制台的 Policies 页面添加一条镜像集群模式策略策略中可指定同步范围要求数据同步到所有节点也可以要求同步到指定数量的节点通过ha-mode与ha-params等参数控制再次创建 queue 时应用该策略数据就会自动同步到其他节点上去。优点任何一个机器宕机都没关系其他节点仍包含这个 queue 的完整数据别的 consumer 可以到其他节点上继续消费实现了高可用。缺点同样明显性能开销巨大消息需要同步到所有机器上网络带宽压力和消耗非常重没有扩展性可言这不是分布式方案。如果某个 queue 负载很重新增的机器同样包含这个 queue 的全部数据无法线性扩展queue 的容量。一旦某个 queue 的数据量大到单机容量无法容纳就会陷入无解的死局。Kafka 的高可用天然分布式 副本机制基本架构topic 分 partition 分散存储Kafka 的基本架构认知是集群由多个 broker 组成每个 broker 是一个节点你创建一个 topic这个 topic 可以划分为多个 partition每个 partition 可以存在于不同的 broker 上每个 partition 只放一部分数据。这是天然的分布式消息队列一个 topic 的数据分散放在多台机器上每台机器只放一部分数据。对比之下RabbitMQ 之类属于传统的消息队列无论怎么玩RabbitMQ 一个 queue 的数据始终完整地放在一个节点里镜像集群模式下则是每个节点都放这个 queue 的完整数据只是提供了一些集群、HAHigh Availability高可用机制而已并非真正的分布式。Kafka 0.8 以前没有 HA 机制Kafka 0.8 以前是没有 HA 机制的任何一个 broker 宕机该 broker 上的 partition 就废了既不能写也不能读没有高可用可言。例如创建一个 partition 数量为 3 的 topic3 个 partition 分别位于三台机器上此时第二台机器宕机这个 topic 就有 1/3 的数据不可用了。正因为如此这个阶段谈不上高可用。Kafka 0.8 以后replica 副本机制带来高可用Kafka 0.8 以后提供了 HA 机制即replica副本机制每个 partition 的数据都会同步到其他机器上形成自己的多个 replica 副本所有 replica 会选举一个 leader生产和消费都跟这个 leader 打交道其他 replica 是 follower写入时 leader 负责把数据同步到所有 follower 上读取时直接读 leader 上的数据Kafka 会均匀地将一个 partition 的所有 replica 分布在不同的机器上以此提高容错性。为什么只能读写 leader不能随意读写 follower原因很简单如果允许随意读写每个 follower就必须处理数据一致性的问题系统复杂度会急剧上升很容易出问题。采用 leader-follower 模型把一致性收敛到leader 同步、follower 追随这一个路径上复杂度可控。高可用如何体现如果某个 broker 宕机该 broker 上的 partition 在其他机器上都有副本。若宕机的 broker 上恰好有某个 partition 的 leader则会从 follower 中重新选举一个新的 leader大家继续读写新的 leader 即可——这就是 Kafka 高可用机制的核心。写入流程生产者写 leader → leader 将数据落地写本地磁盘 → 其他 follower 主动从 leader pull 数据 → 所有 follower 同步好后发送 ack 给 leader → leader 收到所有 follower 的 ack 后返回写成功给生产者。这只是其中一种模式实际可通过acks、min.insync.replicas等参数适当调整行为消费流程消费者只会从 leader 读取只有当一个消息已经被所有 follower 都同步成功并返回 ack 时这个消息才会被消费者读到。两种高可用路线的对比与选型要点对比维度RabbitMQ 镜像集群Kafka 副本机制架构类型基于主从的 HA 机制非分布式天然分布式topic 按 partition 分散存储数据分布每个节点都持有 queue 的完整数据每个 partition 只存部分数据副本分散在不同机器读写模型消息自动同步到所有/指定数量节点读写只与 leader 交互follower 主动 pull 同步扩展性无法线性扩展单 queue 容量可按 partition 水平扩展容错方式任一节点宕机其他节点仍保有完整数据broker 宕机从 follower 重新选举 leader主要代价全量同步带来巨大网络带宽压力需要处理好副本同步与一致性参数选型层面的结论与消息队列选型文档一脉相承中小型公司、技术实力一般、技术挑战不高的业务系统用 RabbitMQ 是不错的选择其镜像集群模式足以覆盖常规高可用诉求且开源社区活跃大型公司、基础架构研发实力较强可选用 RocketMQ分布式架构扩展性好大数据领域的实时计算、日志采集等场景用 Kafka 是业内标准做法——分布式架构、数据多副本少数机器宕机不丢数据、不会导致不可用其高可用由 partition replica 机制天然支撑。进阶高可用之外消息队列系列还需要解决什么高可用只是 MQ 引入后需要面对的问题之一。why-mq.md 指出引入 MQ 会带来三大副作用系统可用性降低、系统复杂度提高、一致性问题。围绕复杂度与一致性的补齐整个 MQ 系列形成了一套完整方案如何保证消息不被重复消费消息消费的幂等性高可用保证服务不挂幂等性保证数据不错二者结合才构成可靠的消费端如何保证消息的可靠性传输消息丢失问题RabbitMQ 用事务/confirm 机制 持久化 手动 ack 三层防护Kafka 则通过replication.factor 1、min.insync.replicas 1、acksall、retriesMAX四个参数组合保证不丢消息——这些参数正是本文 Kafka 副本同步流程在生产环境中的落地配置如何保证消息的顺序性解决高可用与副本同步可能引入的乱序问题消息队列的延时、过期失效与积压处理应对高可用架构下消息堆积的极端场景如何设计一个消息队列从架构设计角度整体审视 MQ 的核心组件。面试时可以把高可用作为切入点顺带展示你对整套 MQ 知识体系的掌控力高可用解决MQ 挂不挂的问题可靠传输解决消息丢不丢的问题幂等性解决数据对不对的问题——三者共同构成在生产环境中可信赖使用消息队列的完整方案。总结回到开头的面试题如何保证消息队列的高可用一个完整的回答应当包含两条主线RabbitMQ 路线主从 镜像单机模式只适合 Demo普通集群模式只有元数据冗余、queue 数据单点存放只提吞吐不提可用性镜像集群模式让每个节点持有 queue 完整镜像并自动同步实现了高可用但付出全量同步的网络带宽代价且无法线性扩展Kafka 路线分布式 副本topic 按 partition 分散在多台 broker 上天然分布式0.8 版本之后引入 replica 副本机制每个 partition 的多个副本选举 leader读写只与 leader 交互follower 主动 pull 同步数据broker 宕机时从 follower 重新选举 leader从而获得高可用。把这两条路线的架构图画清楚、把为什么只能读写 leader这类原理性问题讲明白你就已经在面试官面前证明了自己对 MQ 高可用机制有深入而非浮于表面的理解。【免费下载链接】advanced-java Core Interview Questions Answers For Experienced Java(Backend) Developers | 互联网 Java 工程师进阶知识完全扫盲涵盖高并发、分布式、高可用、微服务、海量数据处理等领域知识项目地址: https://gitcode.com/gh_mirrors/ad/advanced-java创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考
返回列表