一.基础知识

1.LVS 全称 Linux Virtual Server,是 Linux 内核层实现的高性能、高可用的负载均衡集群技术,由章文嵩博士开发,目前是 Linux 内核的标准模块之一。它的核心作用是将前端的请求流量分发到后端多台真实服务器(Real Server)上,从而提升服务的并发处理能力和可用性。

2.lsv集群类型

lvs-nat: 修改请求报文的目标IP,多目标IP的DNAT

lvs-dr: 操纵封装新的MAC地址

lvs-tun: 在原请求IP报文之外新加一个IP首部

lvs-fullnat: 修改请求报文的源和目标IP

二.NAT 模式

1.lsv-nat

本质是多目标IP的DNAT,通过将请求报文中的目标地址和目标端口修改为某挑出的RS的RIP和PORT实现转发

RIP和DIP应在同一个IP网络,且应使用私网地址;RS的网关要指向DIP

请求报文和响应报文都必须经由Director转发,Director易于成为系统瓶颈

支持端口映射,可修改请求报文的目标PORT

VS必须是Linux系统,RS可以是任意OS系统

2.NAT模式的实验环境配置

配置策略

在调度机VSnode上进行配置:

[root@VSnode ~]# echo "net.ipv4.ip_forward=1" > /etc/sysctl.d/ip_forward.conf
[root@VSnode ~]# yum install ipvsadm -y   #下载调度策略生成工具
[root@VSnode ~]# ipvsadm -A -t 172.25.254.100:80 -s rr
[root@VSnode ~]# ipvsadm -a -t 172.25.254.100:80 -r 192.168.0.10:80 -m
[root@VSnode ~]# ipvsadm -a -t 172.25.254.100:80 -r 192.168.0.20:80 -m
[root@VSnode ~]# ipvsadm -Ln
IP Virtual Server version 1.2.1 (size=4096)
Prot LocalAddress:Port Scheduler Flags
  -> RemoteAddress:Port           Forward Weight ActiveConn InActConn
TCP  172.25.254.100:80 rr
  -> 192.168.0.10:80              Masq    1      0          0         
  -> 192.168.0.20:80              Masq    1      0          0     

测试一下:

更改权重:

三.部署DR模式集群案例

环境设定

对各主机的配置如下

1.client
 

[root@client ~]# vim /etc/NetworkManager/system-connections/eth0.nmconnection
[connection]
id=eth0
type=ethernet
interface-name=eth0
 
[ipv4]
method=manual
address1=172.25.254.99/24,172.25.254.100
dns=8.8.8.8;


[root@client ~]# nmcli connection reload
[root@client ~]# nmcli connection up eth0 
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/4)
[root@client ~]#  route  -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         172.25.254.100  0.0.0.0         UG    100    0        0 eth0
172.25.254.0    0.0.0.0         255.255.255.0   U     100    0        0 eth0

2.vsnode

[root@vsnode ~]#  vim /etc/NetworkManager/system-connections/eth0.nmconnection
[connection]
id=eth0
type=ethernet
interface-name=eth0
 
 
[ipv4]
method=manual
address1=192.168.0.50/24,192.168.0.100
[root@vsnode ~]#  vim /etc/NetworkManager/system-connections/eth0.nmconnection
[root@vsnode ~]# cd  /etc/NetworkManager/system-connections/
[root@vsnode system-connections]# cp -p eth0.nmconnection lo.nmconnection
[root@vsnode system-connections]# vim lo.nmconnection
[connection]
id=lo
type=loopback
interface-name=lo
 
[ipv4]
method=manual
address1=127.0.0.1/8
address2=192.168.0.200/32
[root@vsnode system-connections]# nmcli connection reload
[root@vsnode system-connections]# nmcli connection up eth0
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/5)
[root@vsnode system-connections]# nmcli connection up  lo
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/6)



