29-keepalived高可用性负载均衡

以下将为你详细介绍高可用性负载均衡的原理,并使用 Mermaid 绘制对应的流程图和架构图来直观呈现。

高可用性负载均衡原理概述

高可用性负载均衡是为了确保系统在面对各种故障和高流量时仍能稳定运行。其核心原理是通过多个负载均衡器和多个后端服务器组成集群,负载均衡器负责将客户端的请求均匀地分配到后端服务器上,同时具备故障检测和自动切换功能,当某个负载均衡器或后端服务器出现故障时,系统能够自动调整请求的分配,保证服务的连续性。

架构图 Mermaid 代码

graph LR
    classDef startend fill:#F5EBFF,stroke:#BE8FED,stroke-width:2px;
    classDef process fill:#E5F6FF,stroke:#73A6FF,stroke-width:2px;
    classDef decision fill:#FFF6CC,stroke:#FFBC52,stroke-width:2px;

    A(客户端):::process --> B(负载均衡器集群):::process
    B --> C{负载均衡算法}:::decision
    C -->|轮询| D(后端服务器 1):::process
    C -->|加权轮询| E(后端服务器 2):::process
    C -->|IP 哈希| F(后端服务器 3):::process
    C -->|最少连接| G(后端服务器 4):::process
    D --> H(数据存储):::process
    E --> H
    F --> H
    G --> H
    I(监控系统):::process --> B
    I --> D
    I --> E
    I --> F
    I --> G
    J(故障转移机制):::process --> B
    J --> D
    J --> E
    J --> F
    J --> G

架构图代码解释

  1. 客户端:发起请求的终端用户。
  2. 负载均衡器集群:由多个负载均衡器组成,用于接收客户端的请求并进行分配。
  3. 负载均衡算法:包括轮询、加权轮询、IP 哈希、最少连接等,根据不同的策略将请求分配到后端服务器。
  4. 后端服务器:处理客户端请求的服务器,多个后端服务器组成集群以提高系统的处理能力和容错性。
  5. 数据存储:存储系统处理的数据,供后端服务器访问。
  6. 监控系统:实时监控负载均衡器和后端服务器的状态,如 CPU 使用率、响应时间等。
  7. 故障转移机制:当监控到某个负载均衡器或后端服务器出现故障时,自动将请求转移到其他正常的设备上。

工作流程图 Mermaid 代码

graph LR
    classDef startend fill:#F5EBFF,stroke:#BE8FED,stroke-width:2px;
    classDef process fill:#E5F6FF,stroke:#73A6FF,stroke-width:2px;
    classDef decision fill:#FFF6CC,stroke:#FFBC52,stroke-width:2px;

    A([开始]):::startend --> B(客户端发起请求):::process
    B --> C(负载均衡器接收请求):::process
    C --> D{负载均衡器是否正常}:::decision
    D -->|是| E{选择负载均衡算法}:::decision
    D -->|否| F(故障转移到备用负载均衡器):::process
    F --> E
    E -->|轮询| G(选择下一个后端服务器):::process
    E -->|加权轮询| H(根据权重选择后端服务器):::process
    E -->|IP 哈希| I(根据 IP 地址选择后端服务器):::process
    E -->|最少连接| J(选择连接数最少的后端服务器):::process
    G --> K{后端服务器是否正常}:::decision
    H --> K
    I --> K
    J --> K
    K -->|是| L(后端服务器处理请求):::process
    K -->|否| M(故障转移到其他后端服务器):::process
    M --> L
    L --> N(后端服务器返回响应):::process
    N --> O(负载均衡器转发响应给客户端):::process
    O --> P([结束]):::startend

工作流程图代码解释

  1. 开始:流程的起始点。
  2. 客户端发起请求:客户端向负载均衡器发送请求。
  3. 负载均衡器接收请求:负载均衡器接收到客户端的请求。
  4. 负载均衡器是否正常:检查负载均衡器是否处于正常工作状态。
  5. 故障转移到备用负载均衡器:如果当前负载均衡器出现故障,将请求转移到备用负载均衡器。
  6. 选择负载均衡算法:根据预设的算法选择合适的后端服务器。
  7. 后端服务器是否正常:检查所选的后端服务器是否正常工作。
  8. 故障转移到其他后端服务器:如果所选后端服务器出现故障,将请求转移到其他正常的后端服务器。
  9. 后端服务器处理请求:后端服务器对请求进行处理。
  10. 后端服务器返回响应:处理完成后,后端服务器将响应返回给负载均衡器。
  11. 负载均衡器转发响应给客户端:负载均衡器将响应转发给客户端。
  12. 结束:流程结束。

通过这两个 Mermaid 图,你可以清晰地了解高可用性负载均衡的架构和工作流程。

软件官网
http://www.keepalived.org/

利用KeepAlived 实现3CX 高可用- 58VOIP企业通信博客

咱们现在已经进入到期中综合架构的最后一个环节了。

image-20220517183606616

为什么需要keepalived

下面使用 Mermaid 语法绘制一个 Keepalived 高可用 Web 集群架构图,并对其进行详细解释,帮助你理解 Keepalived 在高可用 Web 集群中的工作方式。

