延迟消息的时间不支持很高的自定义度
RocketMQ 只给我们提供了 18 个选项:
messageDelayLevel=1s 5s 10s 30s 1m 2m 3m 4m 5m 6m 7m 8m 9m 10m 20m 30m 1h 2h
用户可以选择延迟等级投递消息
延迟消息判断
在 CommitLog 处理储存 Message 请求时
- 会先判断延迟等级是否大于0
- 如果延迟等级超出最大值,设为最大值
有延迟等级的消息会被截胡保存到延迟消息队列
延迟消息队列
会将消息保存到系统自带的Topic SCHEDULE_TOPIC_XXXX队列中
一共有18个队列,对应不同的延迟消费等级
队列起始索引为0
通过将延迟等级-1来计算出相应的目标延迟队列索引
延迟消息保存到队列后会开启一个线程不断地对队列进行扫描,当检测出到达到时限的消息时就会将它取出进行消费
流程图如下所示:
补充 : 定时任务原理
MessageStore启动初始化的时候会开启定时任务,定时去SCHEDULE_TOPIC_XXXX相关队列中找任务消费,根据消息的延时等级计算一个目标时间,和now当前的时间进行对比,如果now当前的时间超过了目标值设定时间,就把这个消息投入到正常的topic相关队列中,进行消费