RabbitMQ运维

news2025/4/8 14:38:06

RabbitMQ运维

  • 一.集群
    • 1.简单介绍
    • 2.集群的作用
  • 二.搭建集群
    • 1.多机多节点
      • 搭建步骤
    • 2.单机单节点
      • 搭建步骤
    • 3.宕机演示
  • 三.仲裁队列
    • 1.简单介绍
    • 2.Raft协议
      • Raft基本概念
      • 主节点选举
        • 选举过程
    • 3.仲裁队列的使用
  • 四.HAProxy负载均衡
    • 1.安装HAProxy
    • 2.HAProxy的使用

一.集群

1.简单介绍

RabbitMQ 集群是 RabbitMQ 实现高可用性(HA)、负载均衡和横向扩展的核心机制。

2.集群的作用

RabbitMQ集群允许消费者和生产者在RabbitMQ单个节点崩溃的情况下继续运,它可以通过添加更多的节点来线性地扩展消息通信的吞吐量。

当失去⼀个RabbitMQ节点时,客户端能够重新连接到集群中的任何其他节点并继续生产或者消费.

二.搭建集群

1.多机多节点

RabbitMQ集群对延迟非常敏感,所以搭建RabbitMQ集群时,多个节点应当在同⼀个局域网内。

因为需要多台机器进行演示,所以学生党(不宽裕)的话就不要去搞这个了,成本有点高,在网上认识一下就好了。

搭建步骤

使用3台局域网的云服务器进行搭建

  1. 3台机器都将RabbitMQ进行安装(安装都是一样的)
  2. 配置每个节点的hosts文件
  3. 配置Erlang Cookie
  4. 构建集群

这里不详细对多机多节点进行介绍,毕竟吃拼好饭的我,怎么留得住多台云服务器。

2.单机单节点

需要注意的是,单机单节点是通过伪集群的方式,如果机器挂了,就全部挂了,生产环境是不会使用这个的。

搭建步骤

  1. RabbitMQ的安装(已安装,不懂的可以去RabbitMQ简单介绍和安装)
  2. 单机启动两个节点
Node nameAMQP协议端口号Web管理界面端口
rabbit2567315673
rabbit3567215674

启动命令:

RABBITMQ_NODE_PORT=5673 RABBITMQ_SERVER_START_ARGS=“-rabbitmq_management
listener [{port,15673}]” RABBITMQ_NODENAME=rabbit2 rabbitmq-server -detached

RABBITMQ_NODE_PORT=5674 RABBITMQ_SERVER_START_ARGS=“-rabbitmq_management
listener [{port,15674}]” RABBITMQ_NODENAME=rabbit3 rabbitmq-server -detached

在这里插入图片描述

  1. 停止服务器并重置

rabbitmqctl -n rabbit2 stop_app
rabbitmqctl -n rabbit2 reset
rabbitmqctl -n rabbit3 stop_app
rabbitmqctl -n rabbit3 reset

在这里插入图片描述

  1. 把节点加入到集群当中

rabbitmqctl -n rabbit2 join_cluster rabbit@node Name
主节点的node Name,可以通过 rabbitmqctl status 查询
在这里插入图片描述
在这里插入图片描述

rabbitmqctl -n rabbit3 join_cluster rabbit@node Name

  1. 重启rabbit2和rabbit3

rabbitmqctl -n rabbit2 start_app
rabbitmqctl -n rabbit3 start_app

在这里插入图片描述

  1. 查看集群的状态

rabbitmqctl cluster_status -n rabbit
在这里插入图片描述

3.宕机演示

节点关闭之前:
在这里插入图片描述
节点关闭之后:

关闭节点的命令:rabbitmqctl -n rabbit stop_app

此时关闭节点的集群已经不在运行了,并且消息也丢失了。

在这里插入图片描述
在这里插入图片描述

三.仲裁队列

1.简单介绍

RabbitMQ 的仲裁队列是⼀种基于 Raft ⼀致性算法实现的持久化、复制的FIFO队列。仲裁队列提供队列复制的能力,保障数据的高可用和安全性。使用仲裁队列可以在RabbitMQ节点间进行队列数据的复制,从而达到在⼀个节点宕机时,队列仍然可以提供服务的效果。

