生产环境消息堆积如何处理?

363 天前
 fatyoung
我的想法是
机器配置上:增加分区 partition ,增加组内 consumer ,并最好让分区跟 consumer 数量比例为 1:1
代码上:一般消息堆积都是 consumer 消费逻辑里有长时间 I/O 行为导致,所以可以在 consumer 中开启多线程消费
面试官反问:还有其他方法吗? 还有,如果我想这个分区的消息都可以顺序消费,开启多线程怎么保证顺序消费?
如何回答?
2360 次点击
所在节点    程序员
15 条回复
cyaki
363 天前
只用增加 partition 就完事吧, 得注意增加 partition 时, 会暂时性打乱消息顺序.
因为上面这个原因, 所以最好 partition 数量在一开始时就多设置一点
后面消息堆积时, 就只能增加 consumer 就好了

代码上建议保持原样或者缩短长 IO 行为, 不必要引入多线程来增加复杂度
cyaki
363 天前
@cyaki 还有增加节点数, 提高整个集群的读写能力上限
cyaki
363 天前
@cyaki 还有看消息分布, 是不是集中分布到了部分 parition 上, 导致 consumer 无法处理过来
abcfyk
363 天前
无论什么问题
1. 先确定问题背景和现状
2. 确定问题原因

第三步才是设计解决方案
fatyoung
363 天前
@cyaki 谢谢老哥的回复。对我当时也是想到消息可能因为是根据 key 分区然后都打到同一个分区去了,但是我没想到解决方案,将分区策略从根据 key 分区改为轮询?
fatyoung
363 天前
@abcfyk 谢谢老哥回复。确实是,我应该先问一句因为什么导致的消息堆积
admol
363 天前
如果是面试这样回答肯定是有些问题的,你这个回答感觉应该是在设计之初就要想到的方案

堆积的消息重要吗?
- 不重要,过期未处理的消息;都是可以直接删除的
- 重要;那你就得考虑为什么导致消息堆积了,生产者变快还是消费者变慢都有不同的处理方式,比如你说的开启多线程消费,或者还有生产者限流(不推荐)

还可以从事前、事中、事后再考虑下发生这些问题该怎么处理
chutianyao
363 天前
得考虑消费能力啊, 有些场景就是因为下游处理能力不足, 才用消息进行削峰填谷的. 比如异步落库, 你一股脑扩实例、增加队列、并行消费等措施全搞上, 堆积是没有了, 结果把数据库打挂了
fatyoung
363 天前
@chutianyao 谢谢老哥回复。那生产环境数据库如何扩容呢? 这个倒是没有考虑过
fatyoung
363 天前
@fatyoung #9 分库分表? 但是短期内应该做不了这么大改动吧
fatyoung
363 天前
@admol 谢谢老哥回复。是重要的消息,不能直接 purge
justplaymore
363 天前
分开看消息的处理流程
1.从消息队列中取消息
2.用消息去执行业务逻辑

当 1 和 2 同步时,就容易产生消息队列的消息堆积,影响线上增量实时消息。
当 1 和 2 异步时,取消息速度非常快,不会产生消息堆积,把取到的消息放到另外的存储介质里,异步取数据慢慢执行业务逻辑。

消息顺序性是有局限性的,基于什么范围内要保证顺序的?全局?单个用户?单个门店?单个商户?顺序性的范围越小,维护成本越低,并发处理性能越高。
potatowish
363 天前
单个分区开启多线程了还怎么保证顺序呢,后面再进行的一系列保证顺序的操作,都会使它串行化。一般我们会有一个配置,当队列长度超过一个阈值时,就先切换到异步落库模式,然后小批量拉数据进行消费。
qianckjuan
363 天前
我自己遇到的,是因为有重试逻辑,但是大概率会 fail ,所以消费多少基本就会重试多少,会堆积,导致怎么增加 consumer 都没有用。
还是要看为什么堆积的
julyclyde
360 天前
如果都是值钱的业务数据,那恭喜你锻炼的机会到了
如果是垃圾数据,比如直接删了算

分享一个古代我遇到的类似情况
https://julyclyde.org/?p=512
是软件本身的设计问题

这是一个专为移动设备优化的页面(即为了让你能够在 Google 搜索结果里秒开这个页面),如果你希望参与 V2EX 社区的讨论,你可以继续到 V2EX 上打开本讨论主题的完整版本。

https://www.v2ex.com/t/1004313

V2EX 是创意工作者们的社区,是一个分享自己正在做的有趣事物、交流想法,可以遇见新朋友甚至新机会的地方。

V2EX is a community of developers, designers and creative people.

© 2021 V2EX