如何避免消息队列数据丢失

58 篇文章 1 订阅

这个问题我们首先要定位,消息为什么会丢失

rabbitMq

先按照rabbitMq的流程来讲,有三种情况下会出现消息丢失的情况:
在这里插入图片描述
这三种情况出问题的主体分别是生产者、中间件、消费者
下面就根据这三种情况具体分析我们该怎么做

1、生产者丢失数据
可以使用rabbitMq中的事务功能,就是在生产者发送数据之前开启rabbitmq的事务功能(channel.txSelect),然后发送消息的时候生产者会阻塞等待这条消息发送成功,确保rabbitmq接收到消息,然后可以提交事务(channel.txCommit)。如果消息发送失败,没有接收到rabbitmq的回执,或者接收到异常报错的情况,那么会进行事务回滚(channel.txRollback),然后重试发送消息。但是这种情况必然会损失rabbitmq的吞吐量,造成效率低下
所以一般来说会使用另一种方式,开启rabbitmq的confirm模式,把rabbitmq的channel设置为confirm模式。那么发送完消息之后,rabbitmq接收到了消息会回调生产者的一个接口,告知接收成功;如果接收失败会告诉生产者接收失败了,你需要重发。

2、rabbitmq消息丢失
这个就需求开启rabbitmq的持久化,将接收到消息后将数据持久化到磁盘中,这样哪怕rabbitmq自己挂掉了,重启之后也能在磁盘中获取到之前的数据。除非是接收到消息还没存入磁盘就挂掉了,这基本是很小的概率。
持久化有两个步骤,一个是创建queue的时候将其持久化,这样可以保证持久化queue的元数据,但是不会持久化queue里面的数据。另一个是发送消息的时候将deliveMode设置为2,意思是将消息设置为持久化,这样一来就rabbitmq就会保证数据不丢失
这个持久化可以和上面生产者中的confirm模式结合起来,只有rabbitmq将消息持久化到磁盘之后,在通知生产者接收消息成功了,这样哪怕持久化之前mq挂了,也不怕消息丢失,因为生产者可以重发。

3、消费者消息丢失
这种消息丢失的情况呢,一般就是因为消费者开启了autoAck机制,是一种向rabbitmq自动回复处理完消息的通知机制。会出现消费者本身还未处理完,但是autoAck提前发送了,后面又突然宕机,就会导致这条消息丢失掉。
这种情况就是不要使用自动的autoAck,把这个功能关掉。自己来处理消息,保证消息处理完成之后再手动调用rabbitmq的ack接口来通知它我们已经处理完这条消息了,如果rabbitmq长时间未接受到成功的回执那么就会将消息分发给其他的消费者。

总结一下rabbitMq保证数据不丢失就是,生产者开启confirm模式保证数据被rabbitmq接收,rabbitmq本身开启磁盘持久化,消费者将自动的autoAck机制关闭改为处理完消息后手动提交ack

kafka

再讲一下kafka 的情况,和rabbitmq的情况类似
在这里插入图片描述

1、消费者丢失数据
也是因为自动提交了offset,但是本身还未处理完消息数据,一旦处理过程中出现问题,就会导致消息丢失。所以需要保证业务处理完之后,再手动向kafka提交offset告知处理完成。

2、kafka消息丢失
这种情况一般是因为,broker的leader突然宕机了,但是follower还没有将所有数据同步到自己这边,然后follower被选举为新的leader。那么就会造成数据丢失。
避免这种情况的话需要设置kafka的4个参数:

  • topic设置replication.factor参数:这个值必须大于等于2,也就是说每个partiton必须有至少两个副本,一个leader、一个follower。
  • kafka服务端设置min.insync.raplicas参数:这个值大于等于1,也就是说leader必须要感知到至少一个follower还在同步自己的数据。这样才能确保leader挂掉之后还能有一个follower顶上。
  • 在producer端设置acks=all:意思是生产者发送给kafka的数据,只有leader和所有的follower都同步成功了,才可以认为是发送成功。
  • 在producer端设置retries=MAX :这个值要设置很大很大,来保证数据发送失败时一直会重试

3、生产者会不会丢数据
如果在producer端设置acks=all,难么就不会再发送消息的过程中丢失消息,如果没有发送成功会一直去发送消息。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

木小同

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值