rabbit集群

来源:互联网 发布:mac远程桌面win10 编辑:程序博客网 时间:2024/05/29 13:29

开始独立节点
集群是通过重新配置现有的RabbitMQ节点到集群配置来设置。因此,第一步是在正常方式启动RabbitMQ的所有节点:

rabbit1$ rabbitmq-server -detachedrabbit2$ rabbitmq-server -detachedrabbit3$ rabbitmq-server -detached

这将创建三个独立的RabbitMQ中间件,一个在每个节点上,用来确认的cluster_status命令:

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1]}]},{running_nodes,[rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit2]}]},{running_nodes,[rabbit@rabbit2]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit3]}]},{running_nodes,[rabbit@rabbit3]}]...done.

RabbitMQ中间件的节点名称从rabbitmq-server shell脚本开始,
rabbit@shorthostname ,这个短节点名称是小写(如:rabbit@rabbit1) 。如果你用rabbitmq-server.bat批处理文件,这个短节点名字是大写(rabbit@RABBIT1) 。当你键入节点名称时,重要情况,这些字符串必须匹配。

创建集群
为了在集群中连接起来3个节点,我们告诉2个节点: rabbit@rabbit2 和 rabbit@rabbit3加入集群的第三个, rabbit@rabbit1 。
我们首先连接 rabbit@rabbit2 和 rabbit@rabbit1 在集群里。为了实现这个,我们停止rabbit@rabbit2 的RabbitMQ应用,加入rabbit@rabbit1 集群,然后重启RabbitMQ应用。
注意:加入一个集群节点隐式重置,因此,移除了以前存在于该节点上的所有资源和数据。

rabbit2$ rabbitmqctl stop_appStopping node rabbit@rabbit2 ...done.rabbit2$ rabbitmqctl join_cluster rabbit@rabbit1Clustering node rabbit@rabbit2 with [rabbit@rabbit1] ...done.rabbit2$ rabbitmqctl start_appStarting node rabbit@rabbit2 ...done.

我们在任意一个节点上通过运行cluster_status命令看到2个节点加入到集群了:

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit1,rabbit@rabbit2]}]...done.

现在我们加入 rabbit@rabbit3 到同一个集群。步骤与上面的步骤相同,只是这次我们集群rabbit2来证明选择的节点没有集群关系–它足以提供一个在线节点,并且该节点将集群到指定节点所属的集群中。

rabbit3$ rabbitmqctl stop_appStopping node rabbit@rabbit3 ...done.rabbit3$ rabbitmqctl join_cluster rabbit@rabbit2Clustering node rabbit@rabbit3 with rabbit@rabbit2 ...done.rabbit3$ rabbitmqctl start_appStarting node rabbit@rabbit3 ...done.

我们在任意一个节点中通过运行cluster_status命令看到三个节点已经加入到集群了:

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit3,rabbit@rabbit2,rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit3,rabbit@rabbit1,rabbit@rabbit2]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit3,rabbit@rabbit2,rabbit@rabbit1]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1,rabbit@rabbit3]}]...done.

跟着以上步骤,我们可以随时新增节点到集群中,且集群在运行的时候。

重启集群节点
已经加入到集群的节点可以随时停止。它们也可以奔溃。在这两种情况下,集群继续运行不受影响,当它们再次启动的时候,可以自动“追上”其他节点。
我们停止 rabbit@rabbit1 和 rabbit@rabbit3 节点,验证集群状态的步骤:

rabbit1$ rabbitmqctl stopStopping and halting node rabbit@rabbit1 ...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit3,rabbit@rabbit2]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit3]}]...done.rabbit3$ rabbitmqctl stopStopping and halting node rabbit@rabbit3 ...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit2]}]...done.

现在我们再次启动节点,如我们进行的一样来检查集群状态:

rabbit1$ rabbitmq-server -detachedrabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit1,rabbit@rabbit2]}]...done.rabbit3$ rabbitmq-server -detachedrabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1,rabbit@rabbit3]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2,rabbit@rabbit3]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1,rabbit@rabbit3]}]...done.