[root@vsnode system-connections]# route  -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.100   0.0.0.0         UG    100    0        0 eth0
127.0.0.0       0.0.0.0         255.0.0.0       U     30     0        0 lo
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 eth0
[root@vsnode system-connections]# 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
    inet 192.168.0.200/32 scope global 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 mq state UP group default qlen 1000
    link/ether 00:0c:29:8f:9d:1e brd ff:ff:ff:ff:ff:ff
    altname enp3s0
    altname ens160
    inet 192.168.0.50/24 brd 192.168.0.255 scope global noprefixroute eth0
       valid_lft forever preferred_lft forever
    inet6 fe80::dcb1:9de4:80da:6c63/64 scope link noprefixroute 
       valid_lft forever preferred_lft forever


 

3.router

[root@router ~]# echo net.ipv4.ip_forward=1 >> /etc/sysctl.conf   #开启内核路由功能
[root@router ~]# iptables -t nat -A POSTROUTING -o eth1 -j SNAT --to-source 192.168.0.100
[root@router ~]# iptables -t nat -A POSTROUTING -o eth0 -j SNAT --to-source 172.25.254.100

4.RS1

[root@RS1 ~]# nmcli connection modify eth0 ipv4.gateway 192.168.0.100
[root@RS1 ~]# nmcli connection reload
[root@RS1 ~]# nmcli connection up eth0
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/4)
[root@RS1 ~]#  route  -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.100   0.0.0.0         UG    100    0        0 eth0
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 eth0
[root@RS1 ~]# cd /etc/NetworkManager/system-connections/
[root@RS1 system-connections]# cp -p eth0.nmconnection lo.nmconnection
[root@RS1 system-connections]# vim lo.nmconnection
[connection]
id=lo
type=loopback
interface-name=lo
 
[ipv4]
address1=127.0.0.1/8
address2=192.168.0.200/32
method=manual
 
[root@RS1 system-connections]# nmcli connection reload
[root@RS1 system-connections]# nmcli connection up lo
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/6)
#实现arp禁止响应
[root@RS1 system-connections]# echo 1 > /proc/sys/net/ipv4/conf/all/arp_ignore
[root@RS1 system-connections]# echo 1 > /proc/sys/net/ipv4/conf/lo/arp_ignore
[root@RS1 system-connections]# echo 2 > /proc/sys/net/ipv4/conf/lo/arp_announce
[root@RS1 system-connections]# echo 2 > /proc/sys/net/ipv4/conf/all/arp_announce

5.RS2

[root@RS2 ~]# nmcli connection modify eth0 ipv4.gateway 192.168.0.100
[root@RS2 ~]# nmcli connection reload
[root@RS2 ~]# nmcli connection up eth0
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/4)
[root@RS2 ~]# route  -n
Kernel IP routing table
Destination     Gateway         Genmask         Flags Metric Ref    Use Iface
0.0.0.0         192.168.0.100   0.0.0.0         UG    100    0        0 eth0
192.168.0.0     0.0.0.0         255.255.255.0   U     100    0        0 eth0
[root@RS2 ~]# cd /etc/NetworkManager/system-connections/
[root@RS2 system-connections]# cp -p eth0.nmconnection lo.nmconnection
[root@RS2 system-connections]# vim lo.nmconnection
[connection]
id=lo
type=loopback
interface-name=lo
 
[ipv4]
address1=127.0.0.1/8
address2=192.168.0.200/32
method=manual
 
[root@RS2 system-connections]# nmcli connection reload
[root@RS2 system-connections]#  nmcli connection up lo
连接已成功激活(D-Bus 活动路径:/org/freedesktop/NetworkManager/ActiveConnection/6)
[root@RS2 system-connections]# echo 1 > /proc/sys/net/ipv4/conf/all/arp_ignore
[root@RS2 system-connections]# echo 1 > /proc/sys/net/ipv4/conf/lo/arp_ignore
[root@RS2 system-connections]# echo 2 > /proc/sys/net/ipv4/conf/lo/arp_announce
[root@RS2 system-connections]# echo 2 > /proc/sys/net/ipv4/conf/all/arp_announce

