代码编织梦想

当RabbitMQ服务器挂了,它可能就丢失所有队列中的消息和任务。如果你想让RabbitMQ记住当前的状态和内容,就需要通过2件事来确保消息和任务不会丢失:同时将queue和messages标识为durable。

设置了队列和消息的持久化之后,当broker服务重启的之后,消息依旧存在。单只设置队列持久化,重启之后消息会丢失;单只设置消息的持久化,重启之后队列消失,既而消息也丢失。单单设置消息持久化而不设置队列的持久化显得毫无意义。

注意:已经定义的队列,再次定义是无效的!(RabbitMQ不允许重新定义一个已有的队列信息,也就是说不允许修改已经存在的队列的参数。如果你非要这样做,只会返回异常。咋整?

一个快速有效的方法就是重新声明另一个名称的队列,不过这需要修改生产者和消费者的代码,所以,在开发时,最好是将队列名称放到配置文件中。

这时,即使RabbitMQ服务器重启,新队列中的消息也不会丢失。)

消息在正确存入RabbitMQ之后,还需要有一段时间(这个时间很短,但不可忽视)才能存入磁盘之中,RabbitMQ并不是为每条消息都做fsync的处理,可能仅仅保存到cache中而不是物理磁盘上,在这段时间内RabbitMQ broker发生crash, 消息保存到cache但是还没来得及落盘,那么这些消息将会丢失。那么这个怎么解决呢?首先可以引入RabbitMQ的mirrored-queue即镜像队列,这个相当于配置了副本,当master在此特殊时间内crash掉,可以自动切换到slave,这样有效的保障了HA, 除非整个集群都挂掉,这样也不能完全的100%保障RabbitMQ不丢消息,但比没有mirrored-queue的要好很多,很多现实生产环境下都是配置了mirrored-queue的。还有要在producer引入事务机制或者Confirm机制来确保消息已经正确的发送至broker端。

RabbitMQ的可靠性涉及producer端的确认机制、broker端的镜像队列的配置以及consumer端的确认机制,要想确保消息的可靠性越高,那么性能也会随之而降,鱼和熊掌不可兼得,关键在于选择和取舍。

标记为持久化后的消息也不能完全保证不会丢失。虽然已经告诉RabbitMQ消息要保存到磁盘上,但是理论上,RabbitMQ已经接收到生产者的消息,但是还没有来得及保存到磁盘上,服务器就挂了(比如机房断电),那么重启后,RabbitMQ中的这条未及时保存的消息就会丢失。因为RabbitMQ不做实时立即的磁盘同步(fsync)。这种情况下,对于持久化要求不是特别高的简单任务队列来说,还是可以满足的。如果需要更强大的保证,那么你可以考虑使用生产者确认反馈机制。

RabbitMQ消息存储在间隔(几百毫秒)后或者当一个队列处于空闲状态时,将消息持久化到磁盘,以最大限度地减少fsync(2)调用的次数。

持久(persistent)和临时(transient)消息都可以写入磁盘。持久性消息一旦到达队列就会被写入磁盘,而临时消息只会在内存压力下将其从内存中逐出时写入磁盘。

“持久层”(persistence layer)指的是用于将两种类型的消息存储到磁盘的机制。

持久层有两个组件:队列索引(queue index)和消息存储(message store)。

队列索引负责维护关于给定消息在队列中的位置信息,以及它是否已被传递和确认。因此每个队列都有一个队列索引。

消息存储是消息的键值存储,由服务器中的所有队列共享。消息可以直接存储在队列索引中,也可以写入消息存储库。技术上分为两个消息存储器(一个用于临时,一个用于持久消息),但它们通常一起被称做“消息存储”。

内存开销:

每个队列为每个未确认的消息维护一些元数据。如果消息的目标是消息存储,则消息本身可以从内存中删除。

消息存储需要一个索引。默认消息存储索引对存储库中的每条消息使用少量内存。

将非常小的消息作为优化存储在queue index中,而将所有其他消息写入message store。(默认情况下,序列化大小小于4096字节(包括属性和标题)的消息存储在queue index中。)