graph TD;
    subgraph 用户访问层
        A[客户端] -->|HTTP请求| B[虚拟IP(VIP)];
    end
    subgraph Keepalived层
        B --> C[Keepalived主节点(Master)];
        B --> D[Keepalived备节点(Backup)];
        C -->|心跳检测| D;
        D -->|心跳检测| C;
    end
    subgraph Web服务器层
        C --> E[Web服务器1];
        D --> E;
        C --> F[Web服务器2];
        D --> F;
    end
    subgraph 数据存储层
        E --> G[数据库服务器];
        F --> G;
    end
    subgraph 健康检查层
        H[健康检查脚本] --> E;
        H --> F;
        C -->|健康检查结果| H;
        D -->|健康检查结果| H;
    end

架构图详细解释

  1. 用户访问层

    • 客户端:发起 HTTP 请求的设备或应用程序,如浏览器。它通过访问虚拟 IP 地址(VIP)来请求 Web 服务。
    • 虚拟 IP(VIP):是一个逻辑上的 IP 地址,由 Keepalived 管理的主节点和备节点共享。客户端将请求发送到这个 VIP,而不需要关心具体是哪台物理服务器在处理请求。
  2. Keepalived 层

    • Keepalived 主节点(Master):正常情况下,主节点拥有 VIP 的控制权,接收来自客户端的请求,并将请求转发到后端的 Web 服务器。它还会定期向备节点发送心跳检测信号,以表明自己处于正常工作状态。
    • Keepalived 备节点(Backup):处于备用状态,监听主节点发送的心跳检测信号。如果在一定时间内没有收到主节点的心跳信号,备节点会认为主节点出现故障,从而接管 VIP,成为新的主节点。
  3. Web 服务器层

    • Web 服务器 1Web 服务器 2:运行 Web 应用程序,处理客户端的请求并生成相应的响应。这两台服务器都可以接收来自 Keepalived 节点的请求,并进行处理。
  4. 数据存储层

    • 数据库服务器:存储 Web 应用程序所需的数据,如用户信息、业务数据等。Web 服务器在处理请求时,会与数据库服务器进行交互,读取或写入数据。
  5. 健康检查层

    • 健康检查脚本:定期对 Web 服务器进行健康检查,例如检查 Web 服务器的进程是否正常运行、端口是否开放等。健康检查脚本会将检查结果反馈给 Keepalived 的主节点和备节点。如果发现某台 Web 服务器出现故障,Keepalived 可以根据情况调整请求的分发策略,避免将请求发送到故障服务器上。

通过以上架构,Keepalived 实现了 Web 集群的高可用性,确保在某台服务器或某个组件出现故障时,系统仍然能够继续为客户端提供服务。

上图明显看出,LB机器应该是双节点,否则出现单点故障的问题,并且LB作为网站的入口,显然要提供高可用性的访问。

keepalived就是解决了单点故障的问题,给两台不同IP的服务器提供了自动漂移虚拟IP的功能。

lb-5机器如果宕机,这个虚拟IP自动切换到lb-6机器上,这个过程对用户是透明的,不会感知到网站有任意问题。

keepalived工作原理

实现高可用的基本原理是
1. 两台LB机器均部署好keepalived工具,并且启动服务;
2. 角色是master的机器获得IP资源且为用户提供访问(nginx)
3. 角色是backup的机器作为master的热备机器(master挂了,立即接替)


故障时
1. 当master出现故障时
2. backup机器自动接管master的所有工作,接管VIP以及其他资源。

修复后
1. master修复后,自动接管它本身的资源,如VIP。
2. backup自动释放接管的资源。

此时两台机器恢复启动时的角色,以及工作状态。

VRRP协议

VRRP(Virtual Router Redundancy Protocol)即虚拟路由冗余协议,是一种用于提高网络可靠性和可用性的协议,以下是关于它的详细介绍:

定义与作用

VRRP通过在一组路由器之间创建一个虚拟路由器,来实现路由器的冗余备份功能。它允许多台路由器协同工作,对外表现为一个虚拟的路由器,从而确保在某台路由器出现故障时,网络通信能够自动切换到其他正常的路由器上,保证网络的连续性和稳定性,避免单点故障。

工作原理

  • 虚拟路由器与虚拟IP地址
    • 在VRRP中,一组路由器(至少两台)组成一个虚拟路由器组,这个组有一个虚拟IP地址和一个虚拟MAC地址。虚拟IP地址是用户设备配置的默认网关地址,用户设备发送到该虚拟IP地址的数据包,会被虚拟路由器组中的路由器处理。
  • Master与Backup路由器
    • 虚拟路由器组中的路由器分为Master(主)路由器和Backup(备份)路由器。Master路由器负责处理发往虚拟IP地址的数据包,并向Backup路由器发送VRRP通告消息,以表明自己的存活状态和工作状态。Backup路由器则监听Master路由器发送的通告消息,并根据收到的消息来判断Master路由器是否正常工作。
  • 选举机制
    • 路由器在启动时会根据自身的优先级等参数进行选举,优先级最高的路由器将成为Master路由器,其他路由器则成为Backup路由器。如果有多台路由器的优先级相同,则IP地址较大的路由器会成为Master。
  • VRRP通告消息
    • Master路由器会按照一定的时间间隔发送VRRP通告消息,Backup路由器在接收到通告消息后,会更新自己的状态信息,并根据Master路由器的状态来决定是否需要进行角色切换。如果Backup路由器在一定时间内没有收到Master路由器的通告消息,就会认为Master路由器出现故障,然后根据自身的优先级等因素决定是否要成为新的Master路由器。