这里有一些注意事项:
当整个集群被删除时,最后一个要被停止的节点必须是第一个联机的节点。如果不是这样,这个节点将等待30秒,最后一个磁盘节点返回在线,然后失败。如果最后一个脱机的节点不能被备份,可以用forget_cluster_node命令从集群中移除-咨询rabbitmqctl帮助更多信息。
如果所有的节点都以同时或不受控制的方式停止(例如停电),则可以留下一个情况,即所有节点都认为其它节点在它们之后停止。在这种情况下,你可以在一个节点上使用force_boot命令使它再次启动。

打断节点
当节点不再是集群的一部分时,需要从其中显式地移除。我们首先从集群中移除rabbit@rabbit3,将其回归独立运作。要做到这一点,我们需要停止在 rabbit@rabbit3上停止RabbitMQ应用,重置节点,并重启RabbitMQ应用。

rabbit3$ rabbitmqctl stop_appStopping node rabbit@rabbit3 ...done.rabbit3$ rabbitmqctl resetResetting node rabbit@rabbit3 ...done.rabbit3$ rabbitmqctl start_appStarting node rabbit@rabbit3 ...done.

注意,它会列出 rabbit@rabbit3 作为一个节点同样有效。
在节点上运行cluster_status命令,确认 rabbit@rabbit3 现在不再是集群的一部分,并且操作独立:

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1,rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit1,rabbit@rabbit2]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit3]}]},{running_nodes,[rabbit@rabbit3]}]...done.

我们也可以远程删除节点。这是有用的,例如,当必须处理一个没有响应的节点。我们比如从 rabbit@rabbit2 移除 rabbit@rabbit1。

rabbit1$ rabbitmqctl stop_appStopping node rabbit@rabbit1 ...done.rabbit2$ rabbitmqctl forget_cluster_node rabbit@rabbit1Removing node rabbit@rabbit1 from cluster ......done.

注意:rabbit1仍然认为它与rabbit2集群,并且尝试启动,将会发生错误。我们需要重置它才能让它重新启动。

rabbit1$ rabbitmqctl start_appStarting node rabbit@rabbit1 ...Error: inconsistent_cluster: Node rabbit@rabbit1 thinks it's clustered with node rabbit@rabbit2, but rabbit@rabbit2 disagreesrabbit1$ rabbitmqctl resetResetting node rabbit@rabbit1 ...done.rabbit1$ rabbitmqctl start_appStarting node rabbit@mcnulty ......done.

cluster_status命令现在显示3个全部的节点都作为独立的RabbitMQ中间件操作。

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1]}]},{running_nodes,[rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit2]}]},{running_nodes,[rabbit@rabbit2]}]...done.rabbit3$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit3 ...[{nodes,[{disc,[rabbit@rabbit3]}]},{running_nodes,[rabbit@rabbit3]}]...done.

注意, rabbit@rabbit2 保留集群残余状态,而 rabbit@rabbit1 和 rabbit@rabbit3
初始化了RabbitMQ中间件,如果我们想重新初始化 rabbit@rabbit2 ,我们遵循其它
节点相同的步骤:

rabbit2$ rabbitmqctl stop_appStopping node rabbit@rabbit2 ...done.rabbit2$ rabbitmqctl resetResetting node rabbit@rabbit2 ...done.rabbit2$ rabbitmqctl start_appStarting node rabbit@rabbit2 ...done.

升级集群
当从一个大的或小的RabbitMQ版本升级为另一个(如:3.0.x 到 3.1.x,或2.x.x 到 3.x.x),或者更新Erlang,整个集群必须采取升级(因为集群不能像这样运行混合的版本)。当从一个补丁版本升级到另一个补丁版本时(如3.0.x到3.0.y),通常不会出现这种情况,除非在发布说明中另有说明;这些版本可以混在一个集群中。因此,强烈建议在更新之前查阅发行说明。