配置策略

在调度机vsnode上

[root@vsnode ~]# ipvsadm -A -t 192.168.0.200:80 -s wrr
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:80 -r 192.168.0.10:80 -g
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:80 -r 192.168.0.20:80 -g
[root@vsnode ~]# 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.0.200:80 wrr
  -> 192.168.0.10:80              Route   1      0          0         
  -> 192.168.0.20:80              Route   1      0          0   

测试

[root@client ~]# for N in {1..6};do curl 192.168.0.200;done
RS2 - 192.168.0.20
RS1 - 192.168.0.10
RS2 - 192.168.0.20
RS1 - 192.168.0.10
RS2 - 192.168.0.20
RS1 - 192.168.0.10

四.轮询规则中可能会遇到的错误

以http和https为例,当我们在RS中同时开放80和443端口,那么默认控制是分开轮询的,这样我们就出现了一个轮询错乱的问题

当第一次访问80被轮询到RS1后下次访问443仍然可能会被轮询到RS1上

问题呈现

需要在服务器RS1和RS2上配置https服务

[root@RS1 system-connections]# yum install mod_ssl -y
[root@RS1 system-connections]# systemctl restart httpd

在vsnode上配置策略:

[root@vsnode ~]# ipvsadm -A -t 192.168.0.200:80 -s rr
[root@vsnode ~]# ipvsadm -A -t 192.168.0.200:443 -s rr
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:80 -r 192.168.0.10:80 -g
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:80 -r 192.168.0.20:80 -g
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:443 -r 192.168.0.10:80 -g
[root@vsnode ~]# ipvsadm -a -t 192.168.0.200:443 -r 192.168.0.20:80 -g
[root@vsnode ~]# 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.0.200:80 rr
  -> 192.168.0.10:80              Route   1      0          0         
  -> 192.168.0.20:80              Route   1      0          0         
TCP  192.168.0.200:443 rr
  -> 192.168.0.10:443             Route   1      0          0         
  -> 192.168.0.20:443             Route   1      0          0      

测试

[root@client ~]# curl  http://192.168.0.200;curl -k https://192.168.0.200
RS2 - 192.168.0.20
RS2 - 192.168.0.20

防火墙标记解决轮询调度问题

基本原理:防火墙标记通过在数据包上标记特定标识(如连接标记或会话标记),使流量能够被识别并分配到不同的服务器或路径上,从而实现负载均衡。

具体实现方法:

在vsnode上:

[root@vsnode ~]# ipvsadm -A -f 6666 -s rr
[root@vsnode ~]# ipvsadm  -a -f 6666 -r 192.168.0.10 -g
[root@vsnode ~]# ipvsadm  -a -f 6666 -r 192.168.0.20 -g
[root@vsnode ~]# 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.0.200:80 rr
  -> 192.168.0.10:80              Route   1      0          1         
  -> 192.168.0.20:80              Route   1      0          0         
TCP  192.168.0.200:443 rr
  -> 192.168.0.10:443             Route   1      0          0         
  -> 192.168.0.20:443             Route   1      0          0         
FWM  6666 rr
  -> 192.168.0.10:0               Route   1      0          0         
  -> 192.168.0.20:0               Route   1      0          0         

测试:

[root@client ~]# curl  -k https://192.168.0.200
RS1 - 192.168.0.10
[root@client ~]# curl  -k https://192.168.0.200
RS2 - 192.168.0.20
[root@client ~]# curl  -k https://192.168.0.200
RS1 - 192.168.0.10
[root@client ~]# curl  -k https://192.168.0.200;curl 192.168.0.200
RS2 - 192.168.0.20
RS1 - 192.168.0.10

通过防火墙标记解决了只轮询一个服务器的情况

   


 

更多推荐