LVS 机制与调度算法(详细)

简介: 转载:https://blog.csdn.net/moonpure/article/details/52839132LVS之一:三种工作模式的优缺点比较(NAT/TUN/DR)一、Virtual server via NAT(VS-NAT)优点:集群中的物理服务器可以使用任何支持TCP/IP操作系统,物理服务器可以分配Internet的保留私有地址,只有负载均衡器需要一个合法的IP地址。

转载:https://blog.csdn.net/moonpure/article/details/52839132

LVS之一:三种工作模式的优缺点比较(NAT/TUN/DR)

一、Virtual server via NAT(VS-NAT)

优点:集群中的物理服务器可以使用任何支持TCP/IP操作系统,物理服务器可以分配Internet的保留私有地址,只有负载均衡器需要一个合法的IP地址。

缺点:扩展性有限。当服务器节点(普通PC服务器)数据增长到20个或更多时,负载均衡器将成为整个系统的瓶颈,因为所有的请求包和应答包都需要经过负载均衡器再生。假使TCP包的平均长度是536字节的话,平均包再生延迟时间大约为60us(在Pentium处理器上计算的,采用更快的处理器将使得这个延迟时间变短),负载均衡器的最大容许能力为8.93M/s,假定每台物理服务器的平台容许能力为400K/s来计算,负责均衡器能为22台物理服务器计算。

解决办法:即使是是负载均衡器成为整个系统的瓶颈,如果是这样也有两种方法来解决它。一种是混合处理,另一种是采用Virtual Server via IP tunneling或Virtual Server via direct routing。如果采用混合处理的方法,将需要许多同属单一的RR DNS域。你采用Virtual Server via IP tunneling或Virtual Server via direct routing以获得更好的可扩展性。也可以嵌套使用负载均衡器,在最前端的是VS-Tunneling或VS-Drouting的负载均衡器,然后后面采用VS-NAT的负载均衡器。

二、Virtual server via IP tunneling(VS-TUN)

我们发现,许多Internet服务(例如WEB服务器)的请求包很短小,而应答包通常很大。

优点:负载均衡器只负责将请求包分发给物理服务器,而物理服务器将应答包直接发给用户。所以,负载均衡器能处理很巨大的请求量,这种方式,一台负载均衡能为超过100台的物理服务器服务,负载均衡器不再是系统的瓶颈。使用VS-TUN方式,如果你的负载均衡器拥有100M的全双工网卡的话,就能使得整个Virtual Server能达到1G的吞吐量。

不足:但是,这种方式需要所有的服务器支持"IP Tunneling"(IP Encapsulation)协议,我仅在Linux系统上实现了这个,如果你能让其它操作系统支持,还在探索之中。

三、Virtual Server via Direct Routing(VS-DR)

优点:和VS-TUN一样,负载均衡器也只是分发请求,应答包通过单独的路由方法返回给客户端。与VS-TUN相比,VS-DR这种实现方式不需要隧道结构,因此可以使用大多数操作系统做为物理服务器,其中包括:Linux 2.0.36、2.2.9、2.2.10、2.2.12;Solaris 2.5.1、2.6、2.7;FreeBSD 3.1、3.2、3.3;NT4.0无需打补丁;IRIX 6.5;HPUX11等。

不足:要求负载均衡器的网卡必须与物理网卡在一个物理段上

img_e558fe1fc3cebfe87c2cf5af4abecad7.jpe

LVS之二:负载均衡调度算法

前面的文章介绍了LVS的三种模式:NAT、TUN、DR,那这三种模式下,如果进行负载均衡调度计算呢?这就涉及到新的知识点:负载均衡调度算法

目前LVS主要有三种请求转发方式和10种调度算法。根据请求转发方式的不同,所构架集群的网络拓扑、安装方式、性能表现也各不相同。用LVS主要可以架构三种形式的集群,分别是LVS/NAT、LVS/TUN和LVS/DR,可以根据需要选择其中一种。在选定转发方式的情况下,采用哪种调度算法将决定整个负载均衡的性能表现,不同的算法适用于不同的应用场合,有时可能需要针对特殊场合,自行设计调度算法。LVS的算法是逐渐丰富起来的,最初LVS只提供4种调度算法,后来发展到以下10种。

一、静态调度算法:

1.1 轮叫调度(Round Robin,RR)

调度器通过“轮叫"调度算法将外部请求按顺序轮流分配到集群中的真实服务器上,它均等地对待每一台服务器,而不管服务器上实际的连接数和系统负载。

1.2 加权轮叫(Weighted Round Robin,WRR)

调度器通过“加权轮叫"调度算法根据真实服务器的不同处理能力来调度访问请求。这样可以保证处理能力强的服务器能处理更多的访问流量。调度器可以自动问询真实服务器的负载情况,并动态地调整其权值。

1.3 目标地址散列(Destination Hashing,DH)

“目标地址散列"调度算法根据请求的目标IP地址,作为散列键(Hash Key)从静态分配的散列表找出对应的服务器,若该服务器是可用的且未超载,将请求发送到该服务器,否则返回空。主要用于缓存服务器的场景。

1.4 源地址散列(Source Hashing,SH)

“源地址散列"调度算法根据请求的源IP地址,作为散列键(Hash Key)从静态分配的散列表找出对应的服务器,若该服务器是可用的且未超载,将请求发送到该服务器,否则返回空。在没有使用session共享的又需要保存session的环境下(如电子商务网站),建议使用此算法。

二、动态调度算法:

2.1 最少链接(Least Connections,LC)