优点

  • 提高网络可靠性:通过路由器冗余备份,当Master路由器出现故障时,Backup路由器能够快速接管工作,确保网络通信不中断,大大提高了网络的可靠性和可用性。
  • 透明性:对于用户设备来说,无需进行任何配置更改,就可以自动享受VRRP提供的冗余备份功能。用户设备只需要将默认网关设置为虚拟IP地址,无需关心实际的路由器状态和切换过程。
  • 易于部署:VRRP协议相对简单,易于在各种网络设备上进行部署和配置,不需要对网络架构进行大规模的调整。

应用场景

  • 企业网络:在企业网络中,核心路由器通常采用VRRP技术来实现冗余备份,确保企业内部网络与外部网络之间的通信稳定可靠,避免因路由器故障导致企业业务中断。
  • 数据中心:数据中心需要保证网络的高可用性,以支持大量的服务器和应用程序的运行。VRRP可以用于数据中心的网络出口路由器,确保数据中心与外部网络的连接始终保持畅通。
  • 校园网络:校园网络中也需要保证网络的稳定性和可靠性,以满足师生的教学和科研需求。VRRP可以用于校园网络的核心层和汇聚层路由器,提供冗余备份功能。

image-20220517193450919

VRRP工作原理

以下使用Mermaid绘制的系列图表来对VRRP协议进行图解:

基础架构图

graph TD;
    subgraph 用户设备
        A[PC] -->|发送数据包到网关| B[虚拟IP(VIP)];
    end
    subgraph VRRP路由器组
        B --> C[Master路由器];
        B --> D[Backup路由器];
        C -->|VRRP通告消息| D;
    end
    subgraph 目标网络
        C --> E[服务器或其他网络设备];
        D --> E;
    end

在这个架构中,用户设备(如PC)将数据包发送到配置的虚拟IP(VIP),也就是虚拟路由器的地址。VRRP路由器组中的Master路由器负责转发这些数据包到目标网络中的服务器或其他网络设备,同时Master路由器会向Backup路由器发送VRRP通告消息,告知自己的状态。

选举过程图

graph TD;
    A[路由器1] -->|启动并宣告优先级| B{谁优先级高?};
    C[路由器2] -->|启动并宣告优先级| B;
    B -->|路由器1优先级高| D[路由器1成为Master];
    B -->|路由器2优先级高| E[路由器2成为Master];
    D -->|发送VRRP通告| C;
    E -->|发送VRRP通告| A;

在选举过程中,路由器启动后会宣告自己的优先级,优先级高的路由器将成为Master,而优先级低的则成为Backup。Master路由器会向其他路由器发送VRRP通告,告知自己的角色。

故障切换图

graph TD;
    subgraph 正常状态
        A[Master路由器] -->|发送VRRP通告| B[Backup路由器];
    end
    subgraph Master故障
        C[Master路由器故障] -->|无VRRP通告| D[Backup路由器];
    end
    subgraph 切换后状态
        D -->|成为新的Master| E[接管虚拟IP并转发数据包];
    end

当Master路由器出现故障时,它将无法发送VRRP通告消息。Backup路由器在一段时间内没有收到通告后,会认为Master故障,于是自己成为新的Master,接管虚拟IP地址,并开始转发数据包,实现了故障切换,保证网络的连续性。

抢占模式与非抢占模式说明图

graph TD;
    subgraph 抢占模式
        A[原Master恢复] -->|有更高优先级| B[再次成为Master];
    end
    subgraph 非抢占模式
        C[原Master恢复] -->|保持Backup角色| D[新Master继续工作];
    end

在抢占模式下,如果原来的Master路由器恢复正常,且它的优先级仍然高于当前的Master(即原Backup路由器),那么它会再次抢占Master角色。而在非抢占模式下,即使原Master路由器恢复,它也会保持Backup角色,新的Master路由器继续工作。

VRRP协议中定义了三种状态机:初始状态(Initialize)、活动状态(Master)、备份状态(Backup)。

其中,只有处于Master状态的设备才可以转发那些发送到虚拟IP地址的报文。

下表详细描述了三种状态。

状态 说明
Initialize 该状态为VRRP不可用状态,在此状态时设备不会对VRRP通告报文做任何处理。通常设备启动时或设备检测到故障时会进入Initialize状态。
Master 当VRRP设备处于Master状态时,它将会承担虚拟路由设备的所有转发工作,并定期向整个虚拟内发送VRRP通告报文。
Backup 当VRRP设备处于Backup状态时,它不会承担虚拟路由设备的转发工作,并定期接受Master设备的VRRP通告报文,判断Master的工作状态是否正常。

部署nginx+keepalived

