Linux之Keepalived高可用

  • A+
所属分类:linux技术
摘要

一般是指2台机器启动着完全相同的业务系统,当有一台机器down机了,另外一台服务器就能快速的接管,对于访问的用户是无感知的。


一、高可用介绍

1.1 什么是高可用

一般是指2台机器启动着完全相同的业务系统,当有一台机器down机了,另外一台服务器就能快速的接管,对于访问的用户是无感知的。

1.2 常用的工具

  • 硬件通常使用:F5
  • 软件通常使用:Keepalived

1.3 keepalived是如何实现高可用的?

1.3.1 涉及名词

keepalived软件是基于VRRP协议实现的,VRRP虚拟路由冗余协议,主要用于解决单点故障问题

ARP:广播
VRRP协议:在一个局域网中进行广播
vip:负责IP漂移
vmac:负责通知ARP广播修改mac地址

1.3.2 例子

比如公司的网络是通过网关进行上网的,那么如果该路由器故障了,网关无法转发报文了,此时所有人都无法上网了,怎么办?

通常做法是给路由器增加一台备用节点,但是问题是,如果我们的主网关master故障了,用户是需要手动指向backup的,如果用户过多修改起来会非常麻烦。

问题一:假设用户将指向都修改为backup路由器,那么master路由器修好了怎么办?
问题二:假设Master网关故障,我们将backup网关配置为master网关的ip是否可以?

其实是不行的,因为PC第一次通过ARP广播寻找到Master网关的MAC地址与IP地址后,会将信息写到ARP的缓存表中,那么PC之后连接都是通过那个缓存表的信息去连接,然后进行数据包的转发,即使我们修改了IP但是Mac地址是唯一的,pc的数据包依然会发送给master。(除非是PC的ARP缓存表过期,再次发起ARP广播的时候才能获取新的backup对应的Mac地址与IP地址)

如何才能做到出现故障自动转移,此时VRRP就出现了,我们的VRRP其实是通过软件或者硬件的形式在Master和Backup外面增加一个虚拟的MAC地址(VMAC)与虚拟IP地址(VIP),那么在这种情况下,PC请求VIP的时候,无论是Master处理还是Backup处理,PC仅会在ARP缓存表中记录VMAC与VIP的信息。

1.4 高可用keepalived核心概念

  1. 如何确定谁是主节点谁是备节点(选举投票,优先级)
  2. 如果Master故障,Backup自动接管,那么Master恢复后会夺权吗(抢占式、非抢占式)
  3. 如果两台服务器都认为自己是Master会出现什么问题(脑裂问题)

二、keepalived搭建

2.1 环境准备

主机 IP 身份
lb01 192.168.15.5 keepalived master
lb02 192.168.15.6 keepalived backup
web01 172.16.1.7 web端
web02 172.16.1.8 web端
db01 172.16.1.61 数据库
192.168.15.3 VIP

2.2 安装Keepalived

[root@lb01 conf.d]# yum install keepalived -y 

2.3 配置keepalived

  1. 查找配置文件

    [root@lb01 ~]# rpm -qc keepalived /etc/keepalived/keepalived.conf 
  2. 配置主节点LoadBalance01的配置文件

    [root@lb01 ~]# vim /etc/keepalived/keepalived.conf ! Configuration File for keepalived  # 全局配置 global_defs {    # 当前keepalived的唯一标识    router_id LoadBalance01 }  # 配置VRRP协议 vrrp_instance VI_1 {     # 状态,MASTER和BACKUP     state MASTER     # 绑定网卡     interface eth0     # 虚拟路由标示,可以理解为分组     virtual_router_id 50     # 优先级     priority 100     # 监测心跳间隔时间     advert_int 1     # 配置认证     authentication {         # 认证类型         auth_type PASS         # 认证的密码         auth_pass 1111     }     # 设置VIP     virtual_ipaddress {         # 虚拟的VIP地址         192.168.15.3     } } 
  3. 配置备用节点LoadBalance01的配置文件

    [root@lb01 ~]# vim /etc/keepalived/keepalived.conf ! Configuration File for keepalived  # 全局配置 global_defs {    # 当前keepalived的唯一标识    router_id LoadBalance02 }  # 配置VRRP协议 vrrp_instance VI_1 {     # 状态,MASTER和BACKUP     state BACKUP     # 绑定网卡     interface eth0     # 虚拟路由标示,可以理解为分组     virtual_router_id 50     # 优先级     priority 80     # 监测心跳间隔时间     advert_int 1     # 配置认证     authentication {         # 认证类型         auth_type PASS         # 认证的密码         auth_pass 1111     }     # 设置VIP     virtual_ipaddress {         # 虚拟的VIP地址         192.168.15.3     } } 

