负载均衡与双机热备

目录

负载均衡

一、HTTP重定向实现负载均衡

二、DNS负载均衡

三、反向代理负载均衡

四、负载均衡架构实践

双机热备


负载均衡

负载均衡(Load Balance,简称LB)是一种服务器或网络设备的集群技术。负载均衡将特定的业务(网络服务、网络流量等)分担给多个服务器或网络设备,从而提高了业务处理能力,保证了业务的高可用性。

通常情况下,负载均衡可以分为两种:

  • 请求负载均衡,即将用户的请求均衡地分发到不同的服务器进行处理;

  • 数据负载均衡,即将用户更新的数据分发到不同的存储服务器。

在不同层面会有不同的负载均衡方法,在请求方面,常见的轮询策略包括轮询(随机、顺序、加权顺、性能最优、负载最低等,而在数据方面,通常会使用(一致性)哈希的策略

一、HTTP重定向实现负载均衡

当用户向服务器发起请求时,请求首先被集群调度者截获;调度者根据某种分配策略,选择一台服务器,并将选中的服务器的IP地址封装在HTTP响应消息头部的Location字段中,并将响应消息的状态码设为302,最后将这个响应消息返回给浏览器。

当浏览器收到响应消息后,解析Location字段,并向该URL发起请求,然后指定的服务器处理该用户的请求,最后将结果返回给用户。

在使用HTTP重定向来实现服务器集群负载均衡的过程中,需要一台服务器作为请求调度者。用户的一项操作需要发起两次HTTP请求,一次向调度服务器发送请求,获取后端服务器的IP,第二次向后端服务器发送请求,获取处理结果。

调度服务器收到用户的请求后,究竟选择哪台后端服务器处理请求,这由调度服务器所使用的调度策略决定。

  1. 随机分配策略 当调度服务器收到用户请求后,可以随机决定使用哪台后端服务器,然后将该服务器的IP封装在HTTP响应消息的Location属性中,返回给浏览器即可。

  2. 轮询策略(RR) 调度服务器需要维护一个值,用于记录上次分配的后端服务器的IP。那么当新的请求到来时,调度者将请求依次分配给下一台服务器。

由于轮询策略需要调度者维护一个值用于记录上次分配的服务器IP,因此需要额外的开销;此外,由于这个值属于互斥资源,那么当多个请求同时到来时,为了避免线程的安全问题,因此需要锁定互斥资源,从而降低了性能。而随机分配策略不需要维护额外的值,也就不存在线程安全问题,因此性能比轮询要高。

优缺点分析

采用HTTP重定向来实现服务器集群的负载均衡实现起来较为容易,逻辑比较简单,但缺点也较为明显。

在HTTP重定向方法中,调度服务器只在客户端第一次向网站发起请求的时候起作用。当调度服务器向浏览器返回响应信息后,客户端此后的操作都基于新的URL进行的(也就是后端服务器),此后浏览器就不会与调度服务器产生关系,进而会产生如下几个问题:

  • 由于不同用户的访问时间、访问页面深度有所不同,从而每个用户对各自的后端服务器所造成的压力也不同。而调度服务器在调度时,无法知道当前用户将会对服务器造成多大的压力,因此这种方式无法实现真正意义上的负载均衡,只不过是把请求次数平均分配给每台服务器罢了。

  • 若分配给该用户的后端服务器出现故障,并且如果页面被浏览器缓存,那么当用户再次访问网站时,请求都会发给出现故障的服务器,从而导致访问失败。

二、DNS负载均衡

我们提交的请求不会直接发送给想要访问的网站,而是首先发给域名服务器,它会帮我们把域名解析成IP地址并返回给我们。我们收到IP之后才会向该IP发起请求。

那么,DNS服务器有一个天然的优势,如果一个域名指向了多个IP地址,那么每次进行域名解析时,DNS只要选一个IP返回给用户,就能够实现服务器集群的负载均衡。

一般DNS提供商会提供一些调度策略供我们选择,如随机分配、轮询、根据请求者的地域分配离他最近的服务器。

优缺点分析

优点:

1. 配置简单。服务器集群的调度工作完全由DNS服务器承担,那么我们就可以把精力放在后端服务器上,保证他们的稳定性与吞吐量。而且完全不用担心DNS服务器的性能,即便是使用了轮询策略,它的吞吐率依然卓越。

2. 具有较强了扩展性,你完全可以为一个域名解析较多的IP,而且不用担心性能问题。

缺点:

1. 由于把集群调度权交给了DNS服务器,从而我们没办法随心所欲地控制调度者,没办法定制调度策略。

2. 没办法了解每台服务器的负载情况,因此没办法实现真正意义上的负载均衡。它和HTTP重定向一样,只不过把所有请求平均分配给后端服务器罢了。

3. 为一个域名解析多个IP时,如果是公网的IP,其费用较贵。

4. 当我们发现某一台后端服务器发生故障时,即使我们立即将该服务器从域名解析中去除,但由于DNS服务器会有缓存,该IP仍然会在DNS中保留一段时间,那么就会导致一部分用户无法正常访问网站。这是一个致命的问题!好在这个问题可以用动态DNS来解决。

动态DNS

动态DNS能够让我们通过程序动态修改DNS服务器中的域名解析。从而当我们的监控程序发现某台服务器挂了之后,能立即通知DNS将其删掉。

综上:DNS是一种粗犷的负载均衡方法,一般不推荐使用

三、反向代理负载均衡

反向代理服务器是一个位于实际服务器之前的服务器,所有向我们网站发来的请求都首先要经过反向代理服务器,服务器根据用户的请求要么直接将结果返回给用户,要么将请求交给后端服务器处理,再返回给用户。

用反向代理服务器可以实现静态页面和常用的动态页面的缓存。

我们知道,所有发送给我们网站的请求都首先经过反向代理服务器。那么,反向代理服务器就可以充当服务器集群的调度者,它可以根据当前后端服务器的负载情况,将请求转发给一台合适的服务器,并将处理结果返回给用户。

优点

  1. 隐藏后端服务器

    与HTTP重定向相比,反向代理能够隐藏后端服务器,所有浏览器都不会与后端服务器直接交互,从而能够确保调度者的控制权,提升集群的整体性能。

  2. 故障转移

    与DNS负载均衡相比,反向代理能够更快速地移除故障节点。当监控程序发现某一后端服务器出现故障时,能够及时通知反向代理服务器,并立即将其删除。

  3. 合理分配任务

    HTTP重定向和DNS负载均衡都无法实现真正意义上的负载均衡,也就是调度服务器无法根据后端服务器的实际负载情况分配任务。但反向代理服务器支持手动设定每台后端服务器的权重。我们可以根据服务器的配置设置不同的权重,权重的不同会导致被调度者选中的概率的不同。或者使用IP/Url Hash的方法。

缺点

  1. 调度者压力过大

    由于所有的请求都先由反向代理服务器处理,那么当请求量超过调度服务器的最大负载时,调度服务器的吞吐率降低会直接降低集群的整体性能。

  2. 制约扩展

    当后端服务器也无法满足巨大的吞吐量时,就需要增加后端服务器的数量,可没办法无限量地增加,因为会受到调度服务器的最大吞吐量的制约。

常用负载均衡开源软件有nginx(软件-7层-应用层)、lvs(内核-4层-传输层)、haproxy,商业的硬件负载均衡设备F5(硬件-4层-传输层)、Netscale

软件和硬件的区别就在于性能,硬件远远高于软件,Ngxin 的性能是万级,一般的 Linux 服务器上装个 Nginx 大概能到 5 万 / 秒;LVS 的性能是十万级,没有具体测试过,据说可达到 80 万 / 秒;F5 性能是百万级,从 200 万 / 秒到 800 万 / 秒都有。硬件虽然性能高,但是单台硬件的成本也很高,一台最便宜的 F5 都是几十万,但是如果按照同等请求量级来计算成本的话,实际上硬件负载均衡设备可能会更便宜,例如假设每秒处理 100 万请求,用一台 F5 就够了,但用 Nginx,可能要 20 台,这样折算下来用 F5 的成本反而低。因此通常情况下,如果性能要求不高,可以用软件负载均衡;如果性能要求很高,推荐用硬件负载均衡。

其中,LVS是 Linux Virtual Server 的简称,也就是Linux虚拟服务器。

LVS包含三种负载均衡模式,分别为NAT、DR、TUN

LVS详细工作原理

NAT与DR负载均衡的区别(漫画)

另外需要注意的是现在在大厂中如果只将 Nginx 作为转发之用是不够的,一般用的 OpenResty ,什么是 OpenResty 呢

“OpenResty® 是一个基于 Nginx 与 Lua 的高性能 Web 平台,其内部集成了大量精良的 Lua 库、第三方模块以及大多数的依赖项。用于方便地搭建能够处理超高并发、扩展性极高的动态 Web 应用、Web 服务和动态网关。

OpenResty® 的目标是让你的 Web 服务直接跑在 Nginx 服务内部,充分利用 Nginx 的非阻塞 I/O 模型,不仅仅对 HTTP 客户端请求,甚至于对远程后端诸如 MySQL、PostgreSQL、Memcached 以及 Redis 等都进行一致的高性能响应。”

注意上面一句「提供了与 MySQL ,Redis 等的交互能力」这一点非常关键,由于Nginx 可以根据 url 来决定打向哪个集群,假设现在有一个这样的场景:所有包含 operation 的请求都转发到运营中心的集群,则需要写死类似如下的配置

upstream backend {
  server 192.168.1.10:8080
  server 192.168.1.11:8080
}

server {
  location /operation {
    proxy_pass http://backed
  }
}

如果我们像上面这样把所有的规则都一个个写死在 Nginx 的配置文件里,显然不可行,更合理的方式是把这些规则(哪个 url 对应哪些集群)保存在 MySQL 中,然后 Nginx 在启动的时候将这些规则从 MySQL 中取出并保存在 Redis 及本地缓存中,然后 Nginx 要根据 url 匹配的时候从本地缓存(如果没有从 redis 拿,redis 过期从 MySQL 拿)里拿这些规则再根据匹配项转发到相应的集群,Nginx 没有这样的能力,而 OpenResty 由于集成了 Lua,引入了与 MySQL, Redis 等交互的模块,所以用它是可行的

为什么在7层有Nginx后,还要有4层的Lvs作负载均衡呢?

Nginx 是七层(即应用层)负载均衡器 ,这意味着如果它要转发流量首先得和 Client 建立一个 TCP 连接,并且转发的时候也要与转发到的上游 Server 建立一个 TCP 连接,而我们知道建立 TCP 连接其实是需要耗费内存(TCP Socket 接收/发送缓存区等需要占用内存)的,客户端和上游服务器要发送数据都需要先发送暂存到到 Nginx 再经由另一端的 TCP 连接传给对方。

所以 Nginx 的负载能力受限于机器 I/O、CPU、内存等一系列配置。一旦连接很多(比如达到百万)的话,Nginx 抗负载能力就会急剧下降。

经过分析可知,Nginx 的负载能力较差主要是因为它是七层负载均衡器,必须要在上下游分别建立两个 TCP 所致。

所以需要设计一个类似路由器那样的,只负载转发包但不需要建立连接的负载均衡器

不需要建立连接只负责转发包,不需要维护额外的 TCP 连接,它的负载能力必然大大提升。于是,四层负载均衡器 LVS 就诞生了。

可以看到  LVS 只是单纯地转发包,不需要和上下游建立连接即可转发包,相比于 Nginx 它的抗负载能力强、性能高(能达到 F5 硬件的 60%),对内存和 CPU 资源消耗比较低。

注意,Nginx 在 1.9 之后也开始支持四层负载均衡了,但是,由于LVS 是 Linux 的内核模块,工作在内核态,而 Nginx 工作在用户态,相对比较重,所以在性能和稳定性上 Nginx 是不如 LVS 的,这就是为什么有的负载均衡架构要采用 LVS + Nginx 的部署方式,而不是单独设置Nginx。

那么有了4层的Lvs,是否可以不需要7层的Nginx呢?

答案是不可以的,Nginx作为7层的设备,其可以实现通过url来转发流量,那为什么4层的Lvs就不行呢?

根据网络分层原理,如果一个 HTTP POST 请求很大,超过了 1460 byte(一个包 payload 的最大值),那么它必须分成两个包才能传输,也就意味着一个包可能包含 URI,另一个包不包含 URI,既然包都不包含 URI,那么请问 LVS 如何根据 URL 来转发给相应的集群呢。

其实最关键的原因是四层以下其实只负责包的转发,只要拿出包头查看一下 ip 地址就可知道该转发哪里,很高效,如果你还要根据 url 来匹配那么需要拿到应用层数据根据正则等做匹配,显然会消耗更多的性能,所以专业的人做专业的事,应该由 LVS 来负责承载所有流量,Nginx 负责根据 url 来转发给对应的集群,因为它是七层负载均衡器,与上下游各建立了一个 TCP 链接,所以如果有多个分包,由于 Nginx 与 client 建立了 TCP 连接,可以在 Nginx 先拿到 client 发出的所有的分包再组装成完整的报文, 然后根据 url 选择其中一台 server 与之建立 TCP 连接后将数据分批完整地传给上游 server

四层负载均衡设备是如何工作的?

负载均衡设备在接收到第一个来自客户端的 SYN 请求时,即通过负载均衡算法选择一个最佳的服务器,并对报文中目标IP地址进行修改(改为后端服务器 IP ),直接转发给该服务器。

TCP 的连接建立,即三次握手是客户端和服务器直接建立的,负载均衡设备只是起到一个类似路由器的转发动作。在某些部署情况下,为保证服务器回包可以正确返回给负载均衡设备,在转发报文的同时可能还会对报文原来的源地址进行修改。

反向代理负载均衡设备如何防止单点问题? 

通常我们会用 Nginx/Lvs+keepalive 实现主备:防止唯一的负载均衡设备宕机导致系统停止

Keepalived的作用是检测服务器的状态,如果有一台web服务器宕机,或工作出现故障,Keepalived将检测到,并将有故障的服务器从系统中剔除,同时使用其他服务器代替该服务器的工作,当服务器工作正常后Keepalived自动将服务器加入到服务器群中,这些工作全部自动完成,不需要人工干涉,需要人工做的只是修复故障的服务器。

其原理如下:

网络层:Keepalived使用网络层的方式工作时,Keepalived会定期向服务器群中的服务器发送一个ICMP的数据包(既我们平时用的Ping程序),如果发现某台服务的IP地址没有激活,Keepalived便报告这台服务器失效,并将它从服务器群中剔除,这种情况的典型例子是某台服务器被非法关机。网络层的方式是以服务器的IP地址是否有效作为服务器工作正常与否的标准。

传输层:如果您理解了网络层的方式,传输就容易了。传输主要以TCP端口的状态来决定服务器工作正常与否。如web server的服务端口一般是80,如果Keepalived检测到80端口没有启动,则Keepalived将把这台服务器从服务器群中剔除。

四、负载均衡架构实践

图中的 Nginx 可以换成 OpenResty

关于该架构的演进,可点击文末的参考链接

双机热备

常见双机热备的形式

  1. 一台master、一台backup(slave),master挂了backup自动补上去

  2. 135用master、246用backup,周末休息

  3. (推荐)两台Load Balancer都作为master,分别为不同的业务做负载均衡,并且同时设置为对方的slave,即可靠,又不浪费资源

参考链接:

https://mp.weixin.qq.com/s/Rngy_zCopDWFHq4ZUo3m9w

https://mp.weixin.qq.com/s/B1pqmFqeD0IkdqG9Hf9Vfg

https://mp.weixin.qq.com/s/JrSF3HngTJGKRtjuaxJpqg

  • 5
    点赞
  • 8
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值