提升服务器响应能力的方法html
scale on 在原有服务器的基础上进行升级或者直接换一台新的性能更高的服务器。前端
scale out 横向扩展,将多台服务器并发向外响应客户端的请求。优势:成本低,扩展架构比较简单。linux
集群(Cluster),通俗地讲就是按照某种组织方式将几台电脑组织起来完成某种特定任务的这样一种架构。web
三种集群类型:算法
LB,Load Balancing 负载均衡:在必定程度上可以实现高可用的目的。vim
HA,High Availability 高可用:实时在线,可以及时响应客户端请求,企业应用要求达到windows
7*24小时,99.999%时间在线。后端
HP,High Performance 高性能 提供大量超级运算能力的集群。服务器
LB 负载均衡架构:cookie
Director(dispatcher):负责接收客户端请求,并将请求按照某种算法分发到后台真正提供服务的服务器上。既能够基于硬件(F5)来实现,也能够基于软件来实现。基于软件实现的又分为四层交换:基于IP地址和端口号组合起来对服务作重定向(LVS)。七层交换:一般指的是反向代理(proxy),例如:squid。
LVS:Linux Virtual Server
相似于iptables的架构,在内核中有一段代码用于实时监听数据包来源的请求,当数据包到达端口时作一次重定向。这一系列的工做必须在内核中实现。在内核中实现数据包请求处理的代码叫作ipvs。ipvs仅仅提供了功能框架,还须要本身手动定义是数据对哪一个服务的请求,
而这种定义须要经过写规则来实现,写规则的工具就称为ipvsadm。
应用场景
高吞吐量(higher throughput)
冗余 (redundancy)
适应性 (adaptability)
LVS负载均衡架构
Virtual IP(VIP)address:Director用来向客户端提供服务的IP地址
Real IP (RIP) address:集群节点(后台真正提供服务的服务器)所使用的IP地址
Director's IP (DIP) address:Director用来和D/RIP 进行联系的地址
Client computer's IP (CIP) address:公网IP,客户端使用的IP。
根据前端Director和后台Real Server的通讯方式将LVS分为三类:
Network Address Translation(LVS-NAT)
目标地址转换 全部客户端的请求都被Director根据访问请求和算法被定向到后台的Real Server 上。
数据包地址转换过程:
S:CIP D:VIP------->Director------>S:CIP D:RIP------>Real Server------>
----->S:RIP D:CIP----->Director----->S:VIP D:CIP
Director和Real Server必须在同一个网段中;
通常状况下,RIP是私有地址,只用于集群内部节点间通讯;
Director 会响应全部的请求在客户端和Real Server之间,所承担的负载较大;
全部的Real IP 网关必须指向DIP以响应客户端请求;
Director能够重映射网络端口,即前端使用标准端口,后端可使用非标准端口;
后台的Real Server可使用任何操做系统;
Director可能会成为系统瓶颈。
Director routing (LVS-DR )
直接路由 客户端请求通过Director,Real Server直接回应客户端
数据包地址转换过程:
S:CIP D:VIP----->Director--->S:CIP D:RIP -----> Real Server---> S:VIP D:CIP
Real Server 上必须配置VIP切须要隐藏起来,只有在响应客户端请求时才使用VIP做为源地址,除此以外并不使用此VIP。
集群节点和Director必须在同一个网络中;
RIP不要求为私有地址;
Director仅处理全部进来的请求;
Real Server 不能以DIP做为网关,而是以公网上的某台路由器做为网关;
Director 不能再使用端口重映射;
大多数操做系统能够被用来做为Real Server,windows除外;
LVS-DR模式能够处理比LVS-NAT更多的请求。
实际生产环境中最经常使用的一种方式,优势:
RIP 为公网地址,管理员能够远程链接Real Server来查看工做状态;
一旦Director 宕机,能够经过修改DNS记录将A记录指向RIP 继续向外提供服务;
IP tunneling (LVS-TUN )
与DR的网络结构同样,但Director和Real Server能够在不一样的网络当中,能够实现异地容灾的功能。DIP----->VIP 基于隧道来传输,在数据包外层额外封装了S:DIP D :RIP 的地址。
Director和Real Server 必须在同一个物理网络中;
RIP必定不能是私有地址;
Director只负责处理进来的数据包;
Real Server直接将数据包返回给客户端,因此Real Server默认网关不能是DIP,必须是公网上某个路由器的地址;
Director不能作端口重映射;
只有支持隧道协议的操做系统才能做为Real Server。
分发时所采用的算法
固定调度算法:按照某种既定的算法,不考虑实时的链接数予以分配。
Round-robin(RR)轮询:当新请求到达时候,从服务列表中选择一个Real Server,将请求重定向给这台Real Server。
Weighted round-robin(WRR)加权轮询:给每台Real Server分配一个权重/位列,权重越大,分到的请求数越多。
Destination hashing (DH)目标散列:来自于同一个IP地址的请求都被重定向到同一台Real Server上(保证目标地址不变)。
Source hashing(SH)源地址散列:Director必须确保响应的数据包必须经过请求数据包所通过的路由器或者防火墙(保证原地址不变)。
动态调度算法:经过检查服务器上当前链接的活动状态来从新决定下一步调度方式该如何实现。
Lease Connection (LC) 最少链接 哪个Real Server上的链接数少就将下一个链接请求定向到那台Real Server上去。 【算法:链接数=活动链接数*256+非活动链接数】
Weight Least-Connection(WLC) 加权最少链接 在最少链接的基础上给每台Real Server分配一个权重。 【算法:链接数=(活动链接数*256+非活动链接数)÷权重】 一种比较理想的算法。
Shortest Expected Delay (SED) 最短时间望延迟 再也不考虑非活动链接数
【算法:链接数=(活动链接数+1) *256 ÷权重】
Never Queue (NQ) 永不排队算法,对SED的改进,当新请求过来的时候不只要取决于SED算法所获得的值,还要取决于Real Server上是否有活动链接。
Locality-Based Least-Connection (LBLC) 基于本地状态的最少链接,在DH算法的基础上还要考虑服务器上的活动链接数。
Locality-Based Least-Connection with Replication Scheduling (LBLCR) 带复制的基于本地的最少链接 LBLC算法的改进
下面咱们就来作一个基于LVS-NAT的负载均衡实验:
实验环境搭建:
Director :VIP192.168.0.127 桥接
DIP192.168.10.1 仅主机
Real Server 1:RIP 192.168.10.2 仅主机 网关指向:192.168.10.1
Real Server 2:RIP 192.168.10.3 仅主机 网关指向:192.168.10.1
Client:192.168.0.1 物理机
每台Real Server上分别安装有http服务。咱们这里为了演示效果,每一个http服务的页面不一样。
Real Server 1
[root@station39 html]# ifconfig eth0 192.168.10.2
[root@station39 html]# route add default gw 192.168.10.1
Real Server 2
[root@station26 html]# ifconfig eth0 192.168.10.3
[root@station26 html]# route add default gw 192.168.10.1
Director :
[root@server27 ~]# ifconfig eth1 192.168.10.1
打开内核路由功能
[root@server27 ~]# echo 1 > /proc/sys/net/ipv4/ip_forward
确保永久有效:
[root@server27 ~]# vim /etc/sysctl.conf
# Controls IP packet forwarding
net.ipv4.ip_forward = 1
[root@server27 ~]# sysctl -p
net.ipv4.ip_forward = 1
net.ipv4.conf.default.rp_filter = 1
net.ipv4.conf.default.accept_source_route = 0
kernel.sysrq = 0
kernel.core_uses_pid = 1
net.ipv4.tcp_syncookies = 1
kernel.msgmnb = 65536
kernel.msgmax = 65536
kernel.shmmax = 4294967295
kernel.shmall = 268435456
OK,准备工做已经就绪,下面开始实验的关键步骤:
[root@server27 ~]# yum install ipvsadm -y
使用步骤:1.定义服务 2 .为服务定义Real Server
[root@server27 ~]# ipvsadm -A -t 192.168.0.127:80 -s rr
[root@server27 ~]# 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.127:80 rr
[root@server27 ~]# ipvsadm -a -t 192.168.0.127:80 -r 192.168.10.2 -m -w 2
[root@server27 ~]# ipvsadm -a -t 192.168.0.127:80 -r 192.168.10.3 -m -w 5
-g, --gatewaying Use gatewaying (direct routing). This is the default.
-i, --ipip Use ipip encapsulation (tunneling).
-m, --masquerading Use masquerading (network access transla-tion, or NAT).
PS:在这里设定的权重对于RR算法来讲并无什么意义,咱们只是为后面的实验而设定的。
[root@server27 ~]# 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.127:80 rr
-> 192.168.10.3:80 Masq 5 0 16
-> 192.168.10.2:80 Masq 2 0 15
此时,咱们使用物理机访问192.168.0.127就会发现页面交替变化,这是由RR算法的特性决定的。
咱们改变为WRR算法试试:
[root@server27 ~]# ipvsadm -E -t 192.168.0.127:80 -s wrr
[root@server27 ~]# 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.127:80 wrr
-> 192.168.10.3:80 Masq 5 0 86
-> 192.168.10.2:80 Masq 2 0 43
改变为LBLC算法试试:
LBLC:基于本地状态的最少链接,在DH算法的基础上还要考虑服务器上的活动链接数。
[root@server27 ~]# ipvsadm -E -t 192.168.0.127:80 -s lblc
[root@server27 ~]# 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.127:80 lblc
-> 192.168.10.3:80 Masq 5 0 112
-> 192.168.10.2:80 Masq 2 0 41
此时不管客户端怎么刷新,访问页面都不会改变。
保存规则:
ipvsadm -S >>/etc/sysconfig/ipvs-config == ipvsadm-save
ipvsadm -R < /etc/sysconfig/ipvs-config == ipvsadm-restore
Director routing (LVS-DR )
PS:Director分发到Real Server的过程当中,数据包的源地址和目标地址都没有发生改变,Director仅仅是将目标mac地址转换成某台Real Server的mac地址,源mac地址改成Director内网网卡的mac地址。
两个技术难题
1 Real Server要避免对客户端发来的对VIP的arp地址解析请求;
解决方法
1) 修改内核的两个参数:arp_announce, arp_ignore。
arp_announce :定义不一样级别:当ARP请求经过某个端口进来是否利用这个接口来回应。
0 - (default) Use any local address, configured on any interface.
利用本地的任何地址,无论配置在哪一个接口上去响应ARP请求;
1 - Try to avoid local addresses that are not in the target's subnet for this interface.
避免使用另一个接口上的mac地址去响应ARP请求;
2 - Always use the best local address for this target.
尽量使用可以匹配到ARP请求的最佳地址。
arp_ignore:当ARP请求发过来后发现本身正是请求的地址是否响应;
0 - (default): reply for any local target IP address, configured on any interface
利用本地的任何地址,无论配置在哪一个接口上去响应ARP请求;
1 - reply only if the target IP address is local address configured on the incoming
interface.
哪一个接口上接受ARP请求,就从哪一个端口上回应。
PS:对linux来讲IP地址属于系统而不属于某个接口。
2) Red Hat 提供了arptables工具,利用arp防火墙也能够实现。
2 当Real Server内网网卡响应客户端请求时,要以VIP做为源地址,不能以RIP做为源地址。
解决方法
添加一条路由:route add -host 192.168.0.127 dev lo:0使客户端访问VIP,就让VIP来响应客户端。这样避免了使用RIP做为源地址。
Director:VIP:响应客户端请求;
DIP:与RIP彼此间实现arp解析,并将客户端的请求转发给Real Server。
实验环境搭建:
Director :eth0:0 VIP192.168.0.127
eth0 DIP192.168.0.10 桥接
Real Server 1: eth0 RIP 192.168.0.12 桥接
lo:0 VIP 192.168.0.127
Real Server 2: eth0 RIP 192.168.0.13 桥接
lo:0 VIP 192.168.0.127
Client:192.168.0.1 物理机
Real Server 1
[root@station39 ~]# vim /etc/sysctl.conf
net.ipv4.conf.lo.arp_ignore = 1
net.ipv4.conf.all.arp_ignore = 1
net.ipv4.conf.lo.arp_announce = 2
net.ipv4.conf.all.arp_announce = 2
[root@station39 ~]# sysctl -p
[root@station39 ~]# ifconfig eth0 192.168.0.12/24
[root@station39 ~]# ifconfig lo:0 192.168.0.127 broadcast 192.168.0.127 netmask 255.255.255.255
[root@station39 ~]# route add -host 192.168.0.127 dev lo:0
Real Server 2
[root@station26 ~]# vim /etc/sysctl.conf
net.ipv4.conf.lo.arp_ignore = 1
net.ipv4.conf.all.arp_ignore = 1
net.ipv4.conf.lo.arp_announce = 2
net.ipv4.conf.all.arp_announce = 2
[root@station26 ~]# sysctl -p
[root@station26 ~]# ifconfig eth0 192.168.0.13/24
[root@station26 ~]# ifconfig lo:0 192.168.0.127 broadcast 192.168.0.127 netmask 255.255.255.255
[root@station26 ~]# route add -host 192.168.0.127 dev lo:0
Director
[root@server27 ~]# ifconfig eth0 192.168.0.10/24
[root@server27 ~]# ifconfig eth0:0 192.168.0.127 broadcast 192.168.0.127 netmask 255.255.255.255
[root@server27 ~]# route add -host 192.168.0.127 dev eth0:0
[root@server27 ~]# echo 1 > /proc/sys/net/ipv4/ip_forward
[root@server27 ~]# ipvsadm -C
[root@server27 ~]# ipvsadm -A -t 192.168.0.127:80 -s wlc
[root@server27 ~]# ipvsadm -a -t 192.168.0.127:80 -r 192.168.0.12 -g -w 5
[root@server27 ~]# ipvsadm -a -t 192.168.0.127:80 -r 192.168.0.13 -g -w 8
[root@server27 ~]# 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.127:80 wlc
-> 192.168.0.13:80 Route 8 0 18
-> 192.168.0.12:80 Route 5 0 11
PS:若是要保持访问的页面一致,咱们能够另外准备一台服务器专门用来存放网页文件,而后经过NFS共享的方式挂载到Real Server的网页目录下,就能够实现真正的负载均衡了。
实现持久链接:
[root@server27 ~]# ipvsadm -E -t 192.168.0.127:80 -s wlc -p 3600
[root@server27 ~]# 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.127:80 wlc persistent 3600
-> 192.168.0.13:80 Route 8 0 62
-> 192.168.0.12:80 Route 5 0 0
此时,你会发现不管访问页面怎么刷新都不会再改变,这就是LVS持久性。
LVS Persistence 持久性
尽管咱们选择了LVS的分发方法,可是大多时候咱们要保证返回给客户端的全部响应请求必须来自于同一台Real Server,这里咱们就要用到LVS Persistence(持久性)。
当使用SSL会话的时候,咱们经常指望只交换一次密钥就能够创建永久链接,所以,LVS持久性在SSL会话中常常被用到。
当使用LVS持久性的时候,Director在内部使用一个链接根据记录称之为“持久链接模板”来确保全部来自同一个客户端的请求被分发到同一台Real Server上。
LVS 持久性类型:PCC PPC PNMP 混合类型。
Persistent client connections (PCC), cause all services a client is accessing to persist. (Also called zero port connections.)
来自同一客户端全部服务的请求都被重定向到同一台Real Server上,以IP地址为准。
PCC是一个虚拟服务没有端口号(或者端口号为0),以"-p" 来标识服务。
缺陷:定向全部服务,指望访问不一样的Real Server没法实现。
假设一个用户在访问购物网站时同时使用HTTP(80)和HTTPS(443)两种协议,就须要这样定义:
ipvsadm -A -t 192.168.0.220:0 -s rr -p
ipvsadm -a -t 192.168.0.220.3:0 -r 192.168.10.11 -m
ipvsadm -a -t 192.168.0.220:0 -r 192.168.10.11 -m
Persistent port connections (PPC), which cause a single service to persist.
来自同一服务的请求都被重定向到同一台Real Server上,以端口号为准。
例如:client---->LVS(80,22)------>RS1 client----->LVS(23)----->RS2
缺陷:指望访问不一样的端口到同一台RS上,没法实现。
Persistent Netfilter Marked Packet persistence, which causes packets that have been marked with the iptables utility to persist.
根据iptables 的规则,将对于某类服务/几个不一样端口的访问定义为一类。
先对某一特定类型的数据包打上标记,而后再将基于某一类标记的服务送到后台的Real Server上去,后台的Real Server 并不识别这些标记。
PS:在LVS-NAT的环境下作这个实验,因为前边的DR模型使用了网卡别名,因此并不适合这个实验。
[root@server27 ~]# iptables -t mangle -A PREROUTING -i eth0 -d 192.168.0.127 -p tcp --dport 80 -j MARK --set-mark 2
[root@server27 ~]# ipvsadm -A -f 2 -s wlc -p 3600
[root@server27 ~]# ipvsadm -a -f 2 -r 192.168.10.2 -m -w 2
[root@server27 ~]# ipvsadm -a -f 2 -r 192.168.10.3 -m -w 5
将持久和防火墙标记结合起来就可以实现端口姻亲功能,只要是来自某一客户端的对某一特定服务(须要不一样的端口)的访问都定义到同一台Real Server上去。
假设这样一种场景:一个用户在访问购物网站时同时使用HTTP(80)和HTTPS(443)两种协议,咱们须要将其定义到同一台Real Server上,而其余的服务不受限制,咱们能够这样作:
实验基于LVS-NAT的环境。
先作一个自签名的证书
Real Server 1:
[root@station39 ~]# cd /etc/pki/tls/certs/
[root@station39 ~]# cd /etc/pki/tls/certs/
[root@station39 certs]# make httpd.pem
[root@station39 certs]# mv httpd.pem /etc/httpd/
[root@station39 httpd]# yum install mod_ssl -y
[root@station39 httpd]# cd conf.d/
[root@station39 conf.d]# vim ssl.conf
SSLCertificateFile /etc/httpd/httpd.pem //** line 112
SSLCertificateKeyFile /etc/httpd/httpd.pem //** line 119
重启httpd 服务。
[root@station39 ~]# vim /etc/hosts
192.168.10.2 web1.a.com web1
Real Server 2 :
[root@station26 ~]# yum install mod_ssl -y
[root@station26 certs]# cd /etc/httpd
[root@station26 httpd]# make -C /etc/pki/tls/certs httpd.pem
[root@station26 httpd]# mv /etc/pki/tls/certs/httpd.pem ./
[root@station26 httpd]# cd conf.d/
[root@station26 conf.d]# vim ssl.conf
SSLCertificateFile /etc/httpd/httpd.pem //** line 112
SSLCertificateKeyFile /etc/httpd/httpd.pem //** line 119
重启httpd 服务。
[root@station26 ~]# vim /etc/hosts
192.168.10.3 web2.a.com web2
Director:
[root@server27 ~]# iptables -t mangle -A PREROUTING -i eth0 -d 192.168.0.127 -p tcp --dport 80 -j MARK --set-mark 5
[root@server27 ~]# iptables -t mangle -A PREROUTING -i eth0 -d 192.168.0.127 -p tcp --dport 443 -j MARK --set-mark 5
[root@server27 ~]# ipvsadm -A -f 5 -s wlc -p
[root@server27 ~]# ipvsadm -a -f 5 -r 192.168.10.2 -m -w 2
[root@server27 ~]# ipvsadm -a -f 5 -r 192.168.10.3 -m -w 5
OK,修改windows客户端的C:\WINDOWS\system32\drivers\etc\hosts 文件,添加两条名称解析记录:
192.168.0.127 web1.a.com
192.168.0.127 web2.a.com
此时物理机访问192.168.0.127不管是http仍是https 服务都会被定义到同一台Real Server上去。
这里咱们是为了演示实验的效果,使用的不一样的证书,不一样的页面。真实的生产环境中要求这些必须是一致的。
FTP connections (FTP connections require careful handling due to the complex nature of FTP connections).
PS:指定一个范围,将范围内的端口打上标记。而后使VSFTPD在被动模式下再也不使用随机端口,而是使用范围内的随机端口,从而实现FTP的负载均衡。
1 Limiting the port range for passive connections, you must also configure the VSFTP server to use a matching port range:
vim /etc/vsftpd.conf:
pasv_min_port=10000
pasv_max_port=20000
2 You must also control the address that the server displays to the client for passive FTP connections. In a NAT routed LVS system, add the following line to /etc/vsftpd.conf to override the real server IP address to the VIP, which is what the client sees upon connection. For example:
pasv_address=n.n.n.n
3 iptables定义端口姻亲:
iptables -t mangle -A PREROUTING -p tcp -d n.n.n.n/32 --dport 21 -j MARK --set-mark 21
iptables -t mangle -A PREROUTING -p tcp -d n.n.n.n/32 --dport 10000:20000 -j MARK --set-mark 21
Expired persistence, which is used internally by the Director to expire connection tracking entries when the persistent connection template expires.