2.Raft协议

Raft 是⼀种用于管理和维护分布式系统⼀致性的协议,它是⼀种共识算法,旨在实现高可用性和数据的持久性。

Raft通过在节点间复制数据来保证分布式系统中的⼀致性,即使在节点故障的情况下也能保证数据不会丢失。

共识算法(Consensus Algorithm)能够保证多个副本之间的⼀致性,它允许多个分布式节点就某个值或⼀系列值达成⼀致性协议。即使在⼀些节点发生故障,网络分区或其他问题的情况下,共识算法也能保证系统的⼀致性和数据的可靠性。

共识算法

  • Paxos: ⼀种经典的共识算法,基于解决分布式系统中的⼀致性问题。
  • Raft:⼀种较新的共识算法,Paxos不易实现,raft是对Paxos算法的简化和改进,旨在易于理解和实现。
  • Zab:ZooKeeper使用的共识算法,基于Paxos算法,大部分和Raft相同,主要区别是对于Leader的任期,Raft叫做term,Zab叫做epoch,状态复制的过程中,raft的心跳从Leader向Follower发送,而ZAB则相反。
  • Gossip:Gossip算法每个节点都是对等的,即没有角色之分。Gossip算法中的每个节点都会将数据改动告诉其他节点(类似传八卦)

Raft基本概念

Raft使⽤Quorum机制来实现共识和容错,我们将对Raft集群的操作必须得到大多数(>N/2)节点的同意才能提交。

Raft集群读写操作内部发生的情况
Raft集群必须存在⼀个主节点(Leader),客户端向集群发起的所有操作都必须经由主节点处理。所以Raft核心算法中的第⼀部分就是选主(Leader election)。没有主节点集群就无法工作,先选出⼀个主节点,再考虑其它事情。

主节点会负责接收客户端发过来的操作请求,将操作包装为日志同步给其它节点,在保证⼤部分节点都同步了本次操作后,就可以安全地给客户端回应响应了。这⼀部分工作在Raft核心算法中叫日志复制(Log replication).

因为主节点的责任非常大,所以只有符合条件的节点才可以当选主节点。为了保证集群对外展现的⼀致性,主节点在处理操作日志时,也⼀定要谨慎,这部分在Raft核心算法中叫
安全性(Safety).

Raft算法将⼀致性问题分解为三个子问题: Leader选举日志复制安全性.

主节点选举

在Raft算法中,每个节点都处于以下三种角色之⼀

  • Leader(领导者):负责处理所有客户请求,并将这些请求作为日志项复制到所有Follower。Leader定期向所有Follower发送心跳消息,以维持其领导者地位,防止Follower进入选举过程。
  • Follower(跟随者) :接收来自Leader的日志条目,并在本地应用这些条目。跟随者不直接处理客户请求。
  • Candidate(候选者) 当跟随者在⼀段时间内没有收到来自Leader的心跳消息时,它会变得不确定Leader是否仍然可用。在这种情况下,跟随者会转变角色成为Candidate,并开始尝试通过投票过程成为新的Leader。

在正常情况下,集群中只有⼀个Leader,剩下的节点都是follower,下图展示了这些状态和它们之间的转换关系:
在这里插入图片描述

可以看出所有节点在启动时,都是follow状态,在⼀段时间内如果没有收到来自leader的心跳,从follower切换到candidate,发起选举。如果收到多数派(majority)的投票(含自己的⼀票)则切换到leader状态。Leader⼀般会⼀直工作直到它发生异常为止。

任期
Raft将时间划分成任意长度的任期(term)。每⼀段任期从⼀次选举开始,在这个时候会有⼀个或者多个candidate尝试去成为leader。在成功完成⼀次leaderelection之后,⼀个leader就会⼀直节管理集群直到任期结束。

在某些情况下,⼀次选举无法选出leader,这个时候这个任期会以没有leader而结束。同时⼀个新的任期(包含⼀次新的选举)会很快重新开始。
在这里插入图片描述
Term更像是⼀个逻辑时钟(logic clock)的作用,有了它,就可以发现哪些节点的状态已经过期。每⼀个节点都保存⼀个current term,在通信时带上这个term的值。

