RabbitMQ入门教程(十四):RabbitMQ单机集群搭建
2017-12-05 18:54
489 查看
集群简介
理解集群先理解一下元数据队列元数据:队列的名称和声明队列时设置的属性(是否持久化、是否自动删除、队列所属的节点)
交换机元数据:交换机的名称、类型、属性(是否持久化等)
绑定元数据:一张简单的表格展示了如何将消息路由到队列。包含的列有 交换机名称、交换机类型、路由键、队列名称等
vhost元数据:为vhost内队列、交换机和绑定提供命名空间和安全属性
一个队列的完整内容包括队列的元数据和队列的内容
绑定表类似于下图
单节点RabbitMQ
Erlang的集群是通过Erlang cookie(.erlang.cookie文件)的方式来允许互相通信
单机集群:就是在一台物理机器上启动多个节点,每个节点作为作为集群的一部分。此种方式只适合在学习的时候玩一下,或者在验证在生产环境中出现特殊情况的现象,在实际情况下不会使用单机集群,因为如果服务器宕机了整个服务器将完全不能再使用。
普通集群:这里指的每台物理机器作为一个节点,此种模式消息只存在其中一个节点上,集群中的其他节点仅有相同的元数据(即队列元数据),当拥有消息的节点宕机了,那么其他节点就无法获取故障节点中尚未消费的消息,如果故障节点使用了持久化,那只能等故障节点恢复后才能从该节点上的队列进行消费,如果没有持久化,那么所有消息将丢失。例如消费者A连接到节点1,但是队列内容并不在节点1上,可以通过消费者所消费的队列找到该队里所在的节点,然后从该节点上获取消息,返回给消费者。
镜像集群:与普通集群不同,镜像集群会把对垒结构和消息都同步到每个节点。该模式的好处就是随便连接到哪个节点都能获取到消息,坏处是,当队列数量很多,消息也很多的时候,集群内部的网络带宽将会被这种同步通讯大量的消耗掉,此种模式用于可靠性要求较高的场合中。
主从集群warren: 是指一对主备独立服务器,并设置一台负载均衡器来处理故障转移,使用HAproxy设置备用服务器很简单,使用backup来标记一下,只有当主服务器不可用时才使用备用服务器。
// 每5秒对服务器进行健康检查,后台服务器失败3次之后被认为不可用,也就是15秒后消费者会连接到备用服务器 server rabbit 127.0.0.1:5672 check inter 5000 rise 2 fall 3 server rabbit1 127.0.0.1:5673 backup check inter 5000 rise 2 fall 3
内存节点RAM和磁盘节点disk
内存节点:将所有的队列、交换机、绑定、用户、权限、vhost的元数据都存储在内存中 。内存节点更快
磁盘节点:将数据存放在磁盘上。磁盘节点需要保存集群的配置信息
单节点系统只允许磁盘节点,否则每次重启所有数据将会丢失。 一个集群至少有一个节点是磁盘节点,其他节点可以都是内存节点,当节点加入或者离开集群时都要将变更通知到至少一个磁盘节点。实际使用时至少要两个磁盘节点,原因是如果只有一个磁盘节点,恰巧磁盘节点崩溃了,那么RabbitMQ将不能创建队列、创建交换机、创建绑定、添加用户、更改权限、添加或删除节点等操作,可以正常的发布和消费消息。 在实际使用经常将集群的配置放到磁盘节点上来保存。
单机集群搭建详细步骤
第一步:为每个节点配置节点名称和端口号
配置第一个节点// 启动第一个节点,节点名称为rabbit@MacOSX // MacOSX是我的机器名,这里可以改成自己的机器名或者用localhost RABBITMQ_NODE_PORT=5672 RABBITMQ_NODENAME=rabbit@MacOSX rabbitmq-server
配置第二个节点
// 启动第二个节点, 节点名称为rabbit1@MacOSX,这里使用-detached后台模式启动 RABBITMQ_NODE_PORT=5673 RABBITMQ_SERVER_START_ARGS="-rabbitmq_management listener [{port,15673}] -rabbitmq_stomp tcp_listeners [61614] -rabbitmq_mqtt tcp_listeners [1884]" RABBITMQ_NODENAME=rabbit1 rabbitmq-server -detached
配置第三个节点
// 启动第三个节点,节点名称为rabbit2@MacOSX RABBITMQ_NODE_PORT=5674 RABBITMQ_SERVER_START_ARGS="-rabbitmq_management listener [{port,15674}] -rabbitmq_stomp tcp_listeners [61615] -rabbitmq_mqtt tcp_listeners [1885]" RABBITMQ_NODENAME=rabbit2 rabbitmq-server -detached
所有节点启动成功后可以登录RabbitMQ Management看一下
第二步:将rabbit1加入到rabbit中
// 加入集群时可以指定是磁盘模式还是内存模式,默认是disk,可以通过--ram来指定 rabbitmqctl -n rabbit1@MacOSX stop_app rabbitmqctl -n rabbit1@MacOSX reset rabbitmqctl -n rabbit1@MacOSX join_cluster rabbit@MacOSX rabbitmqctl -n rabbit1@MacOSX start_app
// 查看指定节点的状态 rabbitmqctl status -n rabbit1
第三步:将rabbit2加入到rabbit中
rabbitmqctl -n rabbit2@MacOSX stop_app rabbitmqctl -n rabbit2@MacOSX reset rabbitmqctl -n rabbit2@MacOSX join_cluster rabbit@MacOSX --ram rabbitmqctl -n rabbit2@MacOSX start_app // 查看集群的状态 rabbitmqctl cluster_status -n rabbit@MacOSX
参考文章: http://www.zhimengzhe.com/mac/333192.html
HAProxy负载均衡
1. 安装
brew install haproxy // 查看haproxy版本 haproxy -version
2. 配置haproxy.cfg
在usr/local/Cellar/haproxy/目录下创建haproxy.cfg文件,并进行配置( 如果要使用warren方式,要配置成主备模式只需要在备用服务器上使用backup标记一下即可)global log 127.0.0.1 local0 info #[日志输出配置,所有日志都记录在本机,通过local0输出] maxconn 4096 #默认最大连接数,需考虑ulimit-n限制 defaults # 默认负载均衡配置 log global mode tcp #默认的模式mode { tcp|http|health },tcp是4层,http是7层,health只会返回OK option tcplog option dontlognull #不记录健康检查日志信息 retries 3 #三次连接失败就认为是服务器不可用,也可以通过后面设置 option abortonclose #当服务器负载很高的时候,自动结束掉当前队列处理比较久的链接 maxconn 2000 #默认的最大连接数 timeout connect 5000ms #连接超时 timeout client 12000ms #客户端超时 timeout server 12000ms #服务器超时 listen rabbitmq_local_cluster mode tcp bind 127.0.0.1:5670 # 前端IP, 供消费者和生产者使用 balance roundrobin # 负载均衡方式, 轮询方式 server rabbit 127.0.0.1:5672 check inter 5000 rise 2 fall 3 server rabbit1 127.0.0.1:5673 check inter 5000 rise 2 fall 3 server rabbit2 127.0.0.1:5674 check inter 5000 rise 2 fall 3 # 数据统计页面 listen private_monitoring mode http bind 127.0.0.1:8100 option httplog stats enable stats uri /stats stats refresh 5s
3. 启动HAProxy
/usr/local/Cellar/haproxy/1.8.1/bin/haproxy -f /usr/local/Cellar/haproxy/haproxy.cfg
4. 访问数据统计页面http://localhost:8100/stats
public class Consumer1 { @Test public void testBasicConsumer1() throws Exception{ ConnectionFactory factory = new ConnectionFactory(); factory.setVirtualHost("/"); // ip和port为HAProxy的地址和端口 factory.setHost("127.0.0.1"); factory.setPort(5670); factory.setUsername("guest"); factory.setPassword("guest"); Connection connection = factory.newConnection(); final Channel channel = connection.createChannel(); String EXCHANGE_NAME = "exchange.direct"; String QUEUE_NAME = "queue_name"; channel.exchangeDeclare(EXCHANGE_NAME, BuiltinExchangeType.DIRECT); channel.queueBind(QUEUE_NAME, EXCHANGE_NAME, "key"); Consumer consumer = new DefaultConsumer(channel) { @Override public void handleDelivery(String consumerTag, Envelope envelope, AMQP.BasicProperties properties, byte[] body) throws IOException { String message = new String(body, "UTF-8"); System.out.println(message); } }; channel.basicConsume(QUEUE_NAME, true, consumer); Thread.sleep(100000); } }
常见错误
在集群中,在使用rabbitmqctl命令时经常会报错,在使用rabbitmqctl命令时,首先会启动erlang集群,而erlang集群需要保证.erlang.cookie内容保持一致,此时如果cookie不一致,会导致rabbitmqctl命令报错;rabbitmqctl还会启动erlang的mnesia数据库,而数据在启动时会查找一个和主机名相同的schema, 所以要保证这个schema的名字和当前主机名字保持一致,如果不一致mnesia数据库就启动不起来,就会导致rabbitmqctl报错,所以解决rabbitmqctl报错可以从两方面入手,一是cookie值是否相同,二是主机名是否和mnesia的schema是否相同。Error: unable to connect to node rabbit@localhost: nodedown
ERROR: node with name “rabbit” already running on “localhost”
首先检查cookie值是否相同:首先确认一下报错时会显示cookie hash:xxxxx的值是否和~/.erlang.cookie文件中的内容是否一致,如果不一致将报错提示的cookie hash值覆盖掉~/.erlang.cookie的内容,注意.erlang.cookie可能没有修改权限,需要先修改一下文件的权限chmod 777 .erlang.cookie (我就是用这种方式解决的)。
检查主机名是否和mnesia中的schema的名字是否一致,注意查看/usr/local/var/log/rabbitmq/rabbit@<.log 这个日志文件,日志中会打印启动的一些参数,如mnesia的目录位置,我的位置是/usr/local/var/lib/rabbitmq/mnesia/rabbit@MacOSX,如果不一致,将自己机器的主机名改成mnesia中的名字,好像直接删除mnesia中子目录的所有文件也能解决问题, 在rabbitmq-env.conf中发现了一个配置节点名字的配置NODENAME=rabbit@localhost , 在使用rabbitmqctl命令时经常报主机名称不匹配,估计和这有很大的关系。在单机模式下建立集群,建议别使用主机名了,使用localhost代替主机名,估计会减少问题的发生。
rabbitmq启动日志
=INFO REPORT==== 5-Dec-2017::18:13:24 === node : rabbit@MacOSX home dir : /Users/mengday config file(s) : /usr/local/etc/rabbitmq/rabbitmq.config cookie hash : 00v11sjZSBSIWTJU/BkuFg== log : /usr/local/var/log/rabbitmq/rabbit@MacOSX.log sasl log : /usr/local/var/log/rabbitmq/rabbit@MacOSX-sasl.log database dir : /usr/local/var/lib/rabbitmq/mnesia/rabbit@MacOSX
rabbit@localhost: * connected to epmd (port 4369) on localhost * epmd reports node 'rabbit' running on port 25672 * TCP connection succeeded but Erlang distribution failed * Hostname mismatch: node "rabbit@MacOSX" believes its host is different. Please ensure that hostnames resolve the same way locally and on "rabbit@MacOSX"
其他网上找到的答案有人说重启一下就好了,可以试一下,并不好使
// 方式一 rabbitmq-server stop rabbitmq-server start
// 方式二 ps ax | grep rabbit kill -9 PID
{error,”Cookie file /Users/mengday/.erlang.cookie must be accessible by owner only”}
该错是由于.erlang.cookie权限的原因造成的,需要修改权限
chmod 400 .erlang.cookie
相关文章推荐
- RabbitMQ入门教程(十五):普通集群和镜像集群
- 入门级Hadoop集群搭建详细教程(九):MySql的安装
- 全文搜索引擎 Elasticsearch 集群搭建入门教程
- rabbitmq单机多实例集群搭建
- RabbitMQ-Windows单机集群搭建
- 入门级Hadoop集群搭建详细教程(六):yum本地仓库与远程仓库配置
- centos7 搭建docker内运行rabbitmq,然后再镜像ha方案的完全教程,暂时一个宿主机只能运行一个docker的rabbitmq,但是集群 ha都正常
- hadoop2.x单机搭建分布式集群超详细教程
- windows单机搭建RabbitMQ集群
- solr集群的搭建教程和使用入门
- Centos7搭建RabbitMQ集群及单机多节点部署和rabbitmq理论解析
- Hadoop入门基础教程 Hadoop之单机模式搭建
- RabbitMQ入门教程之一--》Windows环境搭建RabbitMQ服务
- RabbitMQ集群环境搭建教程收集(待实践)
- 入门级Hadoop集群搭建详细教程(八):JDK、Tomcat的安装
- RabbitMQ单机集群搭建
- kafka入门:简介、使用场景、设计原理、主要配置及集群搭建(转)[收藏]
- 手把手教程: CentOS 6.5 LVS + KeepAlived 搭建 负载均衡 高可用 集群
- 【Hadoop入门】Hadoop安装教程_单机/伪分布式配置_CentOS6.4/Hadoop2.6.0
- 单机版搭建HBase环境图文教程详解