调度器通过“最少连接"调度算法动态地将网络请求调度到已建立的链接数最少的服务器上。如果集群系统的真实服务器具有相近的系统性能,采用“最小连接"调度算法可以较好地均衡负载。其具体算法为:

active*256+inactive

然后挑选服务器中上述值最小者分配新连接。

2.2 加权最少链接(Weighted Least Connections,WLC)

在集群系统中的服务器性能差异较大的情况下,调度器采用“加权最少链接"调度算法优化负载均衡性能,具有较高权值的服务器将承受较大比例的活动连接负载。调度器可以自动问询真实服务器的负载情况,并动态地调整其权值。WLC为LVS的默认调度算法。其具体算法为:

(active*256+inactive)/weight

然后挑选服务器根据上述方法计算数字最小者分配新连接。

2.3 基于局部性的最少链接(Locality-Based Least Connections,LBLC)

“基于局部性的最少链接"调度算法是针对目标IP地址的负载均衡,目前主要用于Cache集群系统。该算法根据请求的目标IP地址找出该目标IP地址最近使用的服务器,若该服务器是可用的且没有超载,将请求发送到该服务器;若服务器不存在,或者该服务器超载且有服务器处于一半的工作负载,则用“最少链接"的原则选出一个可用的服务器,将请求发送到该服务器。

类似于DH算法,不同的是,其结合了DH算法和LC算法的优势。

2.4 带复制的基于局部性最少链接(Locality-Based Least Connections with Replication,LBLCR)

“带复制的基于局部性最少链接"调度算法也是针对目标IP地址的负载均衡,目前主要用于Cache集群系统。它与LBLC算法的不同之处是它要维护从一个目标IP地址到一组服务器的映射,而LBLC算法维护从一个目标IP地址到一台服务器的映射。该算法根据请求的目标IP地址找出该目标IP地址对应的服务器组,按“最小连接"原则从服务器组中选出一台服务器,若服务器没有超载,将请求发送到该服务器;若服务器超载,则按“最小连接"原则从这个集群中选出一台服务器,将该服务器加入到服务器组中,将请求发送到该服务器。同时,当该服务器组有一段时间没有被修改,将最忙的服务器从服务器组中删除,以降低复制的程度。

2.5 最短的期望的延迟(Shortest Expected Delay Scheduling,SED)

“最短的期望的延迟”是基于WLC算法的,只是其计算方法不同。具体算法如下:

(active+1)*256/weight

2.6 最少队列(Never Queue Scheduling,NQ)

无需队列。如果有台 realserver的连接数=0就直接分配过去,不需要在进行SED运算。如果没有服务器连接数为空闲,则使用SED算法。

了解这些算法原理能够在特定的应用场合选择最适合的调度算法,从而尽可能地保持Real Server的最佳利用性。

LVS之三:ipvsadm常用管理命令介绍

LVS全称为Linux Virtual Server,工作在ISO模型中的第四层,由于其工作在第四层,因此与iptables类似,必须工作在内核空间上。因此lvs与iptables一样,是直接工作在内核中的,叫ipvs,主流的linux发行版默认都已经集成了ipvs,因此用户只需安装一个管理工具ipvsadm即可。

查看内核是否已经集成ipvs:

[root@lvs ~]# grep -i "ip_vs" /boot/config-2.6.32-358.18.1.el6.x86_64

CONFIG_IP_VS=m

CONFIG_IP_VS_IPV6=y

# CONFIG_IP_VS_DEBUG is not set

CONFIG_IP_VS_TAB_BITS=12

CONFIG_IP_VS_PROTO_TCP=y

CONFIG_IP_VS_PROTO_UDP=y

CONFIG_IP_VS_PROTO_AH_ESP=y

CONFIG_IP_VS_PROTO_ESP=y

CONFIG_IP_VS_PROTO_AH=y

CONFIG_IP_VS_PROTO_SCTP=y

CONFIG_IP_VS_RR=m

CONFIG_IP_VS_WRR=m

CONFIG_IP_VS_LC=m

CONFIG_IP_VS_WLC=m

CONFIG_IP_VS_LBLC=m

CONFIG_IP_VS_LBLCR=m

CONFIG_IP_VS_DH=m

CONFIG_IP_VS_SH=m

CONFIG_IP_VS_SED=m

CONFIG_IP_VS_NQ=m

CONFIG_IP_VS_FTP=m

一、安装ipvsadm:

[root@lvs ~]# yum -y install ipvsadm

二、ipvsadm基本介绍:

2.1 集群服务管理类命令:

2.1.1 添加集群:

# ipvs -A -t|u|f service-address [-s scheduler]

选项说明:

-t: TCP协议的集群

-u: UDP协议的集群

service-address:     IP:PORT

-f: FWM: 防火墙标记

service-address: Mark Number

示例:

[root@lvs ~]# ipvsadm -A -t 172.16.1.253:80 -s wlc

2.1.2 修改集群:

# ipvs -E -t|u|f service-address [-s scheduler]

示例:

[root@lvs ~]# ipvsadm -E -t 172.16.1.253:80-s wrr

2.1.3 删除集群:

# ipvsadm -D -t|u|f service-address

示例:

[root@lvs ~]# ipvsadm -D -t 172.16.1.253:80

2.2 管理集群中的RealServer:

2.2.1 添加RS:

# ipvsadm -a -t|u|f service-address -r server-address [-g|i|m] [-w weight]

选项说明:

-t|u|f service-address:事先定义好的某集群服务

-r server-address: 某RS的地址,在NAT模型中,可使用IP:PORT实现端口映射;