好的,用户现在问的是“nginx结合keepalived集群部署方案”。这个问题看起来是关于如何将Nginx与Keepalived结合使用,实现高可用性的集群部署。用户可能是在寻找一种确保他们的Web服务不会因为单点故障而中断的方法。我需要先理解Keepalived和Nginx在这个方案中的角色。

首先,Keepalived是一个用于实现高可用性的软件,它通过VRRP(虚拟路由冗余协议)协议来管理虚拟IP地址(VIP)。当主节点发生故障时,备用节点会自动接管VIP,从而保证服务的连续性。而Nginx作为反向代理或负载均衡器,处理客户端的请求并将流量分发到后端服务器。

用户的需求可能是在生产环境中部署Nginx,但希望避免单点故障,所以需要构建一个高可用的集群。他们可能已经知道Nginx的基本配置,但对Keepalived的使用不太熟悉,需要具体的步骤和配置示例。

接下来,我需要考虑用户可能的具体需求。他们可能希望了解如何安装和配置Keepalived,如何设置虚拟IP,以及如何监控Nginx服务的状态,以便在服务不可用时触发故障转移。此外,用户可能关心如何测试这个配置是否有效,确保当主节点宕机时,备用节点能顺利接管。

另外,用户可能对网络配置有一定了解,但需要明确的指导,比如如何设置防火墙规则,如何处理ARP广播,以及如何配置双节点的Keepalived。同时,他们可能想知道如何自动检测Nginx是否运行正常,而不仅仅是服务器是否在线。例如,如果Nginx进程崩溃但服务器还在运行,Keepalived应该能够检测到并将VIP转移到备用节点。

可能还需要考虑不同的网络环境,比如是在物理服务器、虚拟机还是云环境中部署。不同的环境可能在网络配置上有差异,比如云平台可能需要特定的设置来处理VRRP协议,或者需要允许特定的网络流量。

然后,我需要整理出一个步骤清晰的方案,包括安装Keepalived,配置主备节点的keepalived.conf文件,设置监控脚本,以及测试故障转移的过程。同时,要提醒用户注意的一些常见问题,比如防火墙设置、SELinux的影响、以及确保虚拟IP不会被其他设备占用。

可能还需要给出具体的配置示例,比如主节点和备用节点的配置文件内容,以及如何设置优先级和状态检查脚本。此外,解释VRRP协议的工作原理,帮助用户理解故障转移的机制。

最后,用户可能需要验证配置是否正确,如何查看日志来排查问题,以及如何模拟故障来测试集群的可靠性。这部分也需要详细说明,确保用户能够顺利实施并验证他们的高可用方案。

以下是结合Nginx与Keepalived实现高可用集群的部署方案,通过虚拟IP(VIP)实现故障自动切换,确保服务高可用性:


1. 架构设计

                     +---------------------+
                     |     虚拟IP (VIP)     |
                     |  192.168.1.100/24   |
                     +----------+----------+
                                |
                  +-------------+-------------+
                  |                           |
           +------+------+             +------+------+
           |  Nginx主节点 |             | Nginx备节点 |
           | 192.168.1.1 |             |192.168.1.2 |
           +-------------+             +------------+
                  |                           |
           +------+------+             +------+------+
           | 后端服务器组 |             | 后端服务器组 |
           | (Web/App)  |             | (Web/App)  |
           +------------+             +------------+

2. 环境准备

2.1 节点信息

节点角色 IP地址 主机名
主节点 192.168.1.1 nginx-master
备节点 192.168.1.2 nginx-backup
虚拟IP(VIP) 192.168.1.100 -

2.2 前置条件

  • 所有节点安装Nginx并配置相同负载均衡规则(指向统一后端服务器)。
  • 确保主备节点间网络互通(允许VRRP协议通信,协议号112)。

3. Keepalived安装与配置

3.1 安装Keepalived

# CentOS/RHEL
sudo yum install keepalived -y

# Ubuntu/Debian
sudo apt-get install keepalived -y

3.2 主节点配置 (/etc/keepalived/keepalived.conf)

global_defs {
    router_id nginx_master  # 唯一标识,备节点改为nginx_backup
}

vrrp_script chk_nginx {
    script "/usr/bin/killall -0 nginx"  # 检测Nginx进程是否存在
    interval 2   # 检测间隔(秒)
    weight -20   # 检测失败时降低优先级
}

vrrp_instance VI_1 {
    state MASTER          # 主节点为MASTER,备节点为BACKUP
    interface eth0        # 绑定网卡名称(根据实际修改)
    virtual_router_id 51  # 集群ID,主备必须相同(范围1-255)
    priority 100          # 主节点优先级高于备节点(如备节点设为90)
    advert_int 1          # VRRP通告间隔(秒)

    authentication {
        auth_type PASS
        auth_pass 123456   # 主备节点密码需一致
    }

    virtual_ipaddress {
        192.168.1.100/24  # 虚拟IP地址
    }

    track_script {
        chk_nginx         # 关联健康检查脚本
    }
}

3.3 备节点配置

  • 复制主节点配置文件,修改以下参数:

    global_defs {
        router_id nginx_backup
    }
    
    vrrp_instance VI_1 {
        state BACKUP
        priority 90
    }
    

4. 服务启动与验证

