Skip to content

15. 源码入口与排错:出问题时从哪里看

为什么要读源码入口

教程前面已经能让订单系统跑起来。但真实项目一定会遇到:

text
为什么没有 RocketMQClientTemplate?
为什么监听器没启动?
为什么 producer 配置了 topic 还是发送失败?
为什么 PushConsumer 参数不生效?

这时要知道 starter 的几个核心入口。

核心源码地图

文件作用
RocketMQAutoConfiguration.java创建 ProducerBuilder、SimpleConsumerBuilder、RocketMQClientTemplate
RocketMQProperties.java绑定 rocketmq.* 配置
RocketMQClientTemplate.java发送、事务、SimpleConsumer receive/ack
RocketMQMessageListener.javaPushConsumer 注解参数
RocketMQMessageListenerBeanPostProcessor.java扫描监听器注解
ListenerContainerConfiguration.java注册监听容器
DefaultListenerContainer.java创建和启动 PushConsumer
RocketMQHeaders.javakey、tag、topic 等 header 常量

排错一:没有 RocketMQClientTemplate

RocketMQAutoConfiguration 创建 template 的条件和 producer/simple consumer builder 有关。

排查:

  1. 是否引入了正确 starter。
  2. 是否配置了 rocketmq.producer.endpoints
  3. 如果只用 SimpleConsumer,是否配置了 rocketmq.simple-consumer.endpoints
  4. Spring Boot 自动配置是否被排除。

排错二:监听器没启动

监听器需要:

  1. 类是 Spring Bean,例如 @Service
  2. 实现 RocketMQListener
  3. 标注 @RocketMQMessageListener
  4. 注解里的 endpoints、topic、consumerGroup 不为空。

ListenerContainerConfiguration 会校验 topic 和 endpoints。缺配置时会启动失败。

排错三:消息发出去了但消费不到

按这个顺序查:

  1. producer 的 topic 和 consumer 的 topic 是否一致。
  2. tag 是否匹配。
  3. consumerGroup 是否和预期一致。
  4. 消费者是否启动成功。
  5. 是否被同 group 的其他实例消费。
  6. 是否消费失败后进入重试或死信。

排错四:消费慢或堆积

先不要直接调参数。按下面顺序看:

text
消息量 -> 消费成功率 -> 单条耗时 -> 下游耗时 -> 线程数 -> 本地缓存 -> 实例数

如果业务处理本身慢,调大线程数只能把压力推给数据库和下游接口。

小技巧

每条消息日志都带四个字段:

text
messageId
topic
tag
businessKey

如果还有 traceId,就一起带上。排查时这比“消费失败了”有用得多。

常见坑

  1. 拿旧 starter 文档排 5.x 问题。
    坐标、配置项、endpoint 模型都可能不一样。

  2. 只看业务日志,不看 starter 启动日志。
    producer、consumer 初始化信息通常在启动阶段已经给线索。

  3. 排查消费不到时忽略 consumerGroup。
    同 group 实例会分摊消息,不是每个实例都收到每条消息。

练习题

  1. RocketMQClientTemplate 主要封装了哪些能力?
  2. 监听器没启动时先查哪四件事?
  3. 消息消费不到时为什么要看 tag?

参考答案

  1. 普通、顺序、延时、异步、事务消息发送,以及 SimpleConsumer 的 receive/ack。
  2. Bean、接口、注解、配置。
  3. 因为消费者可能通过 tag 过滤,tag 不匹配就不会收到。

来源

Built with VitePress. Deployed on Cloudflare Pages.