业务背景
在一个项目中需要实现一个功能,商品价格发生变化时将商品价格打印在商品主图上面,那么需要在价格发生变动的时候触发合成一张带价格的图片,每一次触发合图时计算价格都是获取当前最新的价格。上游价格变化的因素很多,变化很频繁,下游合图消耗GPU资源较大,处理容量较低。
上游生产速度很快,下游处理速度很慢,上下游处理速度存在巨大差距时,我们首先可以想到使用消息队列进行削峰填谷,比如RocketMQ、Kafka。但是,在本项目的背景中,触发价格变化的来源很多,产生的触发消息可能存在大量重复,下游重复消费不但会浪费资源还会导致延迟。采用现有MQ消息队列的问题在于重复的消息无法合并处理以减少下游重复处理的次数。
在该项目中,由于合图资源有限,因此需要对不同等级的商家区分优先级处理。采用现有MQ消息队列的问题是,消息发生堆积后,消息只能按照FIFO(先进先出)顺序消费。由于无法区分优先级进行消费,紧急的任务也只能等待先到的任务先消费完成。
接下来,我将介绍一种可将消息合并处理并支持优先级的消息队列——RMQ,RMQ适用于重复消息比较频繁、上下游处理速度存在巨大差距的场景。
产品功能
RMQ是一个支持多Topic的消息队列,可以用作削峰填谷、异步解耦。相比已有的消息队列,他还具有消息合并和优先级的功能,这两个功能也是它存在的意义。
消息合并
RMQ是一个可合并消息的消息队列,如果消息堆积在消息队列中时,内容重复的消息会合并成一条。RMQ支持消息合并但是不支持消息去重,多条内容相同的消息堆积在RMQ中时,多条消息会被合并成一条消息,但一条消息可能由于系统宕机而被重复消费。
还有一种情况也无法避免,两条内容相同的消息先后产生,还没等到第二条消息产生,第一条消息就被消费了,紧接着第二条消息产生后也被消费了。但是,这种情况说明上下游处理速度不存在差距,业务上需要保障可以重复处理。
优先级
RMQ支持消息设置优先级,优先级分为高、中、低三个等级,优先级高的任务不管什么时候产生都会比优先级低的任务先执行,相同优先级的任务会随机被执行。
RocketMQ与RMQ功能对比
消息队列 |
堆积能力 |
顺序消息 |
优先级 |
消息合并 |
消息去重 |
可用性 |
应用场景 |
RocketMQ |
海量 |
支持 |
不支持 |
不支持 |
不支持 |
高可用 |
削峰填谷、异步解耦、海量堆积、重复消息不多的场景 |
RMQ |
亿级 |
不支持 |
支持 |
支持 |
不支持 |
高可用 |
消费填谷、异步解耦、 |