RabbitMQ 3.0 搞砸了一些东西
RabbitMQ 包含许多很棒的新功能。但为了实现其中的一些功能,我们需要改变一些东西。所以在这篇博文中,我将列出其中一些内容,以防您需要对它们进行任何操作。
镜像队列策略
有什么变化? 在 RabbitMQ 3.0 中,队列镜像不再通过声明队列时的 x-ha-policy 参数来控制。您的应用程序可以继续声明此参数,但这不会导致队列被镜像。取而代之的是,您可以声明一个或多个 策略 来控制哪些队列被镜像以及如何被镜像。
为什么会改变? 任何使用过镜像队列的人都会告诉你,要求应用程序知道哪些队列被镜像是一件很麻烦的事。新的方法将配置放在了代理中,而这才是它应有的位置,并且还支持随时更改镜像策略。
我该怎么做? 您需要确保您的队列仍然被镜像。有关完整的文档 请参见此处,但如果您只想确保所有队列(除了名称自动生成的队列)都在所有节点上被镜像,请运行
rabbitmqctl set_policy HA '^(?!amq\\.).*' '{"ha-mode": "all"}'
新联邦
有什么变化? RabbitMQ 3.0 中的联邦配置方式有很大不同。x-federation 交换类型已不再存在;取而代之的是,普通交换机可以通过策略进行联邦,就像 HA 队列一样。此外,上游也支持动态定义。
为什么会改变? 同样,您的应用程序不应该需要了解联邦。rabbitmq.config 中的联邦配置很复杂,让许多人感到困惑。而且,为了添加新的上游而需要重新启动代理也不是一件愉快的事情。
但是我的联邦设置还能正常工作!您把它弄坏了。 迁移到 新的联邦方式 将需要一些工作。在此期间,您可以使用 rabbitmq_old_federation 插件。这是 RabbitMQ 3.0 的 2.8.7 版联邦插件的回溯移植。要使用它
rabbitmq-plugins disable rabbitmq_federation
rabbitmq-plugins enable rabbitmq_old_federation
然后编辑您的 rabbitmq.config 文件,将 rabbitmq_federation 部分重命名为 rabbitmq_old_federation。
新集群
有什么变化? rabbitmqctl 中的集群设置命令已更改。
为什么会改变? 旧的命令不太用户友好。
我需要做什么? 如果您有现有的集群,则无需做任何事。如果您编写脚本来创建集群,则需要编辑这些脚本。特别是,rabbitmqctl cluster 应被替换为 rabbitmqctl join_cluster,但是
- 您无需先调用
rabbitmqctl reset - 您无需在命令行中列出所有节点;如果您提供了多个节点,它们将被视为要尝试与之集群的节点列表
- 新节点是磁盘节点还是内存节点由 --disc 和 --ram 标志决定。默认为磁盘节点。
有关更多详细信息,请参阅 文档。
移除 "immediate" 标志
有什么变化? 我们移除了对 AMQP basic.publish 中很少使用的 "immediate" 标志的支持。
为什么会这样做? 对 "immediate" 的支持使代码库的许多部分更加复杂,尤其是在镜像队列方面。它还阻碍了我们在镜像队列方面实现重要的性能改进。
我需要做什么? 如果您只是想能够发布将在未立即消费时被丢弃的消息,您可以将消息发布到 TTL 为 0 的队列。
如果您还希望发布者能够确定这种情况已发生,您还可以使用 DLX 功能将此类消息路由到另一个队列,发布者可以从该队列中消费它们。
frame_max
有什么变化? RabbitMQ 服务器现在会断开发送的帧大于连接协商的 frame_max 设置的客户端连接。
为什么会改变? 恶意(或编写不当)的客户端可能会发送任意大的帧,导致服务器内存耗尽。
我为什么会关心? 不幸的是,一些客户端未能正确实现 AMQP 帧。RabbitMQ 3.0 会允许客户端超出 frame_max 的一定字节数(以允许一次性错误和错误地排除帧头),但如果您的客户端帧有问题,在尝试发送大于 frame_max 的消息(默认值为 128kb;有关如何提高此值,请参阅 文档)后,您将被断开连接。
管理和 JSON-RPC 通道端口更改
有什么变化? 管理插件现在监听端口 15672,而不是 55672。JSON-RPC 通道现在监听端口 15670,而不是 55670。
为什么会改变? 旧端口在许多操作系统上都位于临时端口范围内,这意味着 Web 浏览器和其他客户端应用程序可能会任意使用这些端口。你不应该监听这些端口。
特别是,我们注意到管理插件 Web UI 在指向本地主机上停止的代理时,可能会导致浏览器连接到自身的 55672 端口。这会阻止代理重新启动。
我必须做什么? 希望是无事可做。RabbitMQ 会尝试打开旧端口并发送 HTTP 重定向到新端口。但如果您使用的不是 Web 浏览器而是其他应用程序来访问 HTTP API,它可能不支持 HTTP 重定向。如果不支持,您需要将其指向新端口。
请注意,3.0 版本之前的 rabbitmqadmin 就是这样的应用程序。抱歉。
另请注意,STOMP 插件仍然监听端口 61313。尽管该端口位于临时端口范围内,但它是 STOMP 最接近标准端口的端口,因此我们必须坚持使用它。
expiration 属性
有什么变化? 现在,我们期望消息属性中的 expiration 字段(如果设置了的话)可以解析为整数。
为什么会改变? 为了支持 每条消息的 TTL,我们需要一个地方来获取消息的 TTL,而这是最明显的位置。不幸的是,AMQP 标准将其定义为字符串,因此我们会尝试将其解析为整数,如果不是,则会抛出通道异常。
我必须做什么? 确保如果您正在使用该属性,那么您这样做的原因是因为您期望 RabbitMQ 在消息过期时将其删除,并确保它被设置为一个可以解析为整数的字符串。