[-g|i|m]: LVS类型

-g: DR

-i: TUN

-m: NAT

[-w weight]: 定义服务器权重

示例:

[root@lvs ~]# ipvsadm -a -t 172.16.1.253:80 -r 172.16.1.101 –g -w 5

[root@lvs ~]# ipvsadm -a -t 172.16.1.253:80 -r 172.16.1.102 –g -w 10

2.2.2 修改RS:

# ipvsadm -e -t|u|f service-address -r server-address [-g|i|m] [-w weight]

示例:

[root@lvs ~]# ipvsadm-e-t 172.16.1.253:80 -r 172.16.1.101 –g -w3

2.2.3 删除RS:

# ipvsadm -d -t|u|f service-address -r server-address

示例:

[root@lvs ~]# ipvsadm -d -t 172.16.1.253:80 -r 172.16.1.101

2.3 查看类:

# ipvsadm -L|l [options]

常用选项[options]如下:

-n: 数字格式显示主机地址和端口

--stats:统计数据

--rate: 速率

--timeout: 显示tcp、tcpfin和udp的会话超时时长

-c: 显示当前的ipvs连接状况

2.4 其他管理类:

2.4.1 删除所有集群服务:

# ipvsadm -C

该命令与iptables的-F功能类似,执行后会清除所有规则。

2.4.2 保存规则

保存规则至默认配置文件:

# service ipvsadm save

保存规则至指定文件:

# ipvsadm -S > /path/to/somefile

示例:

[root@lvs ~]# service ipvsadm save

ipvsadm: Saving IPVS table to /etc/sysconfig/ipvsadm:      [确定]

2.4.3 载入保存在文件中的规则

# ipvsadm -R < /path/form/somefile

三、lvs的其他注意事项:

关于时间同步:各节点间的时间偏差不大于1s,建议使用统一的ntp服务器进行更新时间;

DR模型中的VIP的MAC广播问题:

在DR模型中,由于每个节点均要配置VIP,因此存在VIP的MAC广播问题,在现在的linux内核中,都提供了相应kernel 参数对MAC广播进行管理,具体如下:

arp_ignore: 定义接收到ARP请求时的响应级别;

0:只要本地配置的有相应地址,就给予响应;

    1:仅在请求的目标地址配置在到达的接口上的时候,才给予响应;DR模型使用

arp_announce:定义将自己地址向外通告时的通告级别;

0:将本地任何接口上的任何地址向外通告;

1:试图仅向目标网络通告与其网络匹配的地址;

    2:仅向与本地接口上地址匹配的网络进行通告;DR模型使用

LVS之四:DR模型实现

试验拓扑:

img_43e6e72b8743ed5f396f7f50d8c3e1d0.jpe

img_4638b405f63316c8d863206a37b2f93b.jpe

然后启动各虚拟机,按上述拓扑规划配置好IP地址。

1.2 配置路由器(linux):

使用iptables实现NAT配置较为简单,主要如下:

1.2.1 开启转发功能:

[root@router ~]# echo 1 >/proc/sys/net/ipv4/ip_forward

如果需永久修改,则需要修改sysctl.conf文件。并使用sysctl -p 使其立即生效。

1.2.2 配置iptables:

清除所有规则:

[root@router ~]# iptables –F

配置NAT功能:

[root@router ~]# iptables -t nat -A POSTROUTING -o eth0 -s 172.16.1.0/24 -j SNAT --to 192.168.8.254

[root@router ~]# iptables -t nat -A PREROUTING -d 192.168.8.254 -p tcp --dport 80 -j DNAT --to-destination 172.16.1.253:80

##为了方便使用ssh客户端连接,我还将lvs集群中各服务器的22端口映射到了不同端口,具体如下:

[root@router ~]# iptables -t nat -A PREROUTING -d 192.168.8.254 -p tcp --dport2022-j DNAT --to-destination172.16.1.252:22

[root@router ~]# iptables -t nat -A PREROUTING -d 192.168.8.254 -p tcp --dport2122-j DNAT --to-destination172.16.1.101:22

[root@router ~]# iptables -t nat -A PREROUTING -d 192.168.8.254 -p tcp --dport2222-j DNAT --to-destination172.16.1.102:22

配置转发功能:

[root@router ~]# iptables -A FORWARD -p ip -j ACCEPT

保存规则:

[root@router ~]# service iptables save

此时,Director和RealServer都已可以正常访问外网。

1.3 配置本地windows,添加路由使其能访问lvs集群:

由于试验中物理主机(windows)和试验用路由器(linux)的默认网关指向的是真实的路由器,因此物理主机(windows)是无法访问lvs集群网络的,为了能让物理机(windows)访问到集群网络方便后面测试,因此需要添加路由,命令如下:

C:\windows\system32>route add 172.16.1.0/24 192.168.8.254

操作完成!

二、配置Director

2.1 启用转发:

[root@lvs ~]# echo 1 > /proc/sys/net/ipv4/ip_forward

如果想永久生效,则需要修改/etc/sysctl.conf文件。

2.2 配置VIP和路由:

配置路由:

[root@lvs ~]# route add -host 172.16.1.253 dev eth0:0

配置VIP:

[root@lvs ~]# ifconfig eth0:1 172.16.1.253 netmask 255.255.255.255 up

2.3 清除原有iptables和ipvs规则:

[root@lvs ~]# iptables -F

[root@lvs ~]# iptables -Z

[root@lvs ~]# ipvsadm -C

2.4 配置集群服务:

[root@lvs ~]# ipvsadm -A -t 172.16.1.253:80 -s wlc

