searchusermenu
  • 发布文章
  • 消息中心
点赞
收藏
评论
分享
原创

如何定位rocketmq消息堆积问题

2024-07-01 03:26:48
0
0

1. 基础概念

消费者在消费的过程中,消费的速度跟不上broker服务端的发送速度,未处理的消息会越来越多,消息出现堆积进而会造成消息消费延迟。rocketmq虽然是用来存储消息的中间层(仓库),解决消息的高并发处理(流量削峰)。但不建议用作数据库使用,长久储存消息,应生产消息后,做到及时消费。消息堆积会对集群的性能有一定的影响。

2. 消费原理

 

客户端使用 push模式启动后,消费消息时,分为以下两个阶段:

阶段一:拉取消息

客户端通过长轮询批量拉取的方式从 Broker 服务端获取消息,将拉取到的消息缓存到本地缓冲队列中。

阶段二:消费消息

提交消费线程,客户端将本地缓存的消息提交到消费线程中,使用业务消费逻辑进行处理。

通过以上客户端消费原理可以看出,消息堆积的主要瓶颈在于本地客户端的消费能力,即消费耗时消费并发度

想要避免和解决消息堆积问题,必须合理的控制消费耗时和消息并发度,其中消费耗时的优先级高于消费并发度,必须先保证消费耗时的合理性,再考虑消费并发度问题。

3. 消费瓶颈

绝大部分消息消费行为都属于 IO 密集型,即可能是操作数据库,或者调用 RPC,这类消费行为的消费速度在于后端数据库或者外系统的吞吐量,通过增加消费并行度,可以提高总的消费吞吐量,但是并行度增加到一定程度,反而会下降。

应用必须要设置合理的并行度。 如下有几种修改消费并行度的方法:

a. 同一个 ConsumerGroup 下,通过增加 Consumer 实例数量来提高并行度(需要注意的是超过订阅队列数的 Consumer 实例无效)。可以通过加机器,或者在已有机器启动多个进程的方式。

b. 提高单个 Consumer 实例的消费并行线程,通过修改参数 consumeThreadMin、consumeThreadMax 实现。

4. 解决策略

4.1 确认消息的消费耗时是否合理

首先,需要查看消费耗时,确认消息的消费耗时是否合理。查看消费耗时一般来讲有两种方式:

4.11 打印日志

 

4.12 查看消息轨迹

登录rocketmq控制台查看消息轨迹 

当确定好消费耗时后,可以根据耗时大小,采取不同的措施:

 a. 若查看到消费耗时较长,则需要查看客户端堆栈信息排查具体业务逻辑,需查看客户端 JVM 的堆栈 。

b. 若查看到消费耗时正常,则有可能是因为消费并发度不够导致消息堆积,需要逐步调大消费线程或扩容节点来解决。

4.2查看客户端JVM的堆栈

假如消费耗时非常高,需要查看 Consumer 实例 JVM 的堆栈

a) 通过 jps -m或者 ps -ef | grep java 命令获取当前正在运行的 Java 程序,通过启动主类即可获得应用的进程 pid ;

b) 通过 jstack pid > stack.log 命令获取线程的堆栈 或者通过服务端的mqadmin工具 执行以下命令获取

 

c) 执行以下命令,查看 `ConsumeMessageThread` 的信息 。

常见的堆栈信息

示例1:空闲无堆积的堆栈(WAITTNG)

消费空闲情况下消费线程都会处于 `WAITING` 状态等待从消费任务队里中获取消息。

 示例2:消费逻辑有抢锁休眠等待等情况SLEEP)

消费线程阻塞在内部的一个睡眠等待上,导致消费缓慢

示例3:消费逻辑操作数据库等外部存储卡住RUNNABLE)

消费线程阻塞在外部的 HTTP 调用上,导致消费缓慢 

5总结

5.1 客户端使用 Push模式启动后,消费消息时,分为以下两个阶段:拉取消息消费消息

5.2 客户端消费原理可以看出,消息堆积的主要瓶颈在于本地客户端的消费能力,即消费耗时消费并发度

5.3 当遇到堆积问题,首先分析消费耗时,然后根据耗时大小,采取不同的措施:

a. 若查看到消费耗时较长,则需要查看客户端堆栈信息排查具体业务逻辑,需查看客户端 JVM 的堆栈 。

b. 若查看到消费耗时正常,则有可能是因为消费并发度不够导致消息堆积,需要逐步调大消费线程或扩容节点来解决。

 

0条评论
0 / 1000