每⼀个节点都存储着⼀个当前任期号(current term number)。该任期号会随着时间单调递增。

节点之间通信的时候会交换当前任期号,如果⼀个节点的当前任期号比其他节点小,那么它就将自己的任期号更新为较大的那个值,如果⼀个candidate或者leader发现自己的任期号过期了,它就会立刻回到follower状态。

如果⼀个节点接收了⼀个带着过期的任期号的请求,那么它会拒绝这次请求。Raft算法中服务器节点之间采⽤RPC进行通信,主要有两类RPC请求:

  • RequestVoteRPCs:请求投票,由candidate在选举过程中发出。
  • AppendEntriesRPCs:追加条目,由leader发出用来做日志复制和提供心跳机制
选举过程

Raft采用⼀种心跳机制来触发leader选举,当服务器启动的时候,都是follow状态。如果follower在electiontimeout内没有收到来自leader的心跳(可能没有选出leader,也可能leader挂了,或者leader与follower之间网络故障),则会主动发起选举。

所有节点处于follower状态:

  1. 率先超时的节点,自增当前任期号然后切换为candidate态,并投自己⼀票。
  2. 以并行的放式发送一个RequestVote RPCs 给集群中的其他服务器节点(企图得到它们的投票)
  3. 等待其他节点的回复

在这里插入图片描述

S3节点率先超时,把任期号改成2,切换为candidate状态,发起投票请求,并给自己投一票

在这里插入图片描述

  1. 赢得选举成为Leader(包括自己的⼀票)
  2. 其他节点赢得了选举,它自行切换到follower
  3. ⼀段时间内没有收到majority投票,保持candidate状态,重新发出选举

投票要求:
• 每⼀个服务器节点会按照先来先服务原则(first-come-first-served)只投给⼀个 candidate.
• 候选人知道的信息不能比自己的少

第1种情况: 赢得了选举之后,新的leader会立刻给所有节点发消息,广而告之,避免其余节点触发新的选举。

S3节点应赢得多数投票,广而告之:
在这里插入图片描述

第2种情况: 比如有三个节点A B C, A B同时发起选举,而A的选举消息先到达C,C给A投了⼀票,当B的消息到达C时,已经不能满足上面提到的第⼀个约束,即C不会给B投票,这时候A就胜出了。

A胜出之后,会给B,C发⼼跳消息,节点B发现节点A的term不低于自己的term,知道有已经有Leader了,于是把自己转换成follower.

S1收到S3的心跳信息,发现S3的term不低于自己,就知道已经有leader了,将自己切换成follower:
在这里插入图片描述

第3种情况: 没有任何节点获得majority投票。比如所有的follower同时变成candidate,然后它们都将票投给自己,那这样就没有candidate能得到超过半数的投票了。

当这种情况发生的时候,每个candidate都会进行一次超时响应,然后通过自增任期号来开启⼀轮新的选举,并启动另⼀轮的RequestVoteRPCs。如果没有额外的措施,这种无结果的投票可能会无限重复下去。

S1-S5都在参与选举,每个节点都投给自己,如果超时,会重复发起新一轮的选举
在这里插入图片描述

为了解决上述问题,Raft采用随机选举超时时间(randomized election timeouts)来确保很少产⽣无结果的投票,并且就算发⽣了也能很快地解决。

为了防止选票⼀开始就被瓜分,选举超时时间是从⼀个固定的区间(比如,150-300ms)中随机选择。

这样可以把服务器分散开来以确保在⼤多数情况下会只有⼀个服务器率先结束超时,那么这个时候,它就可以赢得选举并在其他服务器结束超时之前发送⼼跳。

Raft动画演示在线地址

日志复制
每个仲裁队列都有多个副本,它包含⼀个主和多个从副本。replication factor 为 5的仲裁队列将会有1个
主副本和4个从副本。