2.5 添加RS至集群服务:

[root@lvs ~]# ipvsadm -a -t 172.16.1.253:80 -r 172.16.1.101 -g

[root@lvs ~]# ipvsadm -a -t 172.16.1.253:80 -r 172.16.1.102 -g

2.6 将上述过程编写为一个服务脚本,直接在Director上实现开机启动:

#!/bin/bash

#

# LVS script for VS/DR

# chkconfig: - 90 10

#

. /etc/rc.d/init.d/functions

#

VIP=172.16.1.253

DIP=172.16.1.252

RIP1=172.16.1.101

RIP2=172.16.1.102

PORT=80

RSWEIGHT1=5

RSWEIGHT2=5

#

case "$1" in

start)

/sbin/ifconfig eth0:1 $VIP broadcast $VIP netmask 255.255.255.255 up

/sbin/route add -host $VIP dev eth0:1

# Since this is the Director we must be able to forward packets

echo 1 > /proc/sys/net/ipv4/ip_forward

# Clear all iptables rules.

/sbin/iptables -F

# Reset iptables counters.

/sbin/iptables -Z

# Clear all ipvsadm rules/services.

/sbin/ipvsadm -C

# Add an IP virtual service for VIP 192.168.0.219 port 80

# In this recipe, we will use the round-robin scheduling method.

# In production, however, you should use a weighted, dynamic scheduling method.

/sbin/ipvsadm -A -t $VIP:80 -s wlc

# Now direct packets for this VIP to

# the real server IP (RIP) inside the cluster

/sbin/ipvsadm -a -t $VIP:80 -r $RIP1 -g -w $RSWEIGHT1

/sbin/ipvsadm -a -t $VIP:80 -r $RIP2 -g -w $RSWEIGHT2

/bin/touch /var/lock/subsys/ipvsadm &> /dev/null

;;

stop)

# Stop forwarding packets

echo 0 > /proc/sys/net/ipv4/ip_forward

# Reset ipvsadm

/sbin/ipvsadm -C

# Bring down the VIP interface

/sbin/ifconfig eth0:0 down

/sbin/route del $VIP

/bin/rm -f /var/lock/subsys/ipvsadm

echo "ipvs is stopped..."

;;

status)

if [ ! -e /var/lock/subsys/ipvsadm ]; then

echo "ipvsadm is stopped ..."

else

echo "ipvs is running ..."

ipvsadm -L -n

fi

;;

*)

echo "Usage: $0 {start|stop|status}"

;;

esac

将上述内容保存在/etc/init.d/lvs-director文件中,然后添加到服务:

[root@lvs ~]# chmod +x /etc/init.d/lvs-director

[root@lvs ~]# chkconfig --add lvs-director

[root@lvs ~]# chkconfig lvs-director on

[root@lvs ~]# /etc/init.d/lvs-director start

[root@lvs ~]# /etc/init.d/lvs-director status

ipvs is running ...

IP Virtual Server version 1.2.1 (size=4096)

Prot LocalAddress:Port Scheduler Flags

-> RemoteAddress:Port           Forward Weight ActiveConn InActConn

TCP  172.16.1.253:80 wlc

-> 172.16.1.101:80              Route   5      0          0

-> 172.16.1.102:80              Route   5      0          0

三、配置RS:

3.1 配置ARP广播:

[root@rs1 ~]# echo 1 > /proc/sys/net/ipv4/conf/lo/arp_ignore

[root@rs1 ~]# echo 2 > /proc/sys/net/ipv4/conf/lo/arp_announce

[root@rs1 ~]# echo 1 > /proc/sys/net/ipv4/conf/all/arp_ignore

[root@rs1 ~]# echo 2 > /proc/sys/net/ipv4/conf/all/arp_announce

3.2 配置VIP和路由:

[root@rs1 ~]# ifconfig lo:0 172.16.1.253 netmask 255.255.255.255 up

[root@rs1 ~]# route add -host 172.16.1.253 dev lo:0

3.3 编写为脚本:

#!/bin/bash

#

# Script to start LVS DR real server.

# chkconfig: - 90 10

# description: LVS DR real server

#

.  /etc/rc.d/init.d/functions

VIP=172.16.1.253

host=`/bin/hostname`

case "$1" in

start)

# Start LVS-DR real server on this machine.

/sbin/ifconfig lo down

/sbin/ifconfig lo up

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

/sbin/ifconfig lo:0 $VIP broadcast $VIP netmask 255.255.255.255 up

/sbin/route add -host $VIP dev lo:0

;;

stop)

# Stop LVS-DR real server loopback device(s).

/sbin/ifconfig lo:0 down

echo 0 > /proc/sys/net/ipv4/conf/lo/arp_ignore

echo 0 > /proc/sys/net/ipv4/conf/lo/arp_announce

echo 0 > /proc/sys/net/ipv4/conf/all/arp_ignore

echo 0 > /proc/sys/net/ipv4/conf/all/arp_announce

;;

status)

# Status of LVS-DR real server.

islothere=`/sbin/ifconfig lo:0 | grep $VIP`

isrothere=`netstat -rn | grep "lo:0" | grep $VIP`

if [ ! "$islothere" -o ! "isrothere" ];then

# Either the route or the lo:0 device

# not found.

echo "LVS-DR real server Stopped."

else

echo "LVS-DR real server Running."

fi

;;

*)

# Invalid entry.

echo "$0: Usage: $0 {start|status|stop}"

exit 1

;;

esac

保存至/etc/init.d/lvs-rs,并赋予执行权限,然后添加为开机启动:

