10个值得关注的问题
- 使用kafka能帮助我们解决什么问题?
- 我们应该选择kafka、rabbitmq还是activemq?
- kafka有怎样的拓扑结构和关键概念?
- kafka怎么保证消息可靠性?
- kafka怎么做副本数据复制?
- kafka怎么保证消息顺序性?
- kafka怎么保证消息不被重复消费?
- kafka的吞吐量为什么比rabbitmq好?做了哪些性能优化?
- ckafka提供了哪些配置值得关注?
- ckafka提供了哪些监控告警值得关注?
1. 使用kafka能帮助我们解决什么问题?
- 系统解耦:解耦消息生成者和消费者的关系
- 削峰限流:缓存突发请求压力
- 异步通知:通知非必要逻辑做异步处理
- 冗余存储:可做消息的冗余备份
- 发布订阅:一次生产可有多次消费
2. 我们应该选择kafka、rabbitmq还是activemq?
kafka的特点是高性能和可扩展,不保证消息100%可靠,适用于日志压缩收集、监控数据聚合等场景。而rabbitmq遵循AMQP协议,主要用于可靠性要求高的企业金融级产品
下面是业界几款热门开源消息中间件的横向对比。另一点值得关注的是ActiveMQ团队正在推的下一代产品Apache Apollo
3. kafka有怎样的拓扑结构和关键概念?
kafka的拓扑结构:
从拓扑上看,kafka主要由producers、brokers、consumers和zookeeper构成,下面是kafka几个比较核心的概念:
- topic:消息源的不同分类。
- partition:topic的物理分组,一个topic包含一个或多个partition,每个partition内部都是有序队列
- message:消息
- offset:消息在partition编号,编号顺序不跨partition
- producers:生产者,发布topic消息
- consumers group:消费者组,每条消息可被多个消息者组消费
- consumers:消费者,订阅topic消息
- broker:集群中的服务器
- replica:partition 的副本,保障 partition 的高可用
- leader:replica 中的一个角色,producer和consumer只跟leader交互
- follower:replica 中的一个角色,从 leader 中复制数据
- controller:kafka集群进行leader选举以及各种failover
4. kafka怎么保证消息可靠性?
和一般的分布式存储系统类似,kafka使用多副本来保证消息不丢失。对于一个大规模kafka集群,需关注所有环节节点的HA能力
- controller failover:kafka设计很核心一点就是基于zk做中控,通过zk的分布式一致性能力来做broker注册、topic注册、消息负载均衡、leader选举等
- leader failover:当partition对应的leader宕机时,kafka会从zk动态维护的follower中,选择1个commit过所有消息的follower来作为新leader
- follower failover:当partition对应的follower宕机时,kafka会从zk动态维护的broker中,选择新的1个broker做新副本数据同步
在可靠性方面,还有一点特殊说一下,kafka在0.11.0.0版本以一种特殊的设计和方法实现了强语义的exactly-once和事务性
- at least once:消息可能会丢,但绝不会重复传输
- at most once:消息绝不会丢,但可能会重复传输
- exactly once:每条消息肯定会被传输一次且仅传输一次
5. kafka怎么做副本数据复制?
作为kafka HA的基础,副本数据复制机制就显得非常重要,这个机制称为ISR(in-sync Replica)。
- 推还是拉?pull commit,和消费者类似
- 同步还是异步?非单纯同步异步,leader维护一个ISR列表等待follower的ack
- 怎么判断宕机?如果消息滞后太多(数量和时间两个维度,replica.lag.time.max.ms和replica.lag.max.message可配置)则认为宕机
- 什么场景会滞后?新增Replica,GC挂起,follower失效,I/O瓶颈
- 消费者能否读follower?不能,follower只当做备份
6. kafka怎么保证消息顺序性?
不是所有场景都需要顺序性,在像binlog、订单状态转化等场景才会需要。
kafka实现顺序性的核心:partition。但是一个业务想要保证消息顺序性,得从producer->broker->consumer3个环节一起来看:
- producer:要关注发送成功后才能发送下一个,比如有2条消息(A->B),如果A发送失败,这时不能发B之后再重试发A
- broker:kafka对同个partition的消息处理都在同的broker上,每个partition维护自己的offset,相同partition消息的生成和消费是按顺序串行的
- consumer:从partition取出消息后,一般会分发到多个线程去处理,这里要关注需加个Hash队列做成有状态的
7. kafka怎么保证消息不被重复消费?
也需求业务和kafka一起来保证,单纯靠消息中间件一点是不能100%做到的
- kafka的offset和commit机制:确保partition内的每个消息都有唯一offset,且收到offset的commit确认后才认为被消费成功
- 业务要做好消费幂等性:确保在异常情况下(如commit失败),如果收到2条相同消息,业务能识别过滤掉(如加个已处理offset缓存),或者确保消息处理的可重入(如使用DB的ON DUPLICATE KEY UPDATE等)
8. kafka的吞吐量为什么比rabbitmq好?做了哪些性能优化?
这里问题涉及2个维度,分布式维度上,kafka可通过多partition做平行扩容,单集群百万QPS应用很常见;在单partition的维度上,kafka在性能上做了多方面优化:
- 磁盘顺序读写消息
- 零拷贝技术(zero-copy)
- 批量发送消费
- 消息数据压缩
9. ckafka提供了哪些配置值得关注?
业务可根据自己场景对性能和可用性的不同需求,对分区、副本、消息日志等一些配置进行调节:
- num.partitions:分区数
- min.insync.replicas:ISR最小副本数
- replica.lag.time.max.ms:副本没应答时延超过该值,则认为宕机
- replica.lag.max.messages:副本没应答消息数超过该值,则认为宕机
- message.max.bytes:消息体最大字节数
- cleanup.policy:消息日志清理机制
- segment.ms:消息日志分片时长
- retention.ms:消息日志保留时间 几个值得关注的ckafka配置
ckafka提供了哪些监控告警值得关注?
业务上线之后,在Topic和Consumer2个维度,需要对生产消费消息量、未消费消息条数等做监控告警,确保系统异常能及时发现:
- 生产流量、消费流量 MB/min
- 生产条数、消费条数、落盘消息条数
- 当前消费offset、当前分区最大offset
- 未消费消息条数 几个值得关注的ckafka.Topic监控 几个值得关注的ckafka.Consumer监控
参考资料
- Apache Kafka官网 http://kafka.apache.org/
- 腾讯云消息队列CKafka https://cloud.tencent.com/product/ckafka
- 关于ActiveMQ、RocketMQ、RabbitMQ、Kafka一些总结和区别 https://www.cnblogs.com/xiapu5150/p/9927323.html
- kafka和rabbitmq对比 https://blog.csdn.net/myhes/article/details/83247108
- 消息中间件选型分析 https://blog.csdn.net/u013256816/article/details/79838428
- 图解kafka的高可用机制 https://mp.weixin.qq.com/s/C7j3K3lS9qN1YgyhoF3_rQ
- Kafka重复消费和丢失数据 https://blog.csdn.net/qingqing7/article/details/80054281
- kafka原理深入研究 https://www.cnblogs.com/xifenglou/p/7251112.html
- kafka消息如何保证顺序 https://blog.csdn.net/u011439839/article/details/90349596
- kafka是如何保证消息不被重复消费 https://www.cnblogs.com/756623607-zhang/p/10506909.html
- Kafka高性能架构之道 http://www.jasongj.com/kafka/high_throughput/
- kafka配置参数详解 https://www.cnblogs.com/gxc2015/p/9835837.html