RocketMQ在生产阶段、消费阶段、消息持久化阶段消息可能会丢失。
生产阶段
生产者向broker发送消息,这个阶段是网络发送,是有可能会导致消息丢失的。
同步发送:生产者向broker发送消息,broker接收到消息后返回一个ack,生产者会等待ack返回,如果生产者没有收到ack,就会出异常,那么我们就可以去捕获异常,然后去做重试。
异步发送:生产者不会等待ack,但是broker接收到消息后会去调用回调函数,成功接收到消息会回调onSuccess,那我们就可以记录一下发送成功;如果没有收到消息会回调onException,我们同样可以进行重试。
消费阶段
消费者拉模式去拉取消息的时候可能会有消息丢失的问题,offset用于定位到消息,如果消费者在消息还未消费成功就将offset返回,之后消息消费出错,那么这条消息就丢失了,所以我们要确保消息消费成功了再返回offset。
消息持久化阶段
broker接受到消息后,会先把消息存储到内存中,之后再刷到磁盘当中。
同步刷盘:broker存储消息到内存中后立刻刷到磁盘中,成功之后返回ack,不会有消息丢失的风险。
异步刷盘:broker存储消息到内存中,之后就直接返回ack,等内存中消息达到一定量之后,再刷到磁盘中。如果在刷盘过程中出现错误,那么这些消息也就丢失了。
主从复制阶段和消息持久化阶段同理,尽量选择同步复制。