4.1 启动Keepalived

sudo systemctl enable keepalived
sudo systemctl start keepalived

4.2 检查VIP绑定

# 在主节点执行
ip addr show eth0 | grep 192.168.1.100
# 应输出:inet 192.168.1.100/24 scope global secondary eth0

# 在备节点执行相同命令,应无此IP

4.3 查看集群状态

sudo journalctl -u keepalived -f
# 正常日志示例:
# VRRP_Instance(VI_1) Transition to MASTER STATE
# VRRP_Instance(VI_1) Entering MASTER STATE

5. 故障切换测试

5.1 模拟主节点故障

# 在主节点停止Nginx服务
sudo systemctl stop nginx
# Keepalived检测到Nginx停止后,自动释放VIP

# 或在主节点直接关闭Keepalived
sudo systemctl stop keepalived

5.2 验证备节点接管VIP

# 在备节点检查IP
ip addr show eth0 | grep 192.168.1.100
# 应显示VIP已绑定到备节点

# 客户端访问VIP测试
curl http://192.168.1.100

6. 高级配置

6.1 邮件告警(主节点配置)

global_defs {
    notification_email {
        admin@example.com  # 接收告警的邮箱
    }
    notification_email_from keepalived@example.com
    smtp_server smtp.example.com
    smtp_connect_timeout 30
}

vrrp_instance VI_1 {
    notify_master "/etc/keepalived/notify.sh master"
    notify_backup "/etc/keepalived/notify.sh backup"
    notify_fault "/etc/keepalived/notify.sh fault"
}

创建通知脚本 /etc/keepalived/notify.sh

#!/bin/bash
case $1 in
    master) echo "VIP切换至主节点" | mail -s "Keepalived状态变更" admin@example.com ;;
    backup) echo "VIP切换至备节点" | mail -s "Keepalived状态变更" admin@example.com ;;
    fault)  echo "节点进入故障状态" | mail -s "Keepalived状态变更" admin@example.com ;;
esac

6.2 多VIP支持

virtual_ipaddress {
    192.168.1.100/24
    192.168.1.101/24  # 添加第二个VIP
}

7. 防火墙配置(重要!)

允许VRRP协议和Nginx端口:

# CentOS/RHEL (firewalld)
sudo firewall-cmd --permanent --add-rich-rule='rule protocol value="vrrp" accept'
sudo firewall-cmd --permanent --add-service=http
sudo firewall-cmd --permanent --add-service=https
sudo firewall-cmd --reload

# Ubuntu/Debian (ufw)
sudo ufw allow 80/tcp
sudo ufw allow 443/tcp
sudo ufw allow proto vrrp
sudo ufw reload

8. 常见问题

8.1 VIP无法切换

  • 检查项
    • 主备节点virtual_router_id是否一致。
    • 防火墙是否允许VRRP协议(IP协议号112)。
    • 网络是否互通(使用pingtcpdump抓包排查)。

8.2 脑裂问题(双主节点)

  • 解决方法
    • 检查网络延迟和丢包情况。
    • 调整advert_int值(如改为2秒)。
    • 使用第三方仲裁脚本(如通过HTTP检测共享状态)。

通过以上方案,您已实现Nginx+Keepalived的高可用集群,确保在单节点故障时服务无感知切换,适用于生产环境关键业务系统。

VRRP配置前提条件

1. 虚拟IP不得重复
2. 虚拟IP得和相同网段的网卡绑定

面试拿出来背即可

1. keppalived高可用是基于VRRP虚拟路由冗余协议实现的,因此我从VRRP给您描述起
2. VRRP也就是虚拟路由冗余协议,是为了解决静态路由的单点故障;
3. VRRP通过竞选协议将路由任务交给某一台VRRP路由器。
4. VRRP正常工作时,master会自动发送数据包,backup接收数据包,目的是为了判断对方是否存活;如果backup收不到master的数据包了,自动接管master的资源;
backup节点可以有多个,通过优先级竞选,但是keepalived服务器一般都是成对出现;
5. VRRP默认对数据包进行了加密,但是官网默认还是推荐使用明文来配置认证;

说完了VRRP,我再给您描述下keepalived工作原理。
1.keepalived就是基于VRRP协议实现的高可用,master的优先级必须高于backup,因此启动时master优先获得机器的IP资源,backup处于等待状态;若master挂掉后,backup顶替上来,继续提供服务。
2.在keepalived工作时,master角色的机器会一直发送VRRP广播数据包,告诉其他backup机器,“我还活着”,此时backup不会抢夺资源,老实呆着。
当master出现问题挂了,导致backup收不到master发来的广播数据包,因此开始接替VIP,保证业务的不中断运行,整个过程小于1秒。

1.环境准备

lb-5 10.0.0.5  keepalived-master机器  nginx-lb-5
lb-6 10.0.0.6  keepalived-backup机器  nginx-lb-6

web-7 10.0.0.7 web服务器
web-8 10.0.0.8 web服务器

2.安装keepalived(两台机器)

yum install keepalived -y

3.创建keepalived配置文件(lb-5)

global_defs {
    router_id lb-5 # 路由器ID,每个机器不一样
}

