纸上得来终觉浅,绝知此事要躬行。
LVS(Linux Virtual Server)是由章文嵩博士发起的一个开源项目,称为Linux虚拟服务器。现在已经是Linux内核标准的一部分,官方网站是http://www.linuxvirtualserver.org。LVS是一个实现负载均衡集群的开源软件项目,架构从逻辑上可分为调度层、服务器集群层和共享存储。通过LVS达到的负载均衡技术和Linux操作系统实现一个高性能高可用的Linux服务器集群,它具有良好的可靠性、可扩展性和可操作性。从而以低廉的成本实现最优的性能。

1. 负载均衡原理
系统运维:可用 –> 标准化 –> 自动化
1.1 工作原理
下图所示就是LVS的基本工作原理:

- (1) 当用户向负载均衡调度器(
Director Server)发起请求,调度器将请求发往至内核空间。 - (2)
PREROUTING链首先会接收到用户请求,判断目标IP确定是本机IP,将数据包发往INPUT链。 - (3)
IPVS是工作在INPUT链上的,当用户请求到达INPUT时,IPVS会将用户请求和自己已定义好的集群服务进行比对,如果用户请求的就是定义的集群服务,那么此时IPVS会强行修改数据包里的目标IP地址及端口,并将新的数据包发往POSTROUTING链。 - (4)
POSTROUTING链接收数据包后发现目标IP地址刚好是自己的后端服务器,那么此时通过选路,将数据包最终发送给后端的服务器。
1.2 工作特点
LVS是工作在TCP/IP的四层模型上,通过修改Netfilter表中的INPUT链来实现的(所有不是服务而是规则),根据客户端请求报文的目标 IP 和 PORT(主要是端口)将其转发至后端主机集群中的某一台主机(根据挑选算法)。
- 原理
- 当用户请求
LVS载均衡调度器的IP地址,在经过PREROUTING链到达INPUT链,如果匹配规则匹配的话,在到达本机内核之后强行将其扔到POSTROUTING链
- 当用户请求
- 规则
- 服务器端口号:集群基于那个
TCP或UDP端口工作 - 服务器 IP 地址:集群中那些机器可以响应用户请求
- 服务器端口号:集群基于那个
- 架构
- 负载均衡调度器(
Director Server) - 服务器集群(
Real Server) - 共享存储(
Shared Storage)
- 负载均衡调度器(
- 术语
DS:前端负载均衡器节点RS:后端真实的工作服务器CIP:访问客户端的 IP 地址VIP:向外部直接面向用户请求,作为用户请求的目标的 IP 地址DIP:主要用于和内部主机通讯的 IP 地址RIP:后端服务器的 IP 地址
- 工具
ipvs:工作在内核Netfilter表中的INPUT链上,且支持TCP、UDP、AH、EST等多种协议ipvsadm:基于ipvs的基础上编写的用户工具,工作在用户空间,用于LVS的管理集群服务
[root@localhost ~]# grep -i -A 10 'IPVS' /boot/config-2.6.32-573.26.1.el6.x86_64
# IPVS传输协议支持负载均衡
CONFIG_IP_VS_PROTO_TCP=y # 基于TCP做负载均衡
CONFIG_IP_VS_PROTO_UDP=y # 基于UDP做负载均衡
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
# IPVS调度器
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
......
2. 负载均衡类型
CDN(分区域缓存) => LB(LVS/Nginx) => HA(LVS/Haproxy) => Cache(Nginx/Vanish/Mechcache) => HTTP(Nginx/Apache) => Database(master/worker)
- LVS-NAT:多目标的 DNAT
- LVS-DR:直接路由实现
- LVS-TUN:采用 IP 隧道的方式
- LVS-FULLNAT:全 NAT 机制,非标准类型,拥有新特性,淘宝二次研发
企业中最常用的是 DR 实现方式,而 NAT 配置上比较简单和方便
2.1 LVS/NAT
重点:对请求报文进行 DNAT 目标地址转换到挑选出的 RS 地址
NAT 模型的实现原理


- (1) 当用户请求到达
Director Server的VIP上,此时请求的数据报文会先到内核空间的PREROUTING链。 此时报文的源 IP为CIP,目标 IP为VIP。 - (2)
PREROUTING检查发现数据包的目标IP是本机,将数据包送至INPUT链。 - (3)
IPVS比对数据包请求的服务是否为集群服务,若是,修改数据包的目标IP地址为后端服务器RIP,然后将数据包发至POSTROUTING链。 此时报文的源 IP为CIP,目标 IP为RIP。 - (4)
POSTROUTING链通过选路,将数据包发送给Real Server。 - (5)
Real Server比对发现目标为自己的IP,开始构建响应报文发回给Director Server。 此时报文的源 IP为RIP,目标 IP为CIP。 - (6)
Director Server在响应客户端前,此时会将源IP地址修改为自己的VIP地址,然后响应给客户端。 此时报文的源 IP为VIP,目标 IP为CIP。
NAT 模型的的特性
- 特点
- 支持端口映射
RS可以使用任意操作系统,包括Windows系统
- 缺陷
- 请求和响应报文都需要经过
DS,高负载场景中,DS易成为性能瓶颈
- 请求和响应报文都需要经过
- 配置
- 负载均衡调度器上维持一个
nat追踪表,用于转发客户端的请求报文给后端真实服务器响应 - 负载均衡调度器通过修改请求报文的目标
IP地址(同时可能会修改目标端口),使用多目标的DNAT实现转发 DS配置两块网卡,分别为公网地址的VIP和私网地址的DIP,并需要使用DNAT和SNAT技术RS和DIP最好使用同网段内的私网地址,而且RS的网关需要指向DIP,不然响应报文不会经过VIP响应用户
- 负载均衡调度器上维持一个
2.2 LVS/DR
重点:将请求报文的目标 MAC 地址设定为挑选出的 RS 的 MAC 地址
DR 方式的实现原理


- (1) 当用户请求到达
Director Server的VIP上,此时请求的数据报文会先到内核空间的PREROUTING链。 此时报文的源 IP为CIP,目标 IP为VIP。 - (2)
PREROUTING检查发现数据包的目标IP是本机,将数据包送至INPUT链。 - (3)
IPVS比对数据包请求的服务是否为集群服务,若是,将请求报文中的源 MAC 地址修改为 DIP 的 MAC 地址,将目标MAC地址修改RIP的MAC地址,然后将数据包发至POSTROUTING链。 此时的源IP和目的IP均未修改,仅修改了源MAC地址为DIP的MAC地址,目标MAC地址为RIP的MAC地址。 - (4) 由于
DS和RS在同一个网络中,所以是通过二层来传输。POSTROUTING链检查目标MAC地址为RIP的MAC地址,那么此时数据包将会发至Real Server。 - (5)
RS发现请求报文的MAC地址是自己的MAC地址,就接收此报文。处理完成之后,将响应报文通过lo接口传送给eth0网卡然后向外发出。 此时的源 IP地址为VIP,目标 IP为CIP。 - (6) 响应报文最终送达至客户端。
DR 模型的的特性
- 特点
- 不支持地址转换,也不支持端口映射
RS可以是大多数常见的操作系统,但不支持Windows系统- 请求报文经由
DS调度,但响应报文一定不能经由DS对用户进行响应 - 客户请求传递给交换机,交换机进行
ARP地址广播,因为交换机只看Mac地址
- 缺陷
RS和DS必须在同一机房中
- 配置
DS配置网卡网卡,分别为eth0的DIP和eth0:0的VIPRSs集群的每个机器也都配置两块网卡,分别为eth0的RIP和lo:0的VIPRS的RIP可以使用私有地址或公网地址,如果使用公网地址通过互联网对RIP进行直接访问RS的VIP和DIP与DS的VIP和RIP必须在同一个物理网络中,VIP必须使用公网地址,DIP、RIP可以使用公网或私网地址;建议DIP、RIP在同一个网段,方便通信。- 因为我们不允许
DS响应用户请求,所以RS的网关绝不允许指向DS的DIP上
攻克的难题
- 难题简述
- 保证前端路由将目标地址为 VIP 的报文统统发给
DS,而不是也配置了VIP的RS
- 保证前端路由将目标地址为 VIP 的报文统统发给
- 【方式一】静态绑定
- 在前端路由器做静态地址路由绑定,将对于
VIP的地址仅路由到DS上 - 如果
DS服务器挂了将无法使用,需要做单点的高可用,如HB - 有可能路由是运营商提供的,所以用户未必有路由操作权限,所以这个方法未必实用
- 在前端路由器做静态地址路由绑定,将对于
- 【方式二】arptables
- 通过
arptables工具修改ARP规则,禁止RS对VIP的请求做请求,不好配置
- 通过
- 【方式三】修改内核
- 内核的参数:
arp_ignore和arp_announce - 因为需要修改内核参数,
RS主机必须为Linux主机 - 修改
RS主机上内核参数将VIP配置在lo接口的别名上,并限制其不能响应对VIP地址解析请求
- 内核的参数:
2.3 LVS/TUN
重点:在原有的 IP 报文外再次封装多一层 IP 首部,内部 IP 首部(源地址为
CIP、目标 IIP 为VIP),外层 IP 首部(源地址为DIP、目标 IP 为RIP)
TUN 模型的实现原理


- (1) 当用户请求到达
Director Server的VIP上,此时请求的数据报文会先到内核空间的PREROUTING链。 此时报文的源 IP为CIP,目标 IP为VIP。 - (2)
PREROUTING检查发现数据包的目标IP是本机,将数据包送至INPUT链。 - (3)
IPVS比对数据包请求的服务是否为集群服务,若是,在请求报文的首部再次封装一层IP报文,然后发至POSTROUTING链。此时源 IP为DIP,目标 IP为RIP。 - (4)
POSTROUTING链根据最新封装的IP报文,将数据包发至RS(因为在外层封装多了一层 IP 首部,所以可以理解为此时通过隧道传输)。 此时源 IP为DIP,目标 IP为RIP。 - (5)
RS接收到报文后发现是自己的IP地址,就将报文接收下来,拆除掉最外层的IP后,会发现里面还有一层IP首部,而且目标是自己的lo接口VIP,那么此时RS开始处理此请求,处理完成之后,通过lo接口送给eth0网卡,然后向外传递。 此时的源 IP地址为VIP,目标 IP为CIP。 - (6) 响应报文最终送达至客户端。
TUN 模型的的特性
- 特点
- 请求报文必须经由
DS调度,但响应报文必须不能经由DS传送 RS的集群服务可以位于不同的区域,如一个在北京另一个在上海
- 请求报文必须经由
- 缺陷
- 不支持端口映射
RS的操作系统必须支持隧道功能- 对报文的再次封装,可能导致超过最大的传输单元而再次分片
- 配置
VIP、DIP、RIP全为公网 IP 地RS的网关的不能指向DIP,因为响应报文不需要经过DS传送给客户端
攻克的难题
- 【难题】对请求报文的再次封装,可能导致超过
MTU的最大值(一般为1500),导致再次分片 - 【方式一】设备需要支持超过
MTU的请求传输报文 - 【方式二】在
DS限制请求报文长度为1400左右
2.4 LVS/FULLNAT
重点:DS 通过同时修改请求报文的目标地址和源地址进行转发
FULLNAT 模型的实现原理
- 淘宝 FULLNAT 项目地址
- FULLNAT 是淘宝吴佳明(普空)在
NAT基础上搞得,很大简化了LVS的配置和部署 - 百度的
LVS叫BVS(Baidu Virtual Server),在LVS基础上增加了L3 Though和SYN Porxy,类似FULLNAT CentOS不支持FULLNAT,为了方便的实现多机房部署(NAT和DR不支持,TUN支持但比较复杂),需要在淘宝中找到内核编译安装内核


- (1) 客户端发送请求报文给
Director Server的物理网络接口VIP此时请求的数据报文会先到内核空间的PREROUTING链。此时报文的源 IP为CIP,目标 IP为VIP。 - (2)
PREROUTING检查发现数据包的目标IP是本机,将数据包送至INPUT链。 - (3)
IPVS比对数据包请求的服务是否为集群服务,若是,修改数据包的源IP地址为DIP,目标IP地址为后端服务器RIP,然后将数据包发至POSTROUTING链。此时报文的源 IP为DIP,目标 IP为RIP。 - (4)
POSTROUTING链通过选路,将数据包发送给Real Server。 - (5)
Real Server比对发现目标为自己的IP,开始构建响应报文发回给Director Server。 此时报文的源 IP为RIP,目标 IP为DIP。 - (6)
Director Server在响应客户端前,此时会将源IP地址修改为自己的VIP地址,目标IP地址修改为客户端的地址CIP,然后响应给客户端。 此时报文的源 IP为VIP,目标 IP为CIP。
FULLNAT 模型的特性
- 特点
- 支持端口映射机制
- 跨 vlan:可以在多个地方跨域部署
- connection 复用:使
LVS能有类似f5的连接复用的功能 - syn_proxy:可以在
keepalived配置文件中针对每一个服务分别设置打开或关闭
- 配置
VIP是公网地址,RIP和DIP是私网地址,二者无须在同一网络中RS接收到的请求报文的源地址为DIP,因此要响应给DIP,也不需将RS的网关指向DS,能到达即可- 请求报文和响应报文都必须经由
DS,有必要的话,需要做HB高可用 - RS 可以使用任意操作系统,包括
Windows系统
攻克的难题
- 【难题】
RS无法获得用户的真实IP地址 - 【解决】淘宝通过叫
TOA的方式解决,主要原理是将客户端IP地址放到了TCP Option里面带给了后端RS服务器,当RS收到后保存在socket的结构体里并通过toa内核模块hook的getname函数,这样当用户调用getname获取远端地址时,返回的是保存在socket的TCP Option的IP地址。百度的BVS是通过叫ttm模块实现的,其实现方式跟toa基本一样,只是没有开源。

3. 实现 session 保存
我们都知道HTTP服务是一种无状态的,那么用户请求服务器时,怎么标记用户呢?那么这就要使用到session保存的技术了,通过session服务器可以知道这个用户对应哪个资源,实现精准的定位。以下就是session保持的常见方法:
- session 绑定
source ip hash:SNAT多用户同时使用一个公网IP地址;lvs、nginx、haproxy;IP级别cookie hash:自实现的;lvs不行,nginx、haproxy能够使用;进程级别
- session 集群
- 需要进行大量的
session同步工作,断电就尴尬了
- 需要进行大量的
- session 服务器
- 使
session持久化,即使关机了也可以使用,存储在redis的键值数据库 - 网络通信肯定有延迟
- 单点故障,瓶颈 => LB =>
HB
- 使
4. 十种调度算法
静态方法:仅根据算法本身进行调度;起点公平
- RR:
round robin,轮调- 轮询算法假设所有的服务器处理请求的能力都是一样的,调度器会将所有的请求平均分配给每个
RS服务器,非常均衡地分发下去。
- 轮询算法假设所有的服务器处理请求的能力都是一样的,调度器会将所有的请求平均分配给每个
- WRR:
weighted rr,加权轮调- 这种算法会考虑每台服务器的性能,并给每台服务器添加要给权值权重的取值范围
0 – 100。权值越高的服务器,处理的请求越多。
- 这种算法会考虑每台服务器的性能,并给每台服务器添加要给权值权重的取值范围
- SH:
source hash,源地址哈希- 实现
session保持的机制;将来自于同一个 IP 的请求始终调度至同一RS LVS内部会维持一个哈希表,记录源地址、调度的RealServer和计时器,辞旧迎新防止打满
- 实现
- DH:
destination hash,目标地址哈希- 将对同一个目标的请求始终发往同一个
RS - 内网中用户通过同一个防火墙出去的会从同一个防火墙回来,保持用户追踪
- 将对同一个目标的请求始终发往同一个
动态方法:根据算法及各RS的当前负载状态进行调度,Overhead小者获胜;起点公平,结果公平
- LC:
Least Connection,最少连接数Overhead=Active(活动链接数)*256+Inactive(非活动链接数)- 最少连接算法会根据后端
RS的连接数来决定把请求的分配,比如RS1连接数比RS2连接数少,那么请求就优先发给RS1这台服务器。
- WLC:
Weighted LC,加权最少连接数Overhead=(Active*256+Inactive)/weight- 这种算法会考虑每台服务器的性能,并给每台服务器添加要给权值权重的取值范围
0 – 100。权值越高的服务器,处理的请求越多。
- SED:
Shortest Expection Delay,最短期望延迟Overhead=(Active+1)*256/weight
- NQ:
Never Queue,永不排队SED算法的改进,类似于sed+sed的结合
- LBLC:
Locality-Based LC,基于本地最少连接调度算法,即动态的DH算法- 正向代理情形下的
cache server调度;基于本地最少连接调度算法;运营商常使用 - 这个算法是请求数据包的目标
IP地址的一种调度算法,该算法先根据请求的目标IP地址寻找最近的该目标IP地址所有使用的服务器,如果这台服务器依然可用,并且有能力处理该请求,调度器会尽量选择相同的服务器,否则会继续选择其它可行的服务器。
- 正向代理情形下的
- LBLCR:
Locality-Based Least-Connection with Replication,带复制功能的LBLC算法- 记录的不是要给目标
IP与一台服务器之间的连接记录,它会维护一个目标IP到一组服务器之间的映射关系,防止单点服务器负载过高。
- 记录的不是要给目标
5. 负载均衡比较
LVS
- 优势
- 抗负载能力强:工作方式的逻辑是非常之简单
- 工作稳定:因为工作在内核中,所有十分稳定
- 无流量:工作在四层仅做请求分发之用,没有流量
- 支持所有应用:工作在四层,所以可以对几乎所有应用做负载均衡,包括
http、数据库、聊天室等等
- 劣势
- 配置性低:需要通过命令工具进行配置,有一定的学习成本
Nginx
- 优势
- 针对
HTTP应用本身来做分流策略:比如针对域名、目录结构等 - 网络的依赖较小:理论上只要
ping得通,网页访问正常 - 安装和配置比较简单:通过配置文件进行配置,且配置文件书写相对简单
- 承受很高负载且稳定:处理所有流量所以受限于机器 IO 和配置
- 有故障监测机制:比如根据服务器处理网页返回的状态码、超时等等
- 支持对请求的异步处理:可以帮助节点服务器减轻负载
- 针对
- 劣势
- 仅支持
http和email
- 仅支持