一些补丁版本已知需要启动的集群范围:
从3.0.x系列开始,3.0.0不能混合之后的版本
从3.6.x系列开始,3.6.6和之后的版本不能混合之前的版本。

当升级主要/次要版本时,必要时RabbitMQ会自动更新它的持久化数据结构。在集群中,这个任务由要启动的第一个磁盘节点执行(“更新”节点)。因此当RabbitMQ集群升级,你不应该首先试图启动任何内存节点;启动RAM节点将发出错误消息,无法启动。

虽然没有严格的必要,当节点将要升级时,决定提前停止最后一个节点,启动第一个节点,这是一个好主意。否则改变集群配置,停止升级的节点和停止最后一个节点将丢失。

自动升级只可能从RabbitMQ 2.1.1版本和之后的版本。如果你有一个较早的集群,你需要重建它们升级。

单台机器上的集群
某些情况下,在一台机器上运行RabbitMQ节点是很有用的。这通常是有用的,对于在桌面或笔记本电脑上没有为集群启动多个虚拟机的开销的集群实验。
为了运行多个RabbitMQ节点在一个单一的机器,确保节点有不同的节点名称,数据存储位置,日志文件位置,和绑定不同的端口是必需的。详情见RABBITMQ_NODENAME, RABBITMQ_NODE_PORT, and RABBITMQ_DIST_PORT。

你可以在同一个主机上通过rabbitmq-server重复调用来手动启动多个节点(Windows上是rabbitmq-server.bat)。如:

$ RABBITMQ_NODE_PORT=5672 RABBITMQ_NODENAME=rabbit rabbitmq-server -detached$ RABBITMQ_NODE_PORT=5673 RABBITMQ_NODENAME=hare rabbitmq-server -detached$ rabbitmqctl -n hare stop_app$ rabbitmqctl -n hare join_cluster rabbit@`hostname -s`$ rabbitmqctl -n hare start_app

将设置2个节点,都是磁盘节点。注意:如果你的RabbitMQ开放了任何端口除了AMQP,你需要配置那些不冲突。这可以通过命令行来完成:

$ RABBITMQ_NODE_PORT=5672 RABBITMQ_SERVER_START_ARGS="-rabbitmq_management listener [{port,15672}]" RABBITMQ_NODENAME=rabbit rabbitmq-server -detached$ RABBITMQ_NODE_PORT=5673 RABBITMQ_SERVER_START_ARGS="-rabbitmq_management listener [{port,15673}]" RABBITMQ_NODENAME=hare rabbitmq-server -detached

当管理插件安装时,将启动2个节点(然后可以集群)。

主机名改变
RabbitMQ节点用主机名来互相交流。因此,所有节点名称必须能够解析所有的集群节点的名称。对于rabbitmqctl这样的工具也是如此。
除此之外,默认情况下,RabbitMQ名称数据库目录使用当前系统的主机名。如果主机名改变,一个新的空数据库被创建。为了避免数据丢失,建立一个固定的和可解析的主机名是至关重要的。
当主机名变化时,你应该重启RabbitMQ:

$ /etc/init.d/rabbitmq-server restart

类似的效果,可以使用 rabbit@localhost 作为中间件节点的名称来实现。该解决方案的影响是,集群将无法工作,因为选择的主机名不能解析远程主机的路由地址。当从远程主机调用时,rabbitmqctl命令同样失败。一个更复杂的不受这个弱点的解决方案是使用DNS,如:Amazon Route 53,如果运行在EC2。如果你想用完整的主机名作为你的节点名(RabbitMQ默认的短名称),使用DNS,完整的主机名是可以解析的,你可能需要研究设置环境变量RABBITMQ_USE_LONGNAME=true。

