《构建高性能Web站点》笔记 - 7 集群与负载均衡
集群与负载均衡
负载分配的策略:
1.按业务需要分配。比如“镜像下载”这种应用可以按用户所在地分配一个就近的实际服务器
2.Round Robin依次分配。实现这个策略需要记录上一次分发的去向。在高并发条件下,记录这个东西需要使用锁,因此对吞吐率有影响
3.随机分配。做不到精确地平均分配,但一般情况下还是可以比较平均的
分发请求的手段:
1.前端服务器通过http跳转将请求转发到实际服务器。缺点是用户可能会绕过前端服务器直接访问实际服务器,这样的话负载就不能均衡
2.DNS里一个域名配多个IP
a. DNS服务器一般采取Round Robin策略,但一般也支持其他智能策略;不管怎么样,分配策略的灵活度都比较有限,尤其是当你使用第三方的DNS服务时
b. DNS服务器不会成为性能瓶颈,这是它的最大优点
c. 由于DNS缓存问题,处理故障转移(某IP对应的服务机当机了)不是那么实时
d. 总的来说,DNS负载均衡简单可行,但比较粗放
3.反向代理(第7层负载均衡)
a. 方便实现自己的调度策略,比如可以让好的机器多分担一些任务. Nginx就允许你设置“权重”
b. 反向代理本身要有比较强的性能,否则就会沦为瓶颈。当反向代理的能力到达极限时,后端再添加多少服务器都无济于事
c. 可以用作负载均衡器的反向代理:Nginx, HAProxy
d. 总的来说,反向代理做负载均衡比较灵活、好用,但额外开销比较大,容易成为瓶颈
4.DNAT: (传输层负载均衡)修改TCP数据包的目标IP和端口
a. 调度服务器收到用户发来的数据包后,将目标IP和目标端口改成实际服务器的IP和端口,然后将其转发到内部网络
b. 实际服务器发出应答的数据包会经过调度服务器,调度服务器这时会把源IP/端口改成自己的IP/端口
c. 可见调度服务器必须是实际服务器的网关
d. 这种转发在linux内核中进行,数据不会进入用户态进程,所以额外开销比较弱。如果不考虑负载均衡的话,可以使用内核模块netfilter和命令iptables
e. 如果要实现负载均衡,则要使用的内核模块/命令是ipvs/ipvsadm;通过它们搭建起来的集群系统称作LVS-NAT,它采用的默认均衡策略是Round Robin,同时支持很多其他静态和动态策略
f. DNAT中,调度服务器依然可能成为瓶颈,因为所有的请求/应答都要经过它;调度服务器要有很大的带宽才行
5.直接路由:(第二层负载均衡)修改MAC地址
a. 实际服务器和调度服务器都直接向外网暴露,请求都经过调度服务器,但应答不经过它;当请求/应答的带宽使用量很低时,用这种方案可以获得很好的性能,因为调度服务器不会成为发送应答数据包的瓶颈
b. 调度服务器收到请求报文后将目标MAC地址修改成某台实际服务器的MAC地址,实现转发; 实际服务器处理完请求后将报文直接发给用户
c. 实际服务器怎么可能直接将报文发给用户呢?两者并未预先建立连接啊。这里要使用一个诡计:调度服务器和实际服务器使用同样的VIP,在用户眼里,会以为调度服务器和实际服务器是同一台服务器
d. 在linux中,这种技术叫做lvs-dr
e. 如果调度服务器只配了一台(成为单点),则可以在调度服务器发生故障时立即切换到DNS负载均衡方案,这种切换非常好做,因为实际服务器直接向外网暴露
管理
1.流量监控:可以通过SNMP获得各个实际服务器的流量,以实时调整分发策略
2.故障转移:如果一台实际服务器挂了,要避免请求被分发到它的头上
3.健康探测:调度服务器可以轮询实际服务器的状态以判断它是否健康,比如发送一个http请求,看看应答码是否为200
4.避免单点
5.调度服务器的HA:搞一台备用的调度服务器,它通过Heartbeat对主调度服务器进行心跳检测;一旦发现心跳停止就马上接管