一、负载均衡简介
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
[[email protected] ~]# 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
[[email protected] ~]# cd /root/nginx-1.12.1
[[email protected] 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的参数都加上,然后再加上添加的模块
[[email protected] 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目录下
[[email protected] ~]# 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://blog.51cto.com/longlei/2138683