我在集群 (2 个节点) 中拥有 RabbitMQ 服务器。所有队列都是持久的、镜像的,并且所有消息都设置为持久的。
我编写了应用程序来通过 RabbitMQ 队列同步数据库更改。
在大多数情况下,队列是空的,因为消费者读取更改的速度与生产者生产更改的速度一样快。
不幸的是,在初始同步时(当所有表的所有行都已传输时),队列中有大量消息(例如 10GB)等待使用,因为在大多数情况下,从数据库读取数据比写入数据更快。我以为这些消息将保存到磁盘,但似乎所有消息也存储在 RAM 中。因此,一段时间后,所有 RAM 都被使用(无论我有多少 RAM),它开始阻止发布者。
有人知道为什么 RabbitMQ 将所有持久消息也保存在 RAM 中吗?这是“设计使然”的功能吗?
我尝试使用不同的消息大小(从 512kB 到 5MB)。结果是一样的。此外,消费者连接/未连接或为其设置不同的 QOS 也没有任何区别。
版本:RabbitMQ 3.1.0,Erlang R14B04
答案1
这是一项功能,即使您的消息是持久性的,RabbitMQ 也会将消息保存在 RAM 中,原因是如果有足够的 RAM,就无需承担磁盘读取的成本。RabbitMQ将要在内存压力下将它们交换到磁盘(即使它不是持久消息)。
您的发布者由于流量控制而被阻止,您可以使用 切换触发流量控制的设置vm_memory_high_watermark
。