[root@rs1~]# chmod +x /etc/init.d/lvs-rs

[root@rs1 ~]# chkconfig --add lvs-rs

[root@rs1 ~]# chkconfig lvs-rs on

[root@rs1 ~]# /etc/init.d/lvs-rs start

3.4 在RS2上采用相同的配置即可

至此就全部完成了lvs的DR模型配置。

4 测试LVS集群

4.1 配置web服务器:

4.1.1 为rs1节点添加web主页:

[root@rs1 ~]# service httpd start

正在启动 httpd:httpd: apr_sockaddr_info_get() failed for rs1

httpd: Could not reliably determine the server's fully qualified domain name, using 127.0.0.1 for ServerName

[确定]

[root@rs1 ~]# echo "This is RS1..." >/var/www/html/index.html

4.1.2 为rs2节点添加web主页:

[root@rs2 ~]# echo "This is RS2..." >/var/www/html/index.html

4.2 访问测试:

访问时观察ipvs状态:

Every 1.0s: ipvsadm -L -n                                                                        Tue Oct  8 19:58:42 2013

IP Virtual Server version 1.2.1 (size=4096)

Prot LocalAddress:Port Scheduler Flags

-> RemoteAddress:Port           Forward Weight ActiveConn InActConn

TCP  172.16.1.253:80 wlc

-> 172.16.1.101:80              Route   5     2          8

-> 172.16.1.102:80              Route   5     1          8

LVS之五:使用脚本实现RealServer的健康检查

上文部署的DR模型中,当一台RS宕机时,ipvs是不会自动踢出该RS服务器的,我这里使用一个脚本实现对RS的监控检查。

一、需求分析:

脚本要能判断RS运行情况;

当RS的web服务不能访问时,将其从lvs集群中踢出;而当RS重新上线时,再将其加入lvs集群;

定时检查(死循环或cron计划任务);

对RS的下线和上线做日志记录。

二、web健康检查命令:

使用curl能简单的实现对web应用可用性进行监控:

curl命令选项:

--cacert CA证书 (SSL)

--capath CA目录 (made using c_rehash) to verify peer against (SSL)

--compressed 要求返回是压缩的形势 (using deflate or gzip)

--connect-timeout 设置最大请求时间

-H/--header 自定义头信息传递给服务器

-i/--include 输出时包括protocol头信息

-I/--head 只显示文档信息

--interface 使用指定网络接口/地址

-s/--silent静音模式。不输出任何东西

-u/--user 设置服务器的用户和密码

-p/--proxytunnel 使用HTTP代理

三、具体实现:

#!/bin/bash

#

VIP=192.168.8.254

CPORT=80

##使用数组RS定义所有RS服务器

RS=("172.16.1.101" "172.16.1.102")

#定义RS状态,后面引用

declare -a RSSTATUS

#定义权重

RW=("5" "5")

RPORT=80

#集群类型为DR

TYPE=g

CHKLOOP=3

#监控日志

LOG=/var/log/ipvsmonitor.log

#

#addrs函数在RS重新上线时将其添加到集群

addrs() {

ipvsadm -a -t $VIP:$CPORT -r $1:$RPORT -$TYPE -w $2

[ $? -eq 0 ] && return 0 || return 1

}

#delrs函数在RS下线时将其从集群中删除

delrs() {

ipvsadm -d -t $VIP:$CPORT -r $1:$RPORT

[ $? -eq 0 ] && return 0 || return 1

}

#checkrs检查RS状态,如果上次均为离线状态,则判定其为离线

checkrs() {

local I=1

while [ $I -le $CHKLOOP ]; do

if curl --connect-timeout 1http://$1&> /dev/null; then

return 0

fi

let I++

done

return 1

}

#初始化RS状态函数

initstatus() {

local I

local COUNT=0;

for I in ${RS[*]}; do

if ipvsadm -L -n | grep "$I:$RPORT" && > /dev/null ; then

RSSTATUS[$COUNT]=1

else

RSSTATUS[$COUNT]=0

fi

let COUNT++

done

}

#执行初始化RS状态检查函数

initstatus


#死循环

while :; do

let COUNT=0

for I in ${RS[*]}; do

if checkrs $I; then

if [ ${RSSTATUS[$COUNT]} -eq 0 ]; then

addrs $I ${RW[$COUNT]}

[ $? -eq 0 ] && RSSTATUS[$COUNT]=1 && echo "`date +'%F %H:%M:%S'`, $I is back." >> $LOG

fi

else

if [ ${RSSTATUS[$COUNT]} -eq 1 ]; then

delrs $I

[ $? -eq 0 ] && RSSTATUS[$COUNT]=0 && echo "`date +'%F %H:%M:%S'`, $I is gone." >> $LOG

fi

fi

let COUNT++

done

sleep 5

done

LVS之六:使用keepalived实现LVS的DR模式热备

一、说明:

在《LVS之一:三种工作模式的优缺点比较(NAT/TUN/DR)》文章讲述了LVS的三种转发模式对比,我们先就用LVS的DR模式来实现Web应用的负载均衡。为了防止LVS服务器自身的单点故障导致整个Web应用无法提供服务,因此还得利用Keepalived实现lvs的高可用性,keepalived主要使用VRRP协议来保存链路的高可用性。而VRRP(Virtual Router Redundancy Protocol)协议本身是用于实现路由器冗余的协议。

LVS-DR模式的原理如下(借用别人的图):

img_bcbb38b0e792449b37f2087dd569ec47.png

说明:

1、  LVS服务器和WEB服务器必须在同一网段;

2、  多台Web服务器间使用NFS服务器等共享存储存放用户上传附件,以保障数据的一致性(如上传图片)。下文讨论

IP地址规划:

VIP              192.168.18.60

LVS-MASTER     192.168.18.51

LVS-BACKUP     192.168.18.52

NFS   Server       192.168.18.20

MySQL               192.168.18.18

WEB1        192.168.18.61

WEB2        192.168.18.62

三、安装LVS+Keepalived:

1、使用yum在线安装:

[root@lvs1 ~]# yum install ipvsadm  keepalived –y

2、检查安装结果:

[root@lvs1 ~]# rpm -qa |grep ipvsadm

ipvsadm-1.25-10.el6.x86_64

[root@lvs1 ~]# rpm -qa |grep keepalived

keepalived-1.2.7-3.el6.x86_64

3、服务配置:

[root@lvs1 ~]# chkconfig keepalived on   ##设置为开机启动

[root@lvs1 ~]# service keepalived start   ##立即启动keepalived服务

四、配置LVS服务器:

1、  备份配置文件:

[root@lvs1 ~]# cp /etc/keepalived/keepalived.conf /etc/keepalived/keepalived.bak

2、  修改配置文件,具体如下:

原始的配置文件包含了三种模式的配置,而这里我们只需要用到DR模式,因此最终保留配置如下:

[root@lvs1 ~]#  vim /etc/keepalived/keepalived.conf

global_defs {                       ##全局配置部分

#   notification_email {             ##下面几行均为全局通知配置,可以实现出现问题后报警,但功能有限,因此注释掉,并采用Nagios监视lvs运行情况

#       admin@toxingwang.com

#   }

#   notification_email_from master@toxingwang.com

#   smtp_server smtp.exmail.qq.com

#   smtp_connect_timeout 30

router_id LVS_MASTER             ##设置lvs的id,在一个网络内应该是唯一的

}

vrrp_instance VI_1 {            ##设置vrrp组,唯一且同一LVS服务器组要相同

stateMASTER  ##备份LVS服务器设置为BACKUP

interface eth0             # #设置对外服务的接口

virtual_router_id 51        ##设置虚拟路由标识

priority 100                                    #设置优先级,数值越大,优先级越高,backup设置为99,这样就能实现当master宕机后自动将backup变为master,而当原master恢复正常时,则现在的master再次变为backup。

advert_int 1            ##设置同步时间间隔

authentication {         ##设置验证类型和密码,master和buckup一定要设置一样

auth_type PASS

auth_pass 1111

}

virtual_ipaddress {          ##设置VIP,可以多个,每个占一行

192.168.18.60

}

}

virtual_server 192.168.18.60 80 {

delay_loop 6            ##健康检查时间间隔,单位s

lb_algo wrr             ##负载均衡调度算法设置为加权轮叫

lb_kind DR                              ##负载均衡转发规则

nat_mask 255.255.255.0   ##网络掩码,DR模式要保障真是服务器和lvs在同一网段

persistence_timeout 50    ##会话保持时间,单位s

protocol TCP                           ##协议

real_server 192.168.18.61 80 {      ##真实服务器配置,80表示端口

weight 3                              ##权重

TCP_CHECK {                       ##服务器检测方式设置

connect_timeout 5    ##连接超时时间

nb_get_retry 3

delay_before_retry 3

connect_port 80

}

}

real_server 192.168.18.62 80 {

weight 3

TCP_CHECK {

connect_timeout 10

nb_get_retry 3

delay_before_retry 3

connect_port 80

}

}

}

作为高可用的备份lvs服务器配置只需在上述配置中的master修改backup即可,其他保持相同。

3、  分别在两台lvs服务器上重启服务:

[root@lvs1 ~]# service keepalived start

注:由于keepalived配置文件有语法错误也能启动,因此看到启动了lvs服务,不代表配置文件没有错误,如果遇到lvs不能正常转发,及时跟踪日志进行处理。

日志跟踪方法:

1、开两个ssh窗口连接到lvs服务器,第一个窗口运行如下命令:

[root@lvs1 ~]# tail -F /var/log/message

2、第二个窗口重新启动keepalived服务,同时观察窗口1中日志的变化,然后根据日志提示解决即可。

五、WEB服务器IP绑定配置:

在两台WEB服务器安装并配置(非本文重点,不做web安装配置讲解),建立测试网页,先使用实际IP进行访问测试,能正常访问后,进行如下操作:

在前面的文章中介绍DR模式时提到:负载均衡器也只是分发请求,应答包通过单独的路由方法返回给客户端。但实际上客户端访问时,IP都是指向的负载均衡器的ip(也就是LVS的VIP),如何能让真是服务器处理IP头为VIP的请求,这就需要做下面的操作,将VIP绑定到真实服务器的lo网口(回环),为了防止IP广播产生IP冲突,还需关闭IP广播,具体如下:

1、编辑开机启动脚本:

  [root@web1 ~]# vim /etc/init.d/realserver

#!/bin/bash

#chkconfig: 2345 79 20

#description:realserver

SNS_VIP=192.168.18.60

. /etc/rc.d/init.d/functions

case "$1" in

start)

ifconfig lo:0 $SNS_VIP netmask 255.255.255.255 broadcast $SNS_VIP

/sbin/route add -host $SNS_VIP dev lo:0

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

sysctl -p >/dev/null 2>&1

echo "RealServer Start OK"

;;

stop)

ifconfig lo:0 down

route del $SNS_VIP >/dev/null 2>&1