2.4 启动服务(开机自启动)

[root@lb01 ~]# systemctl enable --now keepalived [root@lb02 ~]# systemctl enable --now keepalived 

2.5 keepalived开启日志

#配置keepalived [root@lb01 ~]# vim /etc/sysconfig/keepalived KEEPALIVED_OPTIONS="-D -d -S 0"   #配置rsyslog抓取日志 [root@lb01 ~]# vim /etc/rsyslog.conf local0.*        /var/log/keepalived.log   #重启服务 [root@lb01 ~]# systemctl restart keepalived rsyslog 

三、Keepalived的抢占式与非抢占式

3.1 两个节点都启动的情况

#两个节点都启动时,由于节点1优先级高于节点2,所以只有节点1上有VIP [root@lb01 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0   [root@lb02 ~]# ip addr | grep 192.168.15.3 

3.2 停止主节点

[root@lb01 ~]# systemctl stop keepalived [root@lb01 ~]# ip addr | grep 192.168.15.3   #由于节点1的keepalived 挂掉,节点2会自动接管节点1的工作,即VIP [root@lb02 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0 

3.3 重新启动主节点

#启动主节点 [root@lb01 ~]# systemctl start keepalived [root@lb01 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0  #由于节点1优先级高于节点2,所以当节点1恢复时,会将VIP抢占回来 

3.4 配置非抢占式

  1. 主节点配置(LoadBalance01)

    [root@lb01 ~]# vim /etc/keepalived/keepalived.conf  ... ... vrrp_instance VI_1 {     #状态,MASTER和BACKUP     state BACKUP     # 开启非抢占式     nopreempt     #绑定网卡     interface eth0     #虚拟路由标示,可以理解为分组     virtual_router_id 50     #优先级     priority 100 ... ... }   [root@lb01 ~]# systemctl restart keepalived 
  2. 备用节点配置(LoadBalance02)

    [root@lb02 ~]# vim /etc/keepalived/keepalived.conf  ... ... vrrp_instance VI_1 {     #状态,MASTER和BACKUP     state BACKUP     # 开启非抢占式     nopreempt     #绑定网卡     interface eth0     #虚拟路由标示,可以理解为分组     virtual_router_id 50     #优先级     priority 90 ... ... }   [root@lb02 ~]# systemctl restart keepalived.service 
  3. 配置注意事项

    1. 两个节点的state都必须配置为BACKUP;
    2. 两个节点都必须加上配置 nopreempt;
    3. 其中一个节点的优先级必须要高于另外一个节点的优先级;

    两台服务器都角色状态启用nopreempt后,必须修改角色状态统一为BACKUP,唯一的区分就是优先级。

四、Keepalived脑裂

由于某些原因,导致两台keepalived高可用服务器在指定时间内,无法检测到对方的心跳,各自取得资源及服务的所有权,而此时的两台高可用服务器又都还活着。

4.1 脑裂的故障

  • 网线松动,网络故障
  • 服务器硬件故障
  • 服务器之间开启了防火墙

4.2 脑裂模拟

  1. 开启防火墙

    [root@lb01 ~]# systemctl start firewalld [root@lb01 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0   [root@lb02 ~]# systemctl start firewalld [root@lb02 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0 
  2. 访问网站

    #因为开启了firewalld防火墙,默认拒绝所有连接,要开启80端口 [root@lb01 ~]# firewall-cmd --add-service=http success [root@lb02 ~]# firewall-cmd --add-service=http success   [root@lb01 ~]# firewall-cmd --add-service=https success [root@lb02 ~]# firewall-cmd --add-service=https success   #访问页面没有任何问题 
  3. 关闭防火墙

    [root@lb02 ~]# systemctl stop firewalld  [root@lb02 ~]# ip addr | grep 192.168.15.3   [root@lb01 ~]# systemctl stop firewalld [root@lb01 ~]# ip addr | grep 192.168.15.3     inet 192.168.15.3/32 scope global eth0 