每个副本都在不同的RabbitMQ节点上客户端(生产者和消费者)只会与主副本进行交互,主副本再将这些命令复制到从副本。当主副本所在的节点下线,其中一个从副本会被选举成为主副本,继续提供服务。
在这里插入图片描述

消息复制和主副本选举的操作,需要超过半数的副本同意。当生产者发送⼀条消息,需要超过半数的队列副本都将消息写入磁盘以后才会向生产者进行确认,这意味着少部分比较慢的副本不会影响整个队列的性能。

3.仲裁队列的使用

  1. 使用Spring框架创建仲裁队列
    Producer
@RequestMapping("/quorum")
    public String quorum() {
        rabbitTemplate.convertAndSend("","quorum.queue","quorum test....");
        return "quorum is ok!";
    }

Configuration

@Configuration
public class OpsConfiguration {
    @Bean("quorumQueue")
    public Queue quorumQueue() {
        return QueueBuilder.durable("quorum.queye").quorum().build();
    }
}

在这里插入图片描述
在这里插入图片描述

  1. 在管理页面创建仲裁队列
    Node是leader
    在这里插入图片描述
    在这里插入图片描述
    在这里插入图片描述

此时停止其中一个主节点,此时消息还是存在,不会直接消失,并且会重新选举leader:

先给queue2中创建一个消息:
在这里插入图片描述
在这里插入图片描述
在这里插入图片描述
重新启动原来的leader后,就会有2个follower了:
在这里插入图片描述

仲裁队列,是RabbitMQ从3.8.0版本引⼊的新的队列类型,Quorum相比Classic在分布式环境下对消息的可靠性保障更高。

普通队列只会存放在集群中的⼀个节点上,虽然通过其它节点也可以访问普通队列,但是其它节点只是把请求转发到队列所在的节点进行操作。⼀旦队列所在节点宕机,队列中的消息就会丢失,因此普通集群只是提高了并发能⼒力,并未实现高可用。

仲裁队列可以极大的保障RabbitM集群对接的高可用。

四.HAProxy负载均衡

这时候就存在两个问题:

  1. 如果我们访问的是node1,但是node1挂了,咱们的程序也会出现问题,所以最好是有⼀个统⼀的入口,⼀个节点故障时,流量可以及时转移到其他节点。
  2. 如果所有的客户端都与node1建议连接,那么node1的网络负载必然会大大增加,而其他节点又由于没有那么多的负载而造成硬件资源的浪费,这时候负载均衡显得尤其重要。
    在这里插入图片描述
    这里主要讨论的是如何有效地对RabbitMQ集群使⽤软件负载均衡技术,目前主流的方式有在客户端内
    部实现负载均衡,或者使用HAProxy、LVS等负载均衡有软件来实现。这里讲⼀下使用HAProxy来实现负载均衡。

1.安装HAProxy

HAProxy(High Availability Proxy)是⼀个开源的负载均衡器和TCP/HTTP应用程序的代理服务器,它被设计用来提供高可用性,负载均衡和代理功能。HAProxy主要用于分发网络流量到多个后端服务器,以提高网络的可靠性和性能。

  1. 更新数据包sudo apt-get update在这里插入图片描述

  2. 查找HAProxy:sudo apt list|grep haproxy
    在这里插入图片描述

  3. 安装HAProxy:sudo apt-get install haproxy
    在这里插入图片描述

  4. 验证状态:
    在这里插入图片描述

  5. 查看版本:haproxy -v
    在这里插入图片描述

  6. 需要Proxy服务器自启动则使用:sudo systemctl enable haproxy在这里插入图片描述

  7. 通过vi /etc/haproxy/haproxy.cfg修改haproxy.cfg文件:

#haproxy web 管理界⾯
listen stats #设置⼀个监听器, 统计HAProxy的统计信息
bind *:8100 #指定了监听器绑定到的IP地址和端⼝
mode http #监听器的⼯作模式为HTTP
stats enable #启⽤统计⻚⾯
stats realm Haproxy\ Statistics
stats uri /
stats auth admin:admin #haproxy登录账号和密码
#配置负载均衡
listen rabbitmq #设置监听器
bind *:5670 #监听器绑定到的IP地址和端⼝, 也就是集群前端IP, 供producer和consumer
来进⾏选择,由于5672端⼝已经默认使⽤, 这⾥选择5670端⼝
mode tcp #由于RabbitMQ使⽤AMQP协议,它是⼀个基于TCP的协议,所以这⾥使⽤TCP模
balance roundrobin #指定负载均衡策略为轮询
#负载均衡中的集群节点配置,这⾥选择的rabbit节点
server rabbitmq1 127.0.0.1:5672 check inter 5000 rise 2 fall 3
server rabbitmq2 127.0.0.1:5673 check inter 5000 rise 2 fall 3
server rabbitmq3 127.0.0.1:5674 check inter 5000 rise 2 fall 3

  1. 配置完后,重启HAProxy:sudo systemctl restart haproxy

页面:
在这里插入图片描述

2.HAProxy的使用

yml文件的配置

在这里插入图片描述

Configuration

@Bean("clusterQueue")
    public Queue clusterQueue() {
        return QueueBuilder.durable("cluster.queye").quorum().build();
    }

Producer

 @RequestMapping("/cluster")
    public String cluster() {
        rabbitTemplate.convertAndSend("","cluster.queue","cluster test....");
        return "cluster is ok!";
    }

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/2329913.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

Ansible 实战:Roles,运维的 “魔法函数”

一、介绍 你现在已经学过tasks和handlers,那么,最好的playbook组织方式是什么呢?答案很简单:使用roles!roles基于一种已知的文件结构,能够自动加载特定的vars_files、tasks以及handlers。通过roles对内容进…

关于JVM和OS中的指令重排以及JIT优化

关于JVM和OS中的指令重排以及JIT优化 前言: 这东西应该很重要才对,可是大多数博客都是以讹传讹,全是错误,尤其是JVM会对字节码进行重排都出来了,明明自己测一测就出来的东西,写出来误人子弟… 研究了两天&…

在CPU服务器上部署Ollama和Dify的过程记录

在本指南中,我将详细介绍如何在CPU服务器上安装和配置Ollama模型服务和Dify平台,以及如何利用Docker实现这些服务的高效部署和迁移。本文分为三大部分:Ollama部署、Dify环境配置和Docker环境管理,适合需要在本地或私有环境中运行A…

【计网】TCP 协议详解 与 常见面试题

三次握手、四次挥手的常见面试题 不用死记,只需要清楚三次握手,四次挥手的流程,回答的时候心里要记住,假设网络是不可靠的 问题(1):为什么关闭连接时需要四次挥手,而建立连接却只要三次握手? 关…

7.4 SVD 的几何背景

一、SVD 的几何解释 SVD 将矩阵分解成三个矩阵的乘积: ( 正交矩阵 ) ( 对角矩阵 ) ( 正交矩阵 ) (\pmb{正交矩阵})\times(\pmb{对角矩阵})(\pmb{正交矩阵}) (正交矩阵)(对角矩阵)(正交矩阵),用几何语言表述其几何背景: ( 旋转 ) ( 伸缩 )…

C++的多态-上

目录 多态的概念 多态的定义及实现 1.虚函数 2. 多态的实现 2.1.多态构成条件 2.2.虚函数重写的两个例外 (1)协变(基类与派生类虚函数返回值类型不同) (2)析构函数的重写(基类与派生类析构函数的名字不同) 2.3.多态的实现 2.4.多态在析构函数中的应用 2.5.多态构成条…

内存与显存:从同根生到殊途异路的科技演进

在现代计算机的世界里,内存和显存是两个不可或缺的硬件组件。它们看似功能相近,却在发展历程中逐渐分道扬镳,各自服务于不同的计算需求。今天,我们将从一根内存条和一块显卡入手,深入探讨内存与显存的异同,…

手搓多模态-04 归一化介绍

在机器学习中,归一化是一个非常重要的工具,它能帮助我们加速训练的速度。在我们前面的SiglipVisionTransformer 中,也有用到归一化层,如下代码所示: class SiglipVisionTransformer(nn.Module): ##视觉模型的第二层&am…

【C++】第八节—string类(上)——详解+代码示例

