【11.8】负载均衡、LVS
18.6 负载均衡集群介绍
- 主流开源软件 LVS、keepalived、haproxy、nginx等
- 其中LVS 属于4层(网络OSI 7层模型),nginx 属于7层,haproxy 既可以认为是4层,也可以当做7层使用
- keepalived 的负载均衡功能其实就是 lvs
- lvs 这种4层的负载均衡是可以分发除80外的其他端口通信的,比如 MySQL 的,而 nginx 仅仅支持 http,https,mail,haproxy 也支持MySQL这种
- 相比较来说,LVS 这种4层的更稳定,能承受更多的请求,而 nginx 这种7层的更加灵活,能实现更多的个性化需求
18.7 LVS介绍
- LVS 是由国人章文嵩开发
- 流行度不亚于 apache 的 httpd,基于 TCP/IP 做的路由和转发,稳定性和效率很高
- LVS 最新版本基于 Linux 内核2.6,有好多年不更新了
- LVS 有三种常见的模式:NAT、DR、IP Tunnel
- LVS 架构中有一个核心角色叫做分发器(Load balance),它用来分发用户的请求,还有诸多处理用户请求的服务器(Real Server,简称 rs)
1、LVS NAT模式(10台以下)
- 这种模式借助 iptables 的 nat 表来实现
- 用户的请求到分发器后,通过预设的 iptables 规则,把请求的数据包转发到后端的 rs 上去
- rs 需要设定网关为分发器的内网 ip
- 用户请求的数据包和返回给用户的数据包全部经过分发器,所以分发器成为瓶颈
- 在 nat 模式中,只需要分发器有公网 ip 即可,所以比较节省公网 ip 资源
2、LVS IP Tunnel模式
- 这种模式,需要有一个公共的 IP 配置在分发器和所有rs上,我们把它叫做 vip
- 客户端请求的目标 IP 为 vip,分发器接收到请求数据包后,会对数据包做一个加工,会把目标 IP 改为 rs 的 IP,这样数据包就到了 rs 上
- rs 接收数据包后,会还原原始数据包,这样目标 IP 为 vip,因为所有 rs 上配置了这个 vip,所以它会认为是它自己
- 结果反馈给客户端
NAT 就是 iptables 转发,IP Tunnel 把模板 ip 做更改
3、LVS DR模式
- 这种模式,也需要有一个公共的 IP 配置在分发器和所有 rs 上,也就是 vip
- 和IP Tunnel 不同的是,它会把数据包的 MAC 地址修改为 rs 的 MAC 地址
- rs接收数据包后,会还原原始数据包,这样目标 IP 为 vip ,因为所有 rs 上配置了这个 vip,所以它会认为是它自己
- 结果反馈给客户端
18.8 LVS调度算法
- 轮询 Round-Robin rr
- 加权轮询 Weight Round-Robin wrr
- 最小连接 Least-Connection lc
- 加权最小连接 Weight Least-Connection wlc
- 基于局部性的最小连接 Locality-Based Least Connections lblc
- 带复制的基于局部性最小连接 Locality-Based Least Connections with Replication lblcr
- 目标地址散列调度 Destination Hashing dh
- 源地址散列调度 Source Hashing sh
18.9/18.10 LVS NAT模式搭建
准备工作
1、准备三台机器
分发器,简称 dir 192.168.194.130
rs1 192.168.194.132
rs2 192.168.194.133
2、给分发器添加一块网卡
ens37:192.168.174.100,本地 windows 上能 ping 通
3、三台机器上全部关闭 firewalld
4、三台机器安装 iptables-services,保存空规则
5、RS1 上安装 iptables-service
[root@arslinux-02 ~]# yum install -y iptables-services
iptables-services.x86_64 0:1.4.21-28.el7
6、RS1 开启 iptables 服务,并调用空规则
[root@alexis-02 ~]# systemctl start iptables
[root@alexis-02 ~]# systemctl enable iptables
Created symlink from /etc/systemd/system/basic.target.wants/iptables.service to /usr/lib/systemd/system/iptables.service.
[root@alexis-02 ~]# iptables -F
[root@alexis-02 ~]# service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[ 确定 ]
7、同样的方法在 RS2 上安装 iptables-service,并打开 iptables 服务
[root@alexis-03 ~]# systemctl start iptables
[root@alexis-03 ~]# systemctl enable iptables
Created symlink from /etc/systemd/system/basic.target.wants/iptables.service to /usr/lib/systemd/system/iptables.service.
[root@alexis-03 ~]# iptables -F
[root@alexis-03 ~]# service iptables save
iptables: Saving firewall rules to /etc/sysconfig/iptables:[ 确定 ]
8、将 rs1 和 rs2 的网关设置为分发器的 ip 地址 192.168.194.130
[root@alexis-02 ~]# vim /etc/sysconfig/network-scripts/ifcfg-ens33
[root@alexis-02 ~]# cat !$ |grep GATEWAY
cat /etc/sysconfig/network-scripts/ifcfg-ens33 |grep GATEWAY
GATEWAY=192.168.194.130
[root@alexis-03 ~]# vim /etc/sysconfig/network-scripts/ifcfg-ens33
[root@alexis-03 ~]# cat !$ |grep GATEWAY
cat /etc/sysconfig/network-scripts/ifcfg-ens33 |grep GATEWAY
GATEWAY=192.168.194.130
9、关闭selinux,编辑 /etc/selinux/config,状态改为 disable
10、重启rs1 和 rs2 的网卡后就成了内网机器,无法再上网了
搭建工作
1、在 dir 上安装 ipvsadm
[root@alexis-01 ~]# yum install -y ipvsadm
2、主上写脚本 vim /usr/local/sbin/lvs_nat.sh
[root@alexis-01 ~]# vim /usr/local/sbin/lvs_nat.sh
#! /bin/bash
# director 服务器上开启路由转发功能
echo 1 > /proc/sys/net/ipv4/ip_forward
# 关闭icmp的重定向
echo 0 > /proc/sys/net/ipv4/conf/all/send_redirects
echo 0 > /proc/sys/net/ipv4/conf/default/send_redirects
# 注意区分网卡名字,阿铭的两个网卡分别为ens33和ens37
echo 0 > /proc/sys/net/ipv4/conf/ens33/send_redirects
echo 0 > /proc/sys/net/ipv4/conf/ens37/send_redirects
# director 设置nat防火墙
iptables -t nat -F
iptables -t nat -X
iptables -t nat -A POSTROUTING -s 192.168.194.0/24 -j MASQUERADE
# director设置ipvsadm
IPVSADM='/usr/sbin/ipvsadm'
$IPVSADM -C
$IPVSADM -A -t 192.168.174.100:80 -s lc -p 3
$IPVSADM -a -t 192.168.174.100:80 -r 192.168.194.132:80 -m -w 1
$IPVSADM -a -t 192.168.174.100:80 -r 192.168.194.133:80 -m -w 1
[root@alexis-01 ~]# sh /usr/local/sbin/lvs_nat.sh
3、测试
确保 rs1 和 rs2 上 nginx 都已经启动,并已监听 80端口
rs1 上
[root@alexis-02 ~]# curl localhost
backup,backup
rs2 上
rs2 上的默认页要和 rs1 上区分开,先编辑默认页,再 curl
[root@alexis-03 ~]# mv /usr/share/nginx/html/index.html /usr/share/nginx/html/index.html.bak
[root@alexis-03 ~]# vim /usr/share/nginx/html/index.html
backup2,backup2
[root@alexis-03 ~]# curl localhost
backup2,backup2
访问 192.168.174.100
4、ipvsadm的规则:
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.174.100:80 wlc persistent 3
-> 192.168.194.132:80 Masq 1 0 0
-> 192.168.194.133:80 Masq 1 0 1
5、可能连续几次访问该ip结果都是RS2,也许是缓存的原因
可以把lvs_nat.sh的IPVSADM规则第一条改为:轮询
$IPVSADM -A -t 192.168.174.100:80 -s rr
6、重新sh一下
[root@alexis-01 ~]# sh /usr/local/sbin/lvs_nat.sh
7、用curl来连外网ip,看看结果
[root@alexis-01 ~]# curl 192.168.174.100
backup2,backup2
[root@alexis-01 ~]# curl 192.168.174.100
backup,backup
[root@alexis-01 ~]# curl 192.168.174.100
backup2,backup2
[root@alexis-01 ~]# curl 192.168.174.100
backup,backup
[root@arslinux-01 ~]# curl 192.168.174.100
backup2,backup2
[root@alexis-01 ~]# curl 192.168.174.100
backup,backup
[root@alexis-01 ~]# curl 192.168.174.100
backup2,backup2
[root@alexis-01 ~]# curl 192.168.174.100
backup,backup
访问还是非常平均的,这是rr起作用了
实验成功!
18.11 LVS DR模式搭建
生产环境中 DR 模式使用比较多,IP tunnel 模式比较少,NAT 模式也不多
试验环境:
分发器: 192.168.194.130
rs1 :192.168.194.132
rs2 :192.168.194.133
vip :192.168.194.200
1、将 rs1 和 rs2 的网关改回默认网关,192.168.194.2
2、dir 上编辑脚本 /usr/local/sbin/lvs_dr.sh
[root@alexis-01 ~]# vim /usr/local/sbin/lvs_dr.sh
#! /bin/bash
echo 1 > /proc/sys/net/ipv4/ip_forward
ipv=/usr/sbin/ipvsadm
vip=192.168.194.200
rs1=192.168.194.132
rs2=192.168.194.133
#注意这里的网卡名字
ifdown ens33
ifup ens33
ifconfig ens33:2 $vip broadcast $vip netmask 255.255.255.255 up
route add -host $vip dev ens33:2
$ipv -C
$ipv -A -t $vip:80 -s rr
$ipv -a -t $vip:80 -r $rs1:80 -g -w 1
$ipv -a -t $vip:80 -r $rs2:80 -g -w 1
-m是nat模式,-g是dr模式
3、执行脚本 lvs_dr.sh
[root@alexis-01 ~]# sh /usr/local/sbin/lvs_dr.sh
成功断开设备 'ens33'。
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/4)
4、两台 rs 上也要编辑脚本 /usr/localsbin/lvs_rs.sh
[root@alexis-02 ~]# vim /usr/local/sbin/lvs_rs.sh
#/bin/bash
vip=192.168.133.200
#把vip绑定在lo上,是为了实现rs直接把结果返回给客户端
ifdown lo
ifup lo
ifconfig lo:0 $vip broadcast $vip netmask 255.255.255.255 up
route add -host $vip lo:0
#以下操作为更改arp内核参数,目的是为了让rs顺利发送mac地址给客户端
#参考文档www.cnblogs.com/lgfeng/archive/2012/10/16/2726308.html
echo "1" >/proc/sys/net/ipv4/conf/lo/arp_ignore
echo "2" >/proc/sys/net/ipv4/conf/lo/arp_announce
echo "1" >/proc/sys/net/ipv4/conf/all/arp_ignore
echo "2" >/proc/sys/net/ipv4/conf/all/arp_announce
rs 2 同 rs1
5、分别执行 lvs_rs.sh
6、route -n
[root@alexis-02 ~]# route -n
Kernel IP routing table
Destination Gateway Genmask Flags Metric Ref Use Iface
0.0.0.0 192.168.194.2 0.0.0.0 UG 100 0 0 ens33
192.168.133.200 0.0.0.0 255.255.255.255 UH 0 0 0 lo
192.168.194.0 0.0.0.0 255.255.255.0 U 100 0 0 ens33
[root@alexis-02 ~]# ip add
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
inet 192.168.133.200/32 brd 192.168.133.200 scope global lo:0
valid_lft forever preferred_lft forever
inet6 ::1/128 scope host
valid_lft forever preferred_lft forever
2: ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:14:4f:d9 brd ff:ff:ff:ff:ff:ff
inet 192.168.194.132/24 brd 192.168.194.255 scope global noprefixroute ens33
valid_lft forever preferred_lft forever
inet6 fe80::4c99:ed43:5757:e772/64 scope link noprefixroute
valid_lft forever preferred_lft forever
7、dir 上的 ip,ens33 有 192.168.194.200
[root@alexis-01 ~]# ip add
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: ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:f2 brd ff:ff:ff:ff:ff:ff
inet 192.168.194.130/24 brd 192.168.194.255 scope global noprefixroute ens33
valid_lft forever preferred_lft forever
inet 192.168.194.200/32 brd 192.168.194.200 scope global ens33:2
valid_lft forever preferred_lft forever
inet 192.168.194.150/24 brd 192.168.194.255 scope global secondary noprefixroute ens33:0
valid_lft forever preferred_lft forever
inet6 fe80::c905:5e78:b916:41da/64 scope link noprefixroute
valid_lft forever preferred_lft forever
3: ens37: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:fc brd ff:ff:ff:ff:ff:ff
inet 192.168.100.1/24 brd 192.168.100.255 scope global noprefixroute ens37
valid_lft forever preferred_lft forever
inet6 fe80::f41:9da7:d8e3:10ba/64 scope link noprefixroute
valid_lft forever preferred_lft forever
4: ens38: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:06 brd ff:ff:ff:ff:ff:ff
inet 192.168.174.100/24 brd 192.168.174.255 scope global noprefixroute ens38
valid_lft forever preferred_lft forever
inet6 fe80::d106:93d1:7e89:8102/64 scope link noprefixroute
valid_lft forever preferred_lft forever
8、测试,浏览器访问 192.168.194.200 ,多访问几次看结果
客户量达到一定程度之后,就会达到均衡的作用
注意:打开端口转发,修改内核参数不要忘
nat 模式需要将 rs 的网关修改为 dir 的内网 ip,不要忽略
18.12 keepalived + LVS
-
为什么将 keepalived 加入到 lvs 中来的目的:
1,lvs 有 分发器的角色,一旦宕机,所有服务和访问都会被终止(所有入口在分发器 dir 上)
2,keepalived 有负载均衡的作用
3,lvs 并不聪明,哪怕后台有一个 rs 宕机,它依然会将请求转发过去,有 keepalived 的话,一台 rs宕机时,keepalived 不会再将请求转发过去 -
完整架构需要两台服务器(角色为dir)分别安装 keepalived 软件,目的是实现高可用,但keepalived 本身也有负载均衡的功能,所以本次实验可以只安装一台 keepalived
-
keepalived 内置了 ipvsadm 的功能,所以不需要再安装 ipvsadm 包,也不用编写和执行那个 lvs_dir 的脚本
-
测试环境:
dir :192.168.194.130
rs1 :192.168.194.132
rs2 :192.168.194.133
vip :192.168.194.100
1、dir 上编辑 /etc/keepalived/keepalived.conf
[root@alexis-01 ~]# vim /etc/keepalived/keepalived.conf
vrrp_instance VI_1 {
#备用服务器上为 BACKUP
state MASTER
#绑定vip的网卡为ens33,你的网卡和阿铭的可能不一样,这里需要你改一下
interface ens33
virtual_router_id 51
#备用服务器上为90
priority 100
advert_int 1
authentication {
auth_type PASS
auth_pass aminglinux
}
virtual_ipaddress {
192.168.194.200
}
}
virtual_server 192.168.194.200 80 {
#(每隔10秒查询realserver状态)
delay_loop 10
#(lvs 算法)
lb_algo wlc
#(DR模式)
lb_kind DR
#(同一IP的连接60秒内被分配到同一台realserver)
persistence_timeout 0
#(用TCP协议检查realserver状态)
protocol TCP
real_server 192.168.194.132 80 {
#(权重)
weight 100
TCP_CHECK {
#(10秒无响应超时)
connect_timeout 10
nb_get_retry 3
delay_before_retry 3
connect_port 80
}
}
real_server 192.168.194.133 80 {
weight 100
TCP_CHECK {
connect_timeout 10
nb_get_retry 3
delay_before_retry 3
connect_port 80
}
}
}
2、启动 keepalived
[root@alexis-01 ~]# systemctl start keepalived
[root@alexis-01 ~]# ps aux|grep keep
root 9372 0.0 0.1 122980 1412 ? Ss 11:59 0:00 /usr/sbin/keepalived -D
root 9373 0.1 0.3 133944 3368 ? S 11:59 0:00 /usr/sbin/keepalived -D
root 9374 0.0 0.2 133812 2636 ? S 11:59 0:00 /usr/sbin/keepalived -D
root 9381 0.0 0.0 112724 988 pts/1 R+ 12:00 0:00 grep --color=auto keep
3、因为之前设定的虚拟 ip 和现在的 虚拟 ip 冲突,因此先关闭原先的 虚拟 ip
[root@alexis-01 ~]# systemctl stop keepalived
[root@alexis-01 ~]# ip add
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: ens33: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:f2 brd ff:ff:ff:ff:ff:ff
inet 192.168.194.130/24 brd 192.168.194.255 scope global noprefixroute ens33
valid_lft forever preferred_lft forever
inet 192.168.194.150/24 brd 192.168.194.255 scope global secondary noprefixroute ens33:0
valid_lft forever preferred_lft forever
inet6 fe80::c905:5e78:b916:41da/64 scope link noprefixroute
valid_lft forever preferred_lft forever
3: ens37: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:fc brd ff:ff:ff:ff:ff:ff
inet 192.168.100.1/24 brd 192.168.100.255 scope global noprefixroute ens37
valid_lft forever preferred_lft forever
inet6 fe80::f41:9da7:d8e3:10ba/64 scope link noprefixroute
valid_lft forever preferred_lft forever
4: ens38: <BROADCAST,MULTICAST,UP,LOWER_UP> mtu 1500 qdisc pfifo_fast state UP group default qlen 1000
link/ether 00:0c:29:24:ea:06 brd ff:ff:ff:ff:ff:ff
inet 192.168.174.100/24 brd 192.168.174.255 scope global noprefixroute ens38
valid_lft forever preferred_lft forever
inet6 fe80::d106:93d1:7e89:8102/64 scope link noprefixroute
valid_lft forever preferred_lft forever
192.168.194.200 已经停了
4、ipvsadm 也没有了规则
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
5、启动 keepalived,dir 上查看 ipvsadm 规则
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
-> 192.168.194.133:80 Route 100 0 0
6、关闭 rs2 的 nginx,查看现象
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
-> 192.168.194.133:80 Route 100 0 0
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
-> 192.168.194.133:80 Route 100 0 0
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
-> 192.168.194.133:80 Route 100 0 0
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
关闭 rs2 后:keepalived 会自动将宕机的 rs 踢除
7、重启 rs2 上的 nginx,可以再重新加回来
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
[root@alexis-01 ~]# ipvsadm -ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
-> RemoteAddress:Port Forward Weight ActiveConn InActConn
TCP 192.168.194.200:80 wlc
-> 192.168.194.132:80 Route 100 0 0
-> 192.168.194.133:80 Route 100 0 0
8、注意事项
配置keepalived + lvs
在两台rs上要执行lvs_rs.sh脚本
在dir上只要执行 echo 1 > /proc/sys/net/ipv4/ip_forward 即可
9、浏览器访问 192.168.194.200