echo "0" >/proc/sys/net/ipv4/conf/lo/arp_ignore

echo "0" >/proc/sys/net/ipv4/conf/lo/arp_announce

echo "0" >/proc/sys/net/ipv4/conf/all/arp_ignore

echo "0" >/proc/sys/net/ipv4/conf/all/arp_announce

echo "RealServer Stoped"

;;

*)

echo "Usage: $0 {start|stop}"

exit 1

esac

exit 0

脚本说明:

arp_ignore: 定义接收到ARP请求时的响应级别;

0:只要本地配置的有相应地址,就给予响应;默认;

1:仅在请求的目标地址配置在到达的接口上的时候,才给予响应;

arp_announce:定义将自己地址向外通告时的通告级别;

0:将本地任何接口上的任何地址向外通告;默认;

1:试图仅向目标网络通告与其网络匹配的地址;

2:仅向与本地接口上地址匹配的网络进行通告;

2、  设置脚本开机启动并立即启动:

[root@web1 ~]# chkconfig realserver on

[root@web1 ~]# service realserver start

RealServer Start OK

3、  检测IP配置:

[root@web1 ~]# ifconfig

eth0      Link encap:Ethernet  HWaddr 00:50:56:B3:54:5A

inet addr:192.168.18.61  Bcast:192.168.18.255  Mask:255.255.255.0

inet6 addr: fe80::250:56ff:feb3:545a/64 Scope:Link

UP BROADCAST RUNNING MULTICAST  MTU:1500  Metric:1

RX packets:98940 errors:4 dropped:4 overruns:0 frame:0

TX packets:82037 errors:0 dropped:0 overruns:0 carrier:0

collisions:0 txqueuelen:1000

RX bytes:23077218 (22.0 MiB)  TX bytes:16043349 (15.3 MiB)

Interrupt:18 Base address:0x2000


lo        Link encap:Local Loopback

inet addr:127.0.0.1  Mask:255.0.0.0

inet6 addr: ::1/128 Scope:Host

UP LOOPBACK RUNNING  MTU:16436  Metric:1

RX packets:300 errors:0 dropped:0 overruns:0 frame:0

TX packets:300 errors:0 dropped:0 overruns:0 carrier:0

collisions:0 txqueuelen:0

RX bytes:528420 (516.0 KiB)  TX bytes:528420 (516.0 KiB)


lo:0      Link encap:Local Loopback

inet addr:192.168.18.60 Mask:255.255.255.255

UP LOOPBACK RUNNING  MTU:16436  Metric:1

4、  测试LVS:

在lvs master服务器上运行如下命令:

[root@lvs1 ~]# watch -n 1 ipvsadm -ln

在多台客户端通过浏览器访问VIP或域名(域名需解析到VIP),看能否获取到正确的页面,且同时观察上述窗口的变化。

img_08fd4d297e4ecde40974f9c26faa4a59.png


从上图(为了方便观察,使用了压力测试)可以看出,访问被正常的分担到了两台后端web服务器 。

六、后继问题探讨:

1、用户新上传的附件存放问题;目前我们采用的是NFS方式解决,但存在单点故障,需要配合其他方式解决。NFS的基本用法请参考《NFS的配置和使用

2、后端数据库高可用性;

3、会话共享和保持问题(Session共享);算法调整为SH可解决,但有RealServer宕机时,其上的session也会丢失。后期将调整为实现共享session。

LVS之七:使用持久连接解决session问题

前面在讨论LVS算法中,SH算法可以实现将同一客户端的请求总是发送给第一次指定的RS,除非该RS出现故障不能再提供服务。其实在LVS集群中,持久连接功能也能在一定时间内,将来自同一个客户端请求派发至此前选定的RS,而且是无关算法的。

持久连接的三种类型:

在基于SSL的加密https协议中,特别需要用到持久连接,因为客户端需要与服务器进行交换证书并协商加密算法等。

如果一个集群中提供了两种服务,持久连接会将同一客户端的所有请求都同步到同一RS。持久连接分三种:

PPC(持久端口连接):将来自于同一个客户端对同一个集群服务的请求,始终定向至此前选定的RS;

PCC(持久客户端连接):将来自于同一个客户端对所有端口的请求,始终定向至此前选定的RS;PCC是把所有端口统统定义为集群服务,一律向RS转发;

PNMPP:持久防火墙标记连接。使用iptables的标记功能,可以实现给多个服务(端口)打上相同的标记,然后在ipvsadm使用-f选项,并使用上述防火墙标记即可将多个服务放到一个LVS集群中。实现过程如下:

# iptables -t mangle -A PREROUTING -d 192.168.8.253 -p tcp --dport 80 -i $INCARD -j MARK --set-mark10

# iptables -t mangle -A PREROUTING -d 192.168.8.253 -p tcp --dport 443 -i $INCARD -j MARK --set-mark10

# ipvsadm -A -f10-s wlc –p 600

持久连接模板查看:

LVS的持久连接又集群的持久连接模板(一个内存缓冲区)提供;该持久连接模板保存着每一个客户端及分配给它的RS的映射关系。使用如下命令可以查看该模板:

[root@lvs ~]#ipvsadm -L -c

IPVS connection entries

pro expire state       source             virtual            destination

TCP 01:56  FIN_WAIT    192.168.8.12:51822 172.16.1.253:http  172.16.1.102:http

TCP 01:57  FIN_WAIT    192.168.8.12:51825 172.16.1.253:http  172.16.1.101:http

TCP 01:56  FIN_WAIT    192.168.8.12:51821 172.16.1.253:http  172.16.1.101:http

