一, 负载均衡简介
1, 什么是负载均衡
负载均衡 建立在现有网络结构之上, 它提供了一种廉价有效透明的方法扩展网络设备和服务器的带宽, 增加吞吐量, 加强网络数据处理能力, 提高网络的灵活性和可用性.
负载均衡, 英文名称为 Load Balance, 其意思就是分摊到多个操作单元上进行执行, 例如 web 服务器, FTP 服务器, 企业关键应用服务器和其它关键任务服务器等, 从而共同完成工作任务.
简单的来说. 负载均衡可以减少服务器的压力, 将原本一台服务器所要承受的访问量分给了多台, 并提高了项目的可用性, 当一台服务器挂掉的时候也不会导致整个项目瘫痪.
2, 负载均衡的目的
负载均衡的目的是为了解决单个节点压力过大, 造成 Web 服务响应过慢, 严重的情况下导致服务瘫痪, 无法正常提供服务, 由于一个 Web 服务同时能处理的用户并发请求的数量有限, 同时还有机器故障的情况, 所以一个 Web 站点通常会在 N 台机器上各部署一套同样的程序. 当某一个服务挂掉的时候, 还有第二个, 第三个, 第 N 个服务... 继续为用户提供服务, 给用户的感觉, 你的服务还在正常的运行! 在这些提供同样服务的机器当中, 在硬件配置方面也各不一样, 这样就会存在部份机器性能非常好, 能快速计算并响应用户的请求, 另外一部份机器可能配置差点, 响应用户的请求的时间会长一些.
这就需要我们思考一个问题? 如果有一个服务正在同时处理 1000 个用户的请求, 这个服务的上限可能最多能同时处理 1000 个用户的请求, 这时它已经很忙了, 如果此时又有一个新请求过来, 我们仍然把这个请求分配给这台机器, 这时候这个请求就只能在干等着, 等这个服务处理完那些请求后, 再继续处理它. 这样在浏览器中的反应就像 12306 我们在春节买票一样, 卡在那不动了, 让用户眼巴巴的干着急. 而能提供同样服务的其它机器, 这时确很空闲. 这样不仅是对服务器资源的浪费, 也充分发挥不出弄多台服务器装同一个服务的最高价值. 我们通常称对某一台机器的访问量称为负载量, 如何将一个用户的请求, 合理的分配到一台能快速响应用户请求的服务器上, 我们就需要用到一些负载策略. 也就体现出了文章主题的用意了: 负载均衡, 将用户的所有 HTTP 请求均衡的分配到每一台机器上, 充分发挥所有机器的性能, 提高服务的质量和用户体验. 负载均衡可以通过负载均衡网络硬件设备和 Web 服务器软件来实现, 前者设备成本较高, 小公司通常负担不起, 所以后者一般是我们的首选. 实现负载均衡常用的 Web 服务器软件有 Nginx,HAProxy,LVS 等, 本文主要介绍 Nginx 的负载均衡策略.
3, 负载均衡的常用功能
客户端的请求转发功能: 按照一定的算法 [权重, 轮询] , 将客户端请求转发到不同应用服务器上, 减轻单个服务器压力, 提高系统并发量.
服务器的故障转移功能: 通过心跳检测的方式, 判断应用服务器当前是否可以正常工作, 如果服务器宕掉, 自动将请求发送到其他应用服务器.
服务器故障恢复自动添加功能: 如检测到发生故障的应用服务器恢复工作, 自动将其添加到处理用户请求队伍中.
二, Nginx 内置三种负载策略
Nginx 负载均衡是通过 upstream 模块来实现的, 内置实现了三种负载策略, 配置还是比较简单的. 官网负载均衡配置说明: http://nginx.org/en/docs/http/load_balancing.html
1, 轮循 (默认 weight=1)
Nginx 根据请求次数, 将每个请求按时间顺序逐一分配到不同的后端服务器, 如果后端服务器 down 掉, 能自动剔除
- upstream bakend {
- server 192.168.1.10;
- server 192.168.1.11;
- }
2, 权重轮询 (weight)
通过配置权重, 指定轮询几率, 权重和访问比率成正比, 用于应用服务器性能不均的情况. 如果后端服务器 down 掉, 能自动剔除. 比如以下配置, 则 1.11 服务器的访问量为 1.10 服务器的两倍.
- upstream bakend {
- server 192.168.1.10 weight=1;
- server 192.168.1.11 weight=2;
- }
- 3,ip_hash
每个请求按访问 ip 的 hash 结果分配, 这样每个访客固定访问一个后端服务器, 可以解决 session 不能跨服务器的问题. 如果后端服务器 down 掉, 要手工 down 掉.
- upstream resinserver{
- ip_hash;
- server 192.168.1.10:8080;
- server 192.168.1.11:8080;
- }
4,nginx 相关参数说明
详细的可以参考官方文档: http://nginx.org/en/docs/http/ngx_http_upstream_module.html#server
- http {
- resolver 10.0.0.1;
- upstream tomcats {
- server 192.168.0.100:8080;
- server 192.168.0.101:8080 weight=3;
- server 192.168.0.102:8080 backup;
- server 192.168.0.103:8080 down;
- server 192.168.0.104:8080 max_conns=1000;
- server 192.168.0.105:8080 weight=2 max_fails=3 fail_timeout=15;
- }
- server {
- listen 80;
- location / {
- proxy_pass http://tomcats;
- }
- }
- }
resolve: 将 server 指令配置的域名, 指定域名解析服务器.
upstream 模块: 配置反向代理服务器组, Nginx 会根据配置, 将请求分发给组里的某一台服务器. tomcats 是服务器组的名称.
weight : 默认为 1, 将请求平均分配给每台 server
backup: 备份机, 所有服务器挂了之后才会生效
down: 标识某一台 server 不可用. 可能能通过某些参数动态的激活它吧, 要不真没啥用.
max_conns: 限制分配给某台 Server 处理的最大连接数量, 超过这个数量, 将不会分配新的连接给它. 默认为 0, 表示不限制.
max_fails: 默认为 1. 某台 Server 允许请求失败的次数, 超过最大次数后, 在 fail_timeout 时间内, 新的请求将不会分配给这台机器.
fail_timeout: 默认为 10 秒. 某台 Server 达到 max_fails 次失败请求后, 在 fail_timeout 期间内, nginx 会认为这台 Server 暂时不可用, 不会将请求分配给它
proxy_pass http://tomcats: 表示将所有请求转发到 tomcats 服务器组中配置的某一台服务器上.
三, nginx 第三方负载策略
1,fair(第三方插件)
根据服务器的响应时间来分配请求, 响应时间短的优先分配, 即负载压力小的优先会分配. 由于 fair 模块是第三方提供的, 所以在编译 nginx 源码的时候, 需要将 fair 添加到 nginx 模块中. 我的 nginx 是通过源码安装的, 安装在 / usr/local/nginx-1.12.1 / 目录下, 而且安装时没有添加 fair 模块, 重新编译添加 fair 模块方法如下:
(1) 下载 fair 模块源码并解压
下载地址: https://github.com/gnosek/nginx-upstream-fair/tree/master
- [root@localhost ~]# unzip master.zip
- nginx-1.12.1 nginx-upstream-fair-master master.zip
这个是刚刚解压的
解压后的目录名为: nginx-upstream-fair-master
(2) 重新编译 nginx
重新编译 nginx 将 fair 模块添加到编译参数, 我的 nginx 源码目录在 / root/nginx-1.12.1
- [root@localhost ~]# cd /root/nginx-1.12.1
- [root@localhost nginx-1.12.1]# ./configure --user=nginx --group=nginx --prefix=/usr/local/nginx-1.12.1 --with-http_stub_status_module --with-http_ssl_module --add-module=/root/nginx-upstream-fair-master 把之前编译 nginx 的参数都加上, 然后再加上添加的模块
- [root@localhost nginx-1.12.1]# make
/root/nginx-upstream-fair-master/ngx_http_upstream_fair_module.c: 在函数'ngx_http_upstream_init_fair_rr'中:
/root/nginx-upstream-fair-master/ngx_http_upstream_fair_module.c:543:28: 错误:'ngx_http_upstream_srv_conf_t'没有名为'default_port'的成员
- if (us->port == 0 && us->default_port == 0) {
- ^
/root/nginx-upstream-fair-master/ngx_http_upstream_fair_module.c:553:51: 错误:'ngx_http_upstream_srv_conf_t'没有名为'default_port'的成员
- u.port = (in_port_t) (us->port ? us->port : us->default_port);
- ^
make[1]: *** [objs/addon/nginx-upstream-fair-master/ngx_http_upstream_fair_module.o] 错误 1
make[1]: 离开目录 "/root/nginx-1.12.1"
make: *** [build] 错误 2
这里报错一堆, 可能是 nginx 版本太高导致, 换低版本的就没问题.
注意: 不要执行 make install, 这样会覆盖之前 nginx 的配置
(3) 复制编译好的 nginx 执行文件到 nginx 的 sbin 目录覆盖之前的
将新编译的 nginx 可执行程序拷贝到 / opt/nginx/sbin / 目录下, 覆盖之前安装的 nginx
编译后的 nginx 执行程序, 放在 nginx 源码的 objs 目录下
[root@localhost ~]# cp /root/ nginx-1.12.1/objs/nginx /usr/local/ nginx-1.12.1/sbin/
(4) 配置使用 fair 负载策略模块
- upstream tomcats {
- fair;
- server 192.168.0.100:8080;
- server 192.168.0.101:8080;
- server 192.168.0.102:8080;
- }
由于采用 fair 负载策略, 配置 weigth 参数改变负载权重将无效.
2,url_hash(第三方插件)
按请求 url 的 hash 结果来分配请求, 使每个 url 定向到同一个后端服务器, 服务器做缓存时比较有效. 1.7.2 版本以后, url_hash 模块已经集成到了 nginx 源码当中, 不需要单独安装. 之前的版本仍需要单独安装, 下载地址: https://github.com/evanmiller/nginx_upstream_hash
安装方法和 fair 模块一样, 先下载 url_hash 源码, 然后重新编译 nginx 源码, 将 url_hash 模块添加到编译配置参数当中, 最后将编译后生成的 nginx 二进制文件替换之前安装的 nginx 二进制文件即可.
- upstream tomcats {
- server 192.168.0.100:8080;
- server 192.168.0.101:8080;
- server 192.168.0.102:8080;
- hash $request_uri;
- }
四, 使用 Nginx 的高可用
除了要实现网站的高可用, 也就是提供 n 多台服务器用于发布相同的服务, 添加负载均衡服务器分发请求以保证在高并发下各台服务器能相对饱和的处理请求. 同样, 负载均衡服务器也需要高可用, 以防如果负载均衡服务器挂掉了, 后面的应用服务器也紊乱无法工作.
实现高可用的方案: 添加冗余. 添加 n 台 nginx 服务器以避免发生上述单点故障. 具体方案详见以后的文章: keepalive+nginx 实现负载均衡高可用
五, 总结
总结一点, 负载均衡不论是各种软件或硬件上的解决方案, 主要还是将大量的并发请求按照一定的规律分发给不同的服务器处理, 从而减少某台服务器的瞬时压力, 提高网站的抗并发能力. nginx 在负载均衡的应用之所以广泛, 这归功于它的灵活配置, 一个 nginx.conf 文件解决大部分问题, 不论是 nignx 创建虚拟服务器, nginx 的反向代理服务器, 还是本文介绍的 nginx 的负载均衡, 几乎都在这个配置文件中进行. 服务器上只负责把 nginx 搭好, 跑起来即可. 而且它本身轻量级, 不需要占用服务器太多资源就可以达到较好的效果.
来源: http://www.bubuko.com/infodetail-2676522.html