版权声明:本文为博主原创文章,遵循 CC 4.0 BY-SA 版权协议,转载请附上原文出处链接和本声明。
本文链接:https://blog.csdn.net/Ajekseg/article/details/123790516

rabbitmq实战篇9-消息持久化_朱_哲的博客-爱代码爱编程

在前面的第七和第八节我们讲解了如何实现消息的发布和订阅。同时也提到了一些问题,比如说如果RabbitMQ服务挂掉了,那么我们的消息也就丢失了。怎么解决这样的问题呢?这就需要我们将消息进行持久化啦 这节,我们就在原有的基础上来讲解消息的持久化 如何持久化 其实,在之前我们已经将消息进行了持久化。只是我们并没有去关注。 简单说说消息发布订阅的流程: 生产者将消

rabbitmq 消息持久化实现_zwhfyy的博客-爱代码爱编程

如果想要让消息重启后仍然不丢失,那么需要将queue设置成 durable 为true , 并且发送消息的时候指明消息是要持久化得MessageProperties.PERSISTENT_TEXT_PLAIN channel.queueDeclare(QUEUE_NAME, true, false, false, null); channel.basi

rabbitmq之消息持久化_weixin_34062329的博客-爱代码爱编程

消息的可靠性是RabbitMQ的一大特色,那么RabbitMQ是如何保证消息可靠性的呢——消息持久化。 为了保证RabbitMQ在退出或者crash等异常情况下数据没有丢失,需要将queue,exchange和Message都持久化。 queue的持久化 queue的持久化是通过durable=true来实现的。 一般程

rabbitmq持久化_iiaythi的博客-爱代码爱编程_rabbitmq持久化

rabbitmq持久化 持久化是为提高rabbitmq消息的可靠性,防止在异常情况(重启,关闭,宕机)下数据的丢失 rabbitmq持久化分为三个部分: 交换器的持久化、队列的持久化和消息的持久化 交换器的持

rabbitmq中消息的存储_weixin_34318326的博客-爱代码爱编程

2019独角兽企业重金招聘Python工程师标准>>> 1. 大概原理: 所有队列中的消息都以append的方式写到一个文件中,当这个文件的大小超过指定的限制大小后,关闭这个文件再创建一个新的文件供消息的写入。文件名(*.rdq)从0开始然后依次累加。当某个消息被删除时,并不立即从文件中删除相关信息,

rabbitmq-消息持久化、获取方式、预取模式_weixin_33862514的博客-爱代码爱编程

2019独角兽企业重金招聘Python工程师标准>>> 1、消息的持久化 默认情况下,队列和交换器在服务器重启后都会消失,消息当然也是。将队列和交换器的durable属性设为true,缺省为false,但是消息要持久化还不够,还需要将消息在发布前,将投递模式设置为2。消息要持久化,必须要有持久化的队列、交换

消息队列RabbitMQ之消息持久化-爱代码爱编程

文章目录 前置知识RabbitMQ消息持久化为什么需要消息持久化?怎么设置消息持久化?JavaAPI设置持久化属性 前置知识 什么是消息队列RabbitMQ?参考博客:消息队列RabbitMQ之初学者 什么是消息队列的消息模型?参考博客:消息队列RabbitMQ之五种消息模型 什么是消息队列的基本消息模型?参考博客:消息队列Rabbit

Rabbitmq持久化与消息可靠性-爱代码爱编程

一、持久化机制 1.1、RabbitMQ 持久化机制 不管是持久化的消息还是非持久化的消息都可以被写入到磁盘,非持久化的消息在内存不够用时,有一部分数据会持久化到磁盘;重启之后,这些数据是不存在的。 具体持久化流程图如下: 1.1.1、队列持久化 队列的持久化是在定义队列时的durable参数来实现的,durable为true时,队列才会持久化。

rabbitmq——持久化消息-爱代码爱编程

使用rabbitmq做持久化消息,我们有两种方式。 使用自动确认机制,如果使用这种机制,消费者接收到消息之后自动确认,但是如果接收到消息之后,服务卡顿,就会导致这条消息不会重新发送给其他或者重启之后的消费者所在的服务器。导致间接性消息丢失。使用手动确认机制,当消息接收到之后,不要立即确认收到,而是先处理,处理之后,再确认这条消息。product.go