vrrp_instance VIP_1 {       # 设置VRRP路由器组组名,属于同一组的名字一样
    state MASTER            # 角色,master、backup两种            
    interface eth0          # VIP绑定的网卡         
    virtual_router_id 50    # 虚拟路由IP,同一组的一样    
    priority 150            # 优先级,优先级越高,权重越高
    advert_int 1            # 发送组播间隔1s
    authentication {        # 认证形式
        auth_type PASS      # 密码认证,明文密码 1111
        auth_pass 1111
    }
    virtual_ipaddress {
        10.0.0.3            # 指定虚拟VIP地址,必须没人使用
    }
}

使用如下配置

[root@lb-5 ~]#cat  /etc/keepalived/keepalived.conf 
global_defs {
    router_id lb-5
}

vrrp_instance VIP_1 {
    state MASTER
    interface eth0
    virtual_router_id 50
    priority 150
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {
        10.0.0.3
    }
}
[root@lb-5 ~]#

4.backup配置文件(lb-6)

[root@lb-6 ~]#cat  /etc/keepalived/keepalived.conf 
global_defs {
    router_id lb-6
}

vrrp_instance VIP_1 {
    state BACKUP
    interface eth0
    virtual_router_id 50
    priority 100
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {
        10.0.0.3
    }
}

5.启动keepalived(两台lb)

1.先检查当前的网卡情况

[root@lb-5 ~]#ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:eb:fe:a9 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.5/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:feeb:fea9/64 scope link 
       valid_lft forever preferred_lft forever
[root@lb-5 ~]#


[root@lb-6 ~]#ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:55:9f:53 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.6/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:fe55:9f53/64 scope link 
       valid_lft forever preferred_lft forever
[root@lb-6 ~]#

启动服务

systemctl start keepalived

再次检查VIP情况

[root@lb-5 ~]#ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:eb:fe:a9 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.5/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet 10.0.0.3/32 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:feeb:fea9/64 scope link 
       valid_lft forever preferred_lft forever
[root@lb-5 ~]#



[root@lb-6 ~]#ip addr show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:55:9f:53 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.6/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:fe55:9f53/64 scope link 
       valid_lft forever preferred_lft forever
[root@lb-6 ~]#

6.结合nginx测试(两台lb)

image-20220517205450153

6.1 lb-5

[root@lb-5 /etc/nginx/conf.d]#cat lb.conf 
upstream web_pools {
    server 10.0.0.7;
    server 10.0.0.8;
}
server {
listen 80;
server_name _;
location / {

    proxy_pass http://web_pools;
    include proxy_params;
}

}


[root@lb-5 /etc/nginx/conf.d]#cat /etc/nginx/proxy_params 
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_connect_timeout 30;
proxy_send_timeout 60;
proxy_read_timeout 60;
proxy_buffering on;
proxy_buffer_size 32k;
proxy_buffers 4 128k;




[root@lb-5 /etc/nginx/conf.d]#nginx -t
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful
[root@lb-5 /etc/nginx/conf.d]#systemctl restart nginx

6.2 lb-6

[root@lb-6 /etc/nginx/conf.d]#systemctl restart nginx
[root@lb-6 /etc/nginx/conf.d]#
[root@lb-6 /etc/nginx/conf.d]#
[root@lb-6 /etc/nginx/conf.d]#ls
lb.conf
[root@lb-6 /etc/nginx/conf.d]#cat lb.conf 
upstream web_pools {
    server 10.0.0.7;
    server 10.0.0.8;
}
server {
listen 80;
server_name _;
location / {

    proxy_pass http://web_pools;
    include proxy_params;
}

}
[root@lb-6 /etc/nginx/conf.d]#
[root@lb-6 /etc/nginx/conf.d]#cat /etc/nginx/proxy_params 
proxy_set_header Host $http_host;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_connect_timeout 30;
proxy_send_timeout 60;
proxy_read_timeout 60;
proxy_buffering on;
proxy_buffer_size 32k;
proxy_buffers 4 128k;

6.3 web-7、web-8

# cat web.conf
server {
 listen 80;
 server_name _;
    charset utf-8;
    location / {
        root /code;
        index index.html;
    }
}

# 创建测试数据
echo '你好,我是web-7,你也是来学linux的吗?'  > /code/index.html

echo '你好,我是web-8,你也是来学linux的吗?'  > /code/index.html

7.客户端访问(访问VIP)

image-20220517211719329

8.模拟master故障,查看VIP

当前VIP在lb-5机器上
[root@lb-5 ~]#ip a show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:eb:fe:a9 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.5/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet 10.0.0.3/32 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:feeb:fea9/64 scope link 
       valid_lft forever preferred_lft forever


lb-6的IP情况
[root@lb-6 ~]#ip a show eth0
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:55:9f:53 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.6/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:fe55:9f53/64 scope link 
       valid_lft forever preferred_lft forever

关闭master的keepalived服务

[root@lb-5 ~]#systemctl stop keepalived

查看此时服务会中断吗?继续访问10.0.0.3

查看lb-6机器是否实现了VIP漂移。