TCP 01:42  FIN_WAIT    192.168.8.12:51814 172.16.1.253:http  172.16.1.102:http

TCP 01:57  FIN_WAIT    192.168.8.12:51826 172.16.1.253:http  172.16.1.102:http

TCP 01:57  FIN_WAIT    192.168.8.12:51824 172.16.1.253:http  172.16.1.102:http

TCP 01:56  FIN_WAIT    192.168.8.12:51820 172.16.1.253:http  172.16.1.102:http

TCP 14:58  ESTABLISHED 192.168.8.12:51828 172.16.1.253:http  172.16.1.102:http

TCP 01:55  FIN_WAIT    192.168.8.12:51815 172.16.1.253:http  172.16.1.101:http

TCP 01:56  FIN_WAIT    192.168.8.12:51823 172.16.1.253:http  172.16.1.101:http

TCP 01:57  FIN_WAIT    192.168.8.12:51827 172.16.1.253:http  172.16.1.101:http

配置并启用lvs集群的持久连接:

基本语法:

ipvsadm -A|E ... -p timeout

timeout: 持久连接时长,默认300秒;单位是秒;

在使用《LVS之四:DR模型实现》中的lvs集群,每次刷新客户端时,都会在RS1和RS2上切换。如下图:

img_56ecb1f00e18feae2a453f59cc910910.jpe

我们启用持久连接:

[root@lvs ~]# ipvsadm -L -n

IP Virtual Server version 1.2.1 (size=4096)

Prot LocalAddress:Port Scheduler Flags

-> RemoteAddress:Port           Forward Weight ActiveConn InActConn

TCP  172.16.1.253:80 wlc

-> 172.16.1.101:80              Route   5      0          1

-> 172.16.1.102:80              Route   5      0          2

[root@lvs ~]# ipvsadm -E -t 172.16.1.253:80 -p 600

[root@lvs ~]# ipvsadm -L -n

IP Virtual Server version 1.2.1 (size=4096)

Prot LocalAddress:Port Scheduler Flags

-> RemoteAddress:Port           Forward Weight ActiveConn InActConn

TCP  172.16.1.253:80 wlc persistent 600

-> 172.16.1.101:80              Route   5      0          0

-> 172.16.1.102:80              Route   5      0          1

此时再次刷新客户端,会发现已经不会再改变RS。

[root@lvs ~]# ipvsadm -L --persistent-conn

IP Virtual Server version 1.2.1 (size=4096)

Prot LocalAddress:Port            Weight    PersistConn ActiveConn InActConn

-> RemoteAddress:Port

TCP  172.16.1.253:http wlc persistent 600

-> 172.16.1.101:http            5         0           0          0

->172.16.1.102:http            5         1           0          14

相关实践学习
部署高可用架构
本场景主要介绍如何使用云服务器ECS、负载均衡SLB、云数据库RDS和数据传输服务产品来部署多可用区高可用架构。
负载均衡入门与产品使用指南
负载均衡(Server Load Balancer)是对多台云服务器进行流量分发的负载均衡服务,可以通过流量分发扩展应用系统对外的服务能力,通过消除单点故障提升应用系统的可用性。 本课程主要介绍负载均衡的相关技术以及阿里云负载均衡产品的使用方法。
目录
相关文章
|
算法 Linux 数据处理
《操作系统》—— 处理机调度算法
《操作系统》—— 处理机调度算法
|
6月前
|
缓存 算法 数据管理
基于改进Slime Mold算法的多处理器公平调度
基于改进Slime Mold算法的多处理器公平调度
44 0
|
10天前
|
资源调度 分布式计算 算法
【Hadoop Yarn】Hadoop Yarn 基于优先级的调度算法
【4月更文挑战第7天】【Hadoop Yarn】Hadoop Yarn 基于优先级的调度算法
|
2月前
|
弹性计算 负载均衡 算法
负载均衡调度算法介绍
介绍负载均衡调度算法
81 8
|
7月前
|
资源调度 算法 Java
Java线程常用调度算法与应用
Java线程常用调度算法与应用
94 0
|
4月前
|
算法 调度
进程的调度算法有哪些
进程的调度算法有哪些
|
4月前
|
缓存 负载均衡 算法
xv6(16) 进程二:调度算法
进程二:调度算法
33 0
xv6(16)  进程二:调度算法
|
4月前
|
算法 调度 C语言
操作系统进程调度算法(c语言模拟实现)
操作系统进程调度算法(c语言模拟实现)
137 0
|
4月前
|
算法 调度
磁盘调度算法(OS)
磁盘调度算法(OS)
40 0
|
5月前
|
监控 算法 Java
进程调度的原理和算法探析
本文探讨了进程调度的原理和算法,并提供了全面的概述。进程调度是操作系统中的重要组成部分,用于决定进程的执行顺序和分配CPU时间。我们讨论了优先级调度和时间片轮转调度算法。优先级调度根据进程的优先级确定执行顺序,可以分为抢占式和非抢占式。时间片轮转调度将CPU时间划分为固定大小的时间片,每个进程在一个时间片内执行。合理设置时间片长度能够避免资源浪费和频繁的上下文切换。最短作业优先和最短剩余时间优先是常见的调度算法,通过预估和动态计算进程的执行时间提高系统效率和响应速度。多级反馈队列调度综合了优先级调度和时间片轮转调度的优点,适应不同类型的进程和任务。通过本文的阐述,读者将对进程调度的原理和算法有
204 0
进程调度的原理和算法探析

热门文章

最新文章