26 生产案例:从RocketMQ全链路分析用户支付后没收到红包的原因
Posted 鮀城小帅
tags:
篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了26 生产案例:从RocketMQ全链路分析用户支付后没收到红包的原因相关的知识,希望对你有一定的参考价值。
场景:由用户反馈,按照规则在支付之后应该可以拿到一个现金红包的,但是他在支付了一个订单之后,却并没有收到这个现金红包,于是反馈给客服。
问题排查,查找系统中打印的日志。
发现,按理来说,订单系统在完成支付之后,会推送一条消息到RocketMQ里去,然后红包系统会从RocketMQ里接收那条消息去给用户发现金红包。
但是从订单系统和红包系统当天那个时间段的日志来看,只看到了订单系统有推送消息到RocketMQ的日志,但是并没有看到红包系统从RocketMQ中接收消息以及发现金红包的日志。
由此可见,问题可能就出在这儿了,是不是支付订单消息在传输的过程中丢失了?导致现金红包没有派发出去。
2.订单系统推送消息到MQ的过程会丢失消息吗?
答案是有可能会丢失。
原因有多种:
常见的例子,比如订单系统在推送消息到RocketMQ的过程中,是通过网络去进行传输的,但是这个时候恰巧可能网络发生了抖动,也就是网络突然有问题,导致这次网络通信失败了。于是这个消息就没有成功投递给MQ。
例子二:比如MQ确实收到消息了,但是它的网络通信模块的代码出现了异常,可能是他内部的网络通信的bug,导致信息没成功处理。
例子三:或者在写消息到RocketMQ的过程中,刚好遇到了某个Leader Broker自身故障,其他的Follower Broker正在尝试切换为Leader Broker,这个过程也可能会有异常。
3.消息到达MQ了,MQ自己会导致消息丢失吗?
即使我们的订单系统成功的把消息写入了MQ,也不能想当然的认为你写成功了,消息还是有丢失的可能。
os cache内丢失
根据对RocketMQ 底层原理的分析,可以得知,当你的消息写入MQ之后,其实MQ可能仅仅是把这个消息给写入到page cache里,也就是操作系统自己管理的一个缓冲区,这本质就是写入到内存。
在不了原理的情况下,可能以为真的写成功了一个消息,但是此时仅仅进入了 os cache,还没写入磁盘。
这个时候,一旦出现了Broker机器的崩溃,机器宕机的情况发生,那么os cache内存中的数据就没了。
在上述的情况下,碰上机器宕机,内存里的数据必然就会丢失了,机器即使重启了,然后重启broker进程,此时这个数据也没了。
4.消息进入磁盘了,还会丢失吗
会的,即使Broker把消息写入os cache之后,及时的刷入到磁盘文件里,但是也不能保证数据一定不丢失。
磁盘损坏问题
如果你的磁盘出现故障,比如磁盘坏了,那么上面存储的数据还是会丢失。
5.红包系统拿到了消息,就一定不会丢失了吗?
这是消费者端的问题,消费者也存在丢失消息的问题。
这里就涉及到了底层存储结构以及offset概念了。offset代表了一个消息的标识,代表了他的位置。
场景解读
如图,有两个消息,offset分别为1和2。
假设红包系统已经获取到了消息1了,然后消息1此时就在它的内存里,正准备运行代码去派发现金红包,但是,此时还没派发现金红包。
默认情况下,MQ的消费者有可能会自动提交已经消费的offset,那么如果此时你还没处理这个消息派发红包的情况下,MQ的消费者可能直接自动给你提交这个消息1的offset到broker去了,标示为你已经成功处理了这个消息,如下图:
恰巧在这个时候,我们的红包系统突然故障了,红包系统的机器重启了一下,然后此时内存里的消息1必然就丢失了,而且红包也没发出去。
6.总结
以上是生产者、MQ、消费者可能丢失消息的原因分析过程。
以上是关于26 生产案例:从RocketMQ全链路分析用户支付后没收到红包的原因的主要内容,如果未能解决你的问题,请参考以下文章