[root@lb-6 ~]#ip a 
1: lo: <LOOPBACK,UP,LOWER_UP> mtu 65536 qdisc noqueue state UNKNOWN group default qlen 1000
    link/loopback 00:00:00:00:00:00 brd 00:00:00:00:00:00
    inet 127.0.0.1/8 scope host lo
       valid_lft forever preferred_lft forever
    inet6 ::1/128 scope host 
       valid_lft forever preferred_lft forever
2: eth0: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:55:9f:53 brd ff:ff:ff:ff:ff:ff
    inet 10.0.0.6/24 brd 10.0.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet 10.0.0.3/32 scope global eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:fe55:9f53/64 scope link 
       valid_lft forever preferred_lft forever
3: eth1: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
    link/ether 00:0c:29:55:9f:5d brd ff:ff:ff:ff:ff:ff
    inet 172.16.1.6/24 brd 172.16.1.255 scope global noprefixroute eth1
       valid_lft forever preferred_lft forever
    inet6 fe80::20c:29ff:fe55:9f5d/64 scope link 
       valid_lft forever preferred_lft forever

9.恢复lb-5的keepalived服务

[root@lb-5 ~]#systemctl start keepalived

查看此时VIP又漂移到了那里。

backup机器的VIP是否消失。

Keepalived脑裂问题

简单说就是如果master还在正常工作,但是backup没有正确接收到master的心跳数据包,就会以为master挂掉了,抢夺VIP资源。

这个世道就会导致两个服务器都有了VIP,导致冲突故障,这就是脑裂问题。

1.导致脑裂的原因

要实现心跳检测,需要让至少两台服务器实现互相通信,数据包收发,主要通过如下方式实现

  • (生产环境下做法)直接网线让两台服务器直连
  • 也可以通过局域网通信,确保两台机器可以连接。

高可用软件基于这个心跳线来判断对端机器是否存活,决定是否要实现故障迁移,VIP迁移,保证业务的连续性。

一般来说,导致脑裂的原因有这些,也是排错思路

  • 心跳线老化,线路破损,导致无法通信
  • 网卡驱动损坏,master、backup IP地址冲突。
  • 防火墙配置错误,导致心跳消息收不到
  • 配置文写错了,两台机器的虚拟路由ID不一致。

2.解决脑裂

  • 使用双心跳线路,防止单线路损坏,只要确保master的心跳数据包能发给backup。
  • 通过脚本程序检测脑裂情况
    • 判断是否两边都有VIP,如果心跳重复,强制关闭一个心跳节点(直接发送关机命令,强制断掉主节点的电源)
  • 做好脑裂监控,如果发现脑裂,人为第一时间干预处理。
  • 如果开启了防火墙,注意要允许心跳IP的访问。

keepalived组播原理

单播流量走向图

image-20220518143705130

广播数据流

image-20220518144103582

组播数据流

image-20220518144257051

keepalived组播地址

组播: 主机之间一对多的通讯模式,将数据源发送到一组内的多个接受者;组播将报文发到特定的组播地址,它不属于一个单个的主机,而是一组主机;

一个组播地址属于一个群组,在这个组里的接受者都可以收到报文;

keepalived默认使用VRRP虚拟路由器冗余协议,在默认组播224.0.0.18这个IP地址以实现在master和backup机器之间进行通信,实现健康检查。

抓包查看VRRP

image-20220518144557047

停止master试试

[root@lb-5 ~]#systemctl stop keepalived

心跳切换原理

image-20220518144931148

backup切换原理

image-20220518145050506

抓包工具查看脑裂

这里在linux下进行抓包。

lb-5安装tcpdump

[root@lb-5 ~]#yum install tcpdump -y

lb-5抓包

# 参数 
#  -nn:    指定将每个监听到的数据包中的域名转换成IP、端口从应用名称转换成端口号后显示
# -i      指定监听的网络接口;
# any 抓取所有网络接口
# host 指定抓取的主机地址,这里是组播地址。

tcpdump -nn -i any host 224.0.0.18

lb-6开启防火墙

开启防火墙后,导致lb-5没法和lb-6正常通信,backup以为master挂了,抢夺VIP资源。

此时高可用集群就已故障,无法正常漂移切换VIP了。

1.停止master keepalived
2. 发现backup也无法正常工作

停止lb-6的防火墙

可正确恢复 keepalived;
因为你只要确保master能通过给组播发消息,确保backup能收到。
两边的高可用心跳就没问题。

解决脑裂的方案

防火墙规则放行

# 只要启动服务就会抢夺VIP
systemctl restart firewalld

# VIP应该会消失,VRRP正常
iptables -I INPUT -i eth0 -d 224.0.0.0/8 -p vrrp -j ACCEPT

image-20220519181103252

防止脑裂的脚本开发

更靠谱的做法是,自己编写shell脚本,核心思路是

确保backup机器定时去判断master的VIP状态,如果发生脑裂,backup自杀即可(kill keepalived)

防止脑裂脚本思路

先有思路,再写脚本

针对backup服务器

1. backup定期检查master的nginx是否运行
2. backup定期检查自己是否有VIP
3. 如果有如下情况,backup却也有VIP,就是脑裂
- master的nginx正常
- master有VIP
- backup有VIP

4. 如果backup有脑裂,就干掉自己的keepalived
5. 告知管理员。