4.3 脑裂解决的办法

#如果发生脑裂,则随机kill掉一台即可 #在备用节点上编写检测脚本, 测试如果能ping通主节点并且备节点还有VIP的话则认为产生了脑裂 [root@lb02 ~]# cat check_split_brain.sh #!/bin/sh vip=192.168.15.3 lb01_ip=192.168.15.5 while true;do     ping -c 2 $lb01_ip &>/dev/null     if [ $? -eq 0 -a `ip add|grep "$vip"|wc -l` -eq 1 ];then         echo "ha is split brain.warning."     else         echo "ha is ok"     fi sleep 5 done   [root@lb02 ~]# vim check_keepalive.sh  #!/bin/sh vip=192.168.15.3 lb01_ip=172.16.1.5 while true;do     ssh $lb01_ip 'ip addr | grep 10.0.0.3' &>/dev/null     if [ $? -eq 0 -a `ip add|grep "$vip"|wc -l` -eq 1 ];then         echo "ha is split brain.warning."     else         echo "ha is ok"     fi sleep 3 done 

五、高可用Keepalived与Nginx

Nginx默认监听在所有的IP地址上,VIP会飘到一台节点上,相当于那台nginx多了VIP这么一个网卡,所以可以访问到nginx所在机器

但是.....如果nginx宕机,会导致用户请求失败,但是keepalived没有挂掉不会进行切换,所以需要编写一个脚本检测Nginx的存活状态,如果不存活则kill掉keepalived

5.1 Nginx故障切换脚本

[root@lb01 ~]# vim check_web.sh #!/bin/sh nginxpid=$(ps -ef | grep [n]ginx | wc -l)   #1.判断Nginx是否存活,如果不存活则尝试启动Nginx if [ $nginxpid -eq 0 ];then     systemctl start nginx &>/dev/null     sleep 3     #2.等待3秒后再次获取一次Nginx状态     nginxpid=$(ps -ef | grep [n]ginx | wc -l)      #3.再次进行判断, 如Nginx还不存活则停止Keepalived,让地址进行漂移,并退出脚本       if [ $nginxpid -eq 0 ];then         systemctl stop keepalived     fi fi   #给脚本增加可执行权限 [root@lb01 ~]# chmod +x /root/check_web.sh 

5.2 使用keepalived配置文件调用nginx切换脚本

  • 配置抢占式时

    #只需要在主节点配置 [root@lb01 ~]# vim /etc/keepalived/keepalived.conf  global_defs {     router_id LoadBalance01 }   #每5秒执行一次脚本,脚本执行内容不能超过5秒,否则会中断再次重新执行脚本 vrrp_script check_web {     script "/root/check_web.sh"     interval 5 }   vrrp_instance VI_1 {     state MASTER     nopreempt     interface eth0     virtual_router_id 50     priority 100     advert_int 1     authentication {         auth_type PASS         auth_pass 1111     }     virtual_ipaddress {         192.168.15.3     }     #调用计划的脚本     track_script {         check_web     } } 
  • 配置非抢占式时

    #配置非抢占式时,两边都要配置脚本 [root@lb01 ~]# scp check_web.sh 172.16.1.6:/root   #备用节点也要配置 [root@lb02 ~]# cat /etc/keepalived/keepalived.conf  global_defs {     router_id LoadBalance02 }   vrrp_script check_web {     script "/root/check_web.sh"     interval 5 }   vrrp_instance VI_1 {     state BACKUP     nopreempt     interface eth0     virtual_router_id 50     priority 90     advert_int 1     authentication {         auth_type PASS         auth_pass 1111     }     virtual_ipaddress {         192.168.15.3     }     track_script {         check_web     } } 

5.3 测试

  1. 将VIP所在机器nginx的配置文件修改错误
  2. 停止nginx
  3. 查看VIP是否切换