Java 杂谈java后端开发中间件

rabbitmq 消息100%投递的解决方案

2019-02-20  本文已影响3人  fkxuexi

一、前言:

现在大多都使用 MQ 来做系统的异构,来做系统的解耦,系统的的模块相当于寄信者与收信者,MQ 则扮演者邮局的角色。作为一个中转的角色,就需要确保消息的100%投递。今天我们就来研究一下如何确保消息的100%的投递。

二、先谈谈rabbitmq的特性:

rabbitmq 所做的确保是:只要你把消息投递到 Broker 中,那么我就确保这个消息会送达到消费者的手中。当然这是有前提条件的,比如:① 你需要进行手动应答,② 最起码 Broker 不挂,且消息进行了持久化等。

结合 rabbitmq 的特性来做分析,针对于投递端,我们只需要确保把消息发送到Broker 中即可,那么如何保证可靠性呢,分下列步骤:

三、生产者的投递的可靠性保障:

3.1 先上一个示意图:

image.png

3.2 就上述的图示,我们逐步解析:

上述的方案看似完美无缺,但是细想,如果在 step4 中 Broker 发送应答的过程中,网络出现问题这个消息没有到达生产者会导致整个流程进入补偿的流程当中,此时 Broker 中就有两条消息,也就是发成了重复的投递的问题,所以接下来我们要在消费端来处理这个问题。

四、消费端的幂等:

4.1 导致需要解决幂等的原因

4.2 就上述我们的机制的解决:

因为上述我的消息都有唯一的标识,所以我们只需要查找对应的消息对应的标识来判断其状态即可

4.3 构建唯一标识的方案:

首先说明不同的方案使用不同的应用场景,不要一上来你就说十几万的并发怎么样的,这个慢慢来,一步步往这里走

4.3.1 利用数据库自增id

优点:
1):不能再简单了,在并发不大的情况可以接受
2):对分页和排序是有帮助的
缺点:
1):分库分表和读写分离多住从的情况下不适用
2):性能达不到要求时,不利于扩展
3):不同数据库的语法实现不一样

4.3.2 利用 redis 来生成id

优点:
1):redis 单线程可以生成全局唯一ID
2):可以使用 redis 集群获取更高的吞吐量
缺点:
1):引入新的组件,增加系统复杂度
2):需要注意处理并发问题

4.3.3 利用 twitter 开源的 snowflake

snowflake 是 twitter 开源的一个分布式的 ID 的生成算法,结果是一个 long 的ID,使用 41bit 作为毫秒数,10bit 作为机器 ID(5个 bit 是数据中心,5个 bit 是机器 ID) 12 bit 作为毫秒内的流水号(每个节点每毫秒可以产生 2^12 = 4096 个 ID)最后是一个符号位,
优点:
1):不依赖数据库和其他的中间件,且性能尚可
缺点:
1):是有依赖时间的,如果各个机器的失重不同步就会出现不适全局递增的情况

博客首发地址csdn:https://blog.csdn.net/weixin_42849915
简书地址:https://www.jianshu.com/u/4b48be4cf59f
希望结识更多的乐于分享的伙伴一起前行

上一篇 下一篇

猜你喜欢

热点阅读