这是我参与「第三届青训营-后端场」笔记创作活动的的第15篇笔记。
场景
- 系统崩溃 -- 解耦
- 服务处理能力有限 -- 削峰
- 链路耗时长尾 -- 异步
- 日志如何处理
消息队列(MQ)指保存消息的一个容器,本质是个队列,需要支持高吞吐、高并发、高可用。
常见消息队列
Kafka
分布式的、多分区的、多副本的日志提交服务,在高吞吐场景下发挥较为出色。
使用场景
- 日志信息
- Metric 数据
- 用户行为
如何使用
- 创建集群
- 新增Topic
- 编写生产者逻辑
- 编写消费者逻辑
基本概念
- Producer:生产者,负责将业务消息发送到Topic
- Consumer:消费者,负责消费Topic中的消息
- ConsumerGroup:不同组 Consumer 消费进度互不干涉
- Topic:逻辑队列,每个Topic可以有多个Partition,并发处理
- Cluster:物理集群,每个集群可以建立多个不同的 Topic
- Offset:消息在partition中的相对位置信息,在partition内部严格递增
- Replica: 副本,每个partition有多个replica,分布在集群的不同机器上(容灾)
- Leader:对外写入/读取
- Follower:不断拉取leader数据,努力与leader保持一致
- ISR(In-Sync Replicas):与leader差距(offset或时间)在一定范围内的follower。如果leader的机器宕机,就从ISR中选择一个follower来对外服务。
- Broker:集群中的节点
- Kafka架构中还会有ZooKeeper:负责存储集群元信息,包括分区分配信息等
Kafka 支撑高吞吐的方法
- Producer:消息批量发送,数据压缩(Snappy,ZSTD等)
- Broker:
- 顺序写,提高写入磁盘的效率;
- 二分找到小于目标offset的最大索引位置,或者根据时间戳先找到小于目标时间戳最大索引位置
- 零拷贝
- Consumer:reblance机制,通过 coordinator 为 consumer 自动分配 partition
Kafka 问题:
- 运维成本高
- 对于负载不均衡的场景,解决方案复杂
- 没有自己的缓存,完全依赖 Page Cache
- Controller 和 Coordinator 和 Broker 在同一个进程中,大量IO会造成起性能下降
BMQ
兼容Kafka协议,存算分离,云原生消息队列
- Producer --> Proxy Cluster --> Broker Cluster --> Distributed Storage System
- Distributed Storage System --> Proxy Cluster --> Consumer
读写流程
- 同一个partition的所有segment不会像Kafka一样全部分布在一个节点上,而是打散分布在集群中
- 写入状态机
- failover
高级特性
- 泳道消息
- Databus
- Mirror:解决跨 region 读写问题
- Index
- Parquet
RocketMQ
低延迟、强一致、高性能、高可靠、万亿级容量和灵活的可扩展性,在一些实时场景中运用较广
- Tag
- Nameserver
- Producer group
高级特性
- 事务场景
- 延迟发送。Schedule topic
- 消费重试和死信队列。
Pulsar
下一代云原生分布式消息流平台,集消息、存储、轻量化函数式计算为一体,采用存算分离的架构