hello,又见面了! 云边有个稻草人-CSDN博客 C_云边有个稻草人的博客-CSDN博客——C专栏(质量分高达97!) 菜鸟进化中。。。 目录 一、为什么要学习string类? 1.1 C语言中的字符串 1.2 面试题(暂不做讲解) …

Java 数组与 ArrayList 核心区别解析:从源码到实战!!!

🌟 Java 数组与 ArrayList 核心区别解析:从源码到实战 💡 Java 开发者必读! 数组(Array)和 ArrayList 是 Java 中最常用的数据存储结构,但它们的底层设计、性能表现和适用场景差异显著。本文通…

【易飞】易飞批量选择品号处理方法,工作效率提升300%

开窗选择品号方式要么手动输入,要么以什么开头、包含、从A物料到B物料查询后返回的有规律的品号。对于没有规律且大量品号的处理方式是否有便捷的方法呢? 尤其在通常在查询多阶材料清单,查询库存明细表,整批变更元件等如品号无规律情况下,只能一个个选择,无法通过EXCEL方…

【最新版】啦啦外卖v64系统独立版源码+全部小程序APP端+安装教程

一.系统介绍 啦啦外卖跑腿平台独立版,使用的都知道该系统功能非常强大,应该说是目前外卖平台功能最全的一套系统。主要是功能非常多,拿来即用,包括客户端小程序、配送端小程序、商户端小程序,还有对应四个端的APP源码…

iproute2 工具集使用详解

目录 一、iproute2 核心命令:ip二、常用功能详解1. 管理网络接口(link 对象)2. 管理 IP 地址(address 对象)3. 管理路由表(route 对象)4. 管理 ARP 和邻居缓存(neigh 对象&#xff0…

AD(Altium Designer)更换PCB文件的器件封装

一、确定是否拥有想换的器件PCB封装 1.1 打开现有的原理图 1.2 确定是否拥有想换的器件PCB文件 1.2.1 如果有 按照1.3进行切换器件PCB封装 1.2.2 如果没有 按照如下链接进行添加 AD(Altium Designer)已有封装库的基础上添加器件封装-CSDN博客https://blog.csdn.net/XU15…

【文献研究】含硼钢中BN表面偏析对可镀性的影响

《B 添加钢的溶融 Zn めっき性に及ぼす BN 表面析出の影響》由JFE公司田原大輔等人撰写。研究聚焦 B 添加钢在低露点退火时 BN 形成对镀锌性的影响,对汽车用高强度钢镀锌工艺优化意义重大。通过多组对比实验,结合多种分析手段,明确了相关因素…

React学习-css

W3Schools Tryit Editor CSS 教程 CSS 规则由两个主要的部分构成:选择器,以及一条或多条声明: p { /* 这是个注释 */ color:red; text-align:center; }选择器 CSS Id: #para1{ text-align:center; color:red; } Class: .center {text-align:center;} p…

数据分析-Excel-学习笔记Day1

Day1 复现报表聚合函数:日期联动快速定位区域SUMIF函数SUMIFS函数环比、同比计算IFERROR函数混合引用单元格格式总结汇报 拿到一个Excel表格,首先要看这个表格的构成(包含了哪些数据),几行几列,每一列的名称…

树莓派PICO 设备烧录成cmsis dap

文章目录 1. 实际操作2. IO连接 1. 实际操作 2. IO连接

【数据结构】图的存储

目录 邻接矩阵 表示方法 代码定义 结构特点与度的信息 邻接表 表示方法 代码定义 结构特点与度的信息 十字链表 表示方法 第二步,将顶点x的firstIn域与所有headvex域为x的弧连起来。 结构特点与度的信息 邻接多重表 表示方法 结构特点与度的信息 图…

如何解决uniapp打包安卓只出现功能栏而无数据的问题

如何解决uniapp打包安卓只出现功能栏而无数据的问题 经验来自:关于Vue3中调试APP触发异常:exception:white screen cause create instanceContext failed,check js stack -> at useStore (app-service.js:2309:15)解决方案 - 甲辰哥来帮你算命 - 博客…