1.backup脚本开发

cat > /etc/keepalived/check_vip.sh << 'EOF'
#!/bin/bash
MASTER_VIP=$(ssh 10.0.0.5 ip a|grep 10.0.0.3|wc -l)
MY_VIP=$(ip a|grep 10.0.0.3|wc -l)

# 如果远程有VIP并且自己本地也存在了VIP,就干掉自己
if [ ${MASTER_VIP} == 1 -a ${MY_VIP} == 1 ]
then
   systemctl stop keepalived
fi
EOF

2. backup服务调用自杀脚本

这里是利用了keepalived自身提供的vrrp_script脚本功能,实现监控,自动干掉自己。。

前提条件是

  • 脚本添加执行权限
  • lb-6和lb-5免密登录
cat > /etc/keepalived/keepalived.conf << 'EOF'
global_defs {
    router_id lb-6
}

# 定义脚本
vrrp_script check_vip {
    script "/etc/keepalived/check_vip.sh"
    interval 5 # 脚本执行的时间间隔
}

vrrp_instance VIP_1 {
    state BACKUP 
    interface eth0
    virtual_router_id 50
    priority 100
    advert_int 1
    authentication {
        auth_type PASS
        auth_pass 1111
    }
    virtual_ipaddress {
        10.0.0.3
    }
    # 调动脚本
    track_script {
        check_vip
    }
}
EOF

3.测试backup的监控脚本

1. 确保master、backup正常 
systemctl restart keepalived


2. 主动导致脑裂,查看情况
[root@lb-6 /etc/keepalived]#systemctl restart firewalld

image-20220519184805278

情况2:master出现问题

问题背景

刚才的脚本解决了backup抢夺VIP的问题;
但是如果master出了问题呢?比如master的nginx挂了,那keepalived没啥用了,服务还是挂了。

监控master故障的脚本。

思路

master机器脚本
1. 如果自己的nginx已经不存在了,keepalived还活着,尝试重启nginx
2. 如果重启nginx失败,干掉自己的keepalived,放弃master资源,让backup继续干活

脚本如下

cat > /etc/keepalived/check_web.sh << 'EOF'
#!/bin/bash
NGINX_STATUS=$(ps -ef|grep ngin[x]|wc -l)
# 如果nginx挂了
if [ ${NGINX_STATUS} == 0 ]
then
   systemctl restart nginx
   # 如果重启失败
   if [ $? == 1 ]
   then
         # keepalived没必要活着了
      systemctl stop keepalived
   fi
fi
EOF

keepalived调用脚本

cat > /etc/keepalived/keepalived.conf << 'EOF'
global_defs {
    router_id lb-5
}

vrrp_script check_web {
    script "/etc/keepalived/check_web.sh"
    interval 5
}

vrrp_instance VIP_1 {
    state MASTER
        interface eth0
        virtual_router_id 50
        priority 150
        advert_int 1
        authentication {
            auth_type PASS
            auth_pass 1111
        }
        virtual_ipaddress {
            10.0.0.3
        }
        track_script {
            check_web
        }
}
EOF

注意给脚本加上权限

[root@lb-5 ~]#chmod +x /etc/keepalived/check_web.sh

模拟故障

1.确保master和backup正常

2.停止master的nginx
[root@lb-5 ~]#chmod +x /etc/keepalived/check_web.sh 

3.发现你此时就已经没法停了,keepalived帮你自动重启nginx

4.你可以试试让nginx起不来
[root@lb-5 ~]#echo 'yuchaoit.cn' >> /etc/nginx/nginx.conf 
[root@lb-5 ~]#systemctl stop nginx
[root@lb-5 ~]#

5.此时已经正确切换到backup了。

修复master

[root@lb-5 ~]#systemctl restart nginx

[root@lb-5 ~]#systemctl restart keepalived

查看backup是否归还VIP资源。

小结

Keepalived是一个优秀的高可用工具,不仅可以结合nginx做高可用性负载均衡;

也可以和mysql数据库软件实现主从复制的高可用性;

生产环境负载均衡集群

阿里云提供的高可用性负载均衡文档

https://help.aliyun.com/document_detail/67915.html

看动画片学习什么是负载均衡

http://tbm-auth.alicdn.com/LLFT8IQamEO30zOTfNw/6AcL8H7yRzRN7AKZ0UN_219932284972_hd_hq.mp4?auth_key=1652962160-0-0-9cefb1d3f3742210e479ed08abfeb23a&t=21360c5f16529594601105023e43b8&b=video&p=cloudvideo_http_42_4

待你和于超老师学完了 (高可用性负载均衡集群),在你真真切切的动手练习了,以及掌握其中内部原理了。

再去维护公有云提供的阿里云SLB,就是易如反掌了。

在阿里云上,点击购买不同价格的负载均衡,获取到一个SLB的IP地址(nginx + keepalived)
然后再填写后端的服务器组即可(upstream 地址池)

老铁们,你学废了吗?~~~~

image-20220519192829775

Copyright © www.yuchaoit.cn 2025 all right reserved,powered by Gitbook作者:于超 2025-02-28 22:33:31

results matching ""

    No results matching ""