防火墙节点
当节点在数据中心或在一个可靠的网络时,存在防火墙节点的情况,除了分离防火墙。同样,不建议在广域网或节点之间的网络链路不可靠时进行集群。
在最常见的配置中,您需要打开多个标准端口:
4369 (epmd)
5672, 5671 (AMQP 0-9-1 and 1.0 without and with TLS)
25672(这个端口被Erlang分布用于节点间通信和命令行工具使用)
This port used by Erlang distribution for inter-node and CLI tools communication and is allocated from a dynamic range (limited to a single port by default, computed as AMQP port + 20000). See networking guide for details.
15672 (if management plugin is enabled)
61613, 61614 (if STOMP is enabled)
1883, 8883 (if MQTT is enabled)

从客户端连接集群
客户机可以与集群内的任何节点正常连接。如果该节点失败,则其余的群集生存,然后客户端应注意关闭连接,应该能够重新连接到一些幸存的集群成员。一般来说,不建议烤入节点主机名或IP地址到客户端应用;本文介绍了刚性需要客户端应用程序的编辑、编译和部署该集群变化或集群中的节点数量的配置变化。相反,我们建议更抽象的方法:这可能是一个动态的DNS服务,有一个很短的TTL配置,或一个普通的TCP负载平衡器,或某种移动IP实现与起搏器或类似技术。总的来说,这方面的管理连接到集群内的节点是超越RabbitMQ本身的范围,我们建议使用其他专门设计来解决这些问题的技术。

带内存节点的集群
RAM节点只保留它们的元数据在内存中。由于RAM节点不必像磁盘节点对磁盘写入一样多,它们可以执行更好。然而,注意,由于持久队列数据总是存储在磁盘上,性能改进只影响资源管理(如:增加或移除队列,交换机或vhosts),但是没有发布或消耗速度。

内存节点是一个先进的用例;设置第一个群集时,不应该使用它们。你应该有足够的磁盘节点来处理你的冗余需求,然后如果需要,添加额外的RAM节点的规模。

只包含RAM节点的群集是脆弱的,如果群集停止,您将无法重新启动,将丢失所有数据。RabbitMQ将防止在许多情况下,创建只有RAM节点的集群,但它不能完全阻止它。

创建内存节点
当它首次加入群集时,我们可以声明一个节点作为RAM节点。我们如之前一样用rabbitmqctl join_cluster 来做,但是传递–ram标志:

rabbit2$ rabbitmqctl stop_appStopping node rabbit@rabbit2 ...done.rabbit2$ rabbitmqctl join_cluster --ram rabbit@rabbit1Clustering node rabbit@rabbit2 with [rabbit@rabbit1] ...done.rabbit2$ rabbitmqctl start_appStarting node rabbit@rabbit2 ...done.

RAM节点在群集状态中被显示为:

rabbit1$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit1 ...[{nodes,[{disc,[rabbit@rabbit1]},{ram,[rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit2,rabbit@rabbit1]}]...done.rabbit2$ rabbitmqctl cluster_statusCluster status of node rabbit@rabbit2 ...[{nodes,[{disc,[rabbit@rabbit1]},{ram,[rabbit@rabbit2]}]}, {running_nodes,[rabbit@rabbit1,rabbit@rabbit2]}]...done.

改变节点类型
我们可以改变从RAM到磁盘的节点类型,反之亦然。说我们想颠倒 rabbit@rabbit2和rabbit@rabbit1的类型,把前者从RAM节点变成磁盘节点,后者从磁盘节点变成RAM节点。我们可以使用change_cluster_node_type命令来做。节点首先必须被停止。

rabbit2$ rabbitmqctl stop_appStopping node rabbit@rabbit2 ...done.rabbit2$ rabbitmqctl change_cluster_node_type discTurning rabbit@rabbit2 into a disc node ......done.Starting node rabbit@rabbit2 ...done.rabbit1$ rabbitmqctl stop_appStopping node rabbit@rabbit1 ...done.rabbit1$ rabbitmqctl change_cluster_node_type ramTurning rabbit@rabbit1 into a ram node ...rabbit1$ rabbitmqctl start_appStarting node rabbit@rabbit1 ...done.
1 0
原创粉丝点击