Nginx负载均衡

1、实现 Nginx 负载均衡的组件说明

Nginx http 功能模块模块说明
ngx_http_proxy_moduleproxy 代理模块, 用于把请求后拋给服务器节点或 upstream 服务器池
ngx_http_upstream_module负载均衡模块, 可以实现网站的负载均衡功能及节点的健康检査

2、Nginx中常用模块说明

1)Nginx upstream模块

Nginx的负载均衡功能依赖于ngx_http_upsteam_module模块,所支持的代理方式包括proxy_pass、fastcgi_pass、memcached_pass等。

其中的​ngx_http_upstream_module模块允许Nginx定义一组或多组节点服务器组,使用时可以通过proxy_pass代理方式把网站的请求发送到事先定义好的对应Upstream组的名字上,具体写法为“proxy_pass http:// www_server_pools”,其中www_server_pools就是一个Upstream节点服务器组名字。

ngx_http_upstream_module模块官方地址:http://nginx.org/en/docs/http/ngx_http_upstream_module.html

① upstream参数

模块内参数参数说明
server 10.0.10.8:80负载均衡后面的RS配置,可以是 IP 或者是域名,如果端口不写,默认是 80 端口。高并发场景下, IP可换成域名,通过 DNS做负载均衡
weigth=1代表服务器的权重,默认值是 1 。权重数字越大表示接受的请求比例越大
max_fails=3Nginx 尝试连接后端主机失败的次数,这个值是配合 proxy_next_upstream、fastcgi_next_upstream 和memcached_next_upstream 这三个参数来使用的。当 nginx 接收后端服务器返回这三个参数定义的状态码时,会将这个请求转发给正常工作的后端服务器,例如 404、502、503、Max_fails 的默认值是 1 ;企业场景下建议 2-3 次。如京东 1 次,蓝汛 10 次,根据业务需求去配置
fail_timeout=10s在 max_fails 定义的失败次数后,距离下次检查的间隔时间,默认是 10s ;如果 max_fails 是 5 ,它就检测 5 次,如果 5 次都是 502 ,那么就会根据 fail_timeout 的值,等待 10s 再去检查,还是只检查一次,如果持续 502 ,在不重新加载 Nginx 配置的情况下,每隔 10s 都只检查一次。常规业务 2~3 秒比较合理,比如京东 3 秒,蓝汛 3 秒,可根据业务需求去配置
backup热备配置( RS 节点的高可用),当前面激活的 RS 都失败后会自动启用热备 RS 这标志看这个服务器作为备份服务器,若主服务器全部宕机了,就会向它转发请求。注意:当负载调度算法为 ip_hash 时,后端服务器在负载均衡调度中的状态不能是 weight 和 backup
down这标志着服务器永远不可用,这个参数可配合 ip_hash 使用,类似与注释

模块调度算法:

第一类:静态调度算法,即负载均衡器根据自身设定的规则进行分配,不需要考虑后端节点服务器的情况,例如:rr、wrr、ip_hash等都属于静态调度算法;
第二类:动态调度算法,即负载均衡器会根据后端节点的当前状态来决定是否分发请求,比如说连接数少的优先获得请求,响应时间短的优先获得请求。例如:least_conn、fair等都属于动态调度算法。

常用调动算法:

A.定义轮询调度算法——rr(默认调度算法)
B.定义权重调度算法——wrr
C.定义静态调度算法——ip_hash(该调度算法可以解决动态网页的session共享问题)
D.定义最小的连接数——least_conn

② 示例1:基本的upstream配置案例

upstream wwwPools {
#upstream是关键字必须有,后面的www_server_pools为一个Upstream集群组的名字,可以自己起名,调用时就用这个名字
	server 192.168.0.223:80 weight=5;
	server 192.168.0.224:80 weight=10;
	server 192.168.0.225:80 weight=15;
	#server关键字是固定的,后面可以接域名(门户会用)或IP。如果不指定端口,默认是80端口。weight代表权重,数值越大被分配的请求越多,结尾需要带分号
}

③ 示例2:较完整的upstream配置案例

upstream wwwPools {
	server 192.168.0.223;   #这行标签和下行是等价的
	server 192.168.0.224:80 weight=1 max_fails=1 fail_timeout=10s;       #这行标签和上一行是等价的,此行多余的部分就是默认配置,不写也可以。
	server 192.168.0.225:80 weight=1 max_fails=2 fail_timeout=20s backup;		#这行末尾的backup表示备份服务器(当其余所有服务器都宕机后才会激活使用)
	#server最后面还可以添加很多参数,具体参数作用对比上方的表格
}

④ 示例3:使用域名及socket的upstream配置案例

upstream backend {
	server backend1.example.com weight=5;
	server backend2.example.com:8080;	#域名加端口(转发到后端的指定端口上)
	server unix:/tmp/backend3;		#指定socket文件
	#提示:server后面如果接域名,需要在内网配有DNS服务器或者在负载均衡器的hosts文件中添加域名解析条目

	server 192.168.0.223;
	server 192.168.0.224:8080;
	#备份服务器,等上面指定的服务器都不可访问的时候会启动,backup的用法和Haproxy中用法一样
	server backup1.example.com:8080 backup;
	server backup2.example.com:8080 backup;
}

2)http_proxy_module模块

proxy_pass指令属于ngx_http_proxy_module模块,此模块可以将请求转发到另一台服务器,在实际的反向代理工作中,会通过location功能匹配指定的URI,然后把接收到的符合匹配URI的请求通过proxy_pass抛给定义好的upstream节点池。

http_proxy_module模块官方地址:http://nginx.org/en/docs/http/ngx_http_proxy_module.html#proxy_pass

① proxy参数

http proxy模块内参数参数说明
proxy_set_header设置 http 请求 header 项传给后端服务器节点,例如:可实现让代理后端的服务器节点获取访问客户端用户的真实 IP 地址
client_body_buffer_size用于指定客户端请求主体缓冲区大小
proxy_connect_timeout表示反向代理后端节点服务器连接的超时时间,即发起握手等候响应的超时时间
proxy_send_timeout表示代理后端服务器的数据回传时间,即在规定时间内后端服务器必须传完所有数据,否则nginx将断开这个连接
proxy_read_timeout设置 nginx 从代理的后端服务器获取信息的时间,表示连接建立成功后,nginx 等待后端服务器的响应时间,其实是 nginx 已经进入后端的排队之中等候处理的时间
proxy_buffer_size设置缓冲区大小,默认该缓冲区大小等于指令 proxy_buffers 设置的大小
proxy_buffers设置缓冲区的数量和大小,nginx 从代理的后端服务器获取的响应信息,会设置到缓冲区
proxy_busy_buffers_size用于设置相同很忙时可以使用的 proxy_buffers 大小,官方推荐的大小为 proxy_buffers * 2
proxy_trmp_file_write_size指定 proxy 缓存临时文件的大小

② 示例1:将匹配URI为name的请求抛给http://127.0.0.1/remote/

location /name/ {
	proxy_pass http://127.0.0.1/remote/;
}

③ 示例2:将匹配URI为some/path的请求抛给http://127.0.0.1

location /some/path/ {
	proxy_pass http://127.0.0.1;
}

④ 示例3:将匹配URI为name的请求应用指定的rewrite规则,随后再抛给http://127.0.0.1

location /name/ {
	rewrite /name/( [^/]+ )  /username=$1 break;
	proxy_pass http://127.0.0.1;
}

3、nginx负载均衡相关重要参数

Nginx反向代理重要参敎解释说明
proxy_pass http://server_pools;通过 proxy_pass 功能把用户的清求转向到反向代理定义的 upstream 服务器池
proxy_set_header Host $host在代理向后端服务器发送的 http 请求头中加入 host 字段信息,用于当后端服务器配置有多个虚拟主机时,可以识别代理的是哪个虚拟主机,是节点服务器多虚拟主机时的关键配置
proxy_set_header X-Forwarded-For $remote_addr;在代理向后端服务器发送的 http 请求头中加入 X-Forward-For 字段信息,用于后端服务器程序、日志等接收记录真实用户的 IP,而不是代理服务器的 IP这是反向代理时,节点服务器获取用户真实 IP 的必要功能配置

4、配置实现负载均衡

1)实验环境

代理服务器:192.168.25.138
实际内网服务器:192.168.25.136 & 192.168.25.137
客户:192.168.25.139

2)单虚拟主机节点服务器案例

① 实际内网服务器配置网站

136内网服务器

[root@136 ~]# yum install nginx -y
[root@136 ~]# vim /etc/nginx/conf.d/vhost.conf
server {
        listen 80;
        server_name web1.yunjisuan.com;
        
        location / { 
                root /usr/share/nginx/html/web1;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web1/logs/access_bbs.log main;
}
[root@136 ~]# mkdir -p /usr/share/nginx/html/web1/logs
[root@136 ~]# echo "`hostname -I `web1" > /usr/share/nginx/html/web1/index.html

[root@136 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@136 ~]# systemctl restart nginx		#重启

137内网服务器

[root@137 ~]# yum install nginx -y
[root@137 ~]# vim /etc/nginx/conf.d/vhost.conf
server {
        listen 80;
        server_name web1.yunjisuan.com;
        
        location / { 
                root /usr/share/nginx/html/web1;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web1/logs/access_bbs.log main;
}
[root@137 ~]# mkdir -p /usr/share/nginx/html/web1/logs
[root@137 ~]# echo "`hostname -I `web1" > /usr/share/nginx/html/web1/index.html

[root@137 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@137 ~]# systemctl restart nginx		#重启

② 代理服务器配置负载均衡

138代理服务器

[root@138 ~]# yum install nginx -y
[root@138 ~]# vim /etc/nginx/conf.d/lb_test.conf
upstream www_server_pools {
		#定义“www_server_pools”服务器池,包含了136137两个Web节点,权值均为1
        server 192.168.25.136:80 weight=1;
        server 192.168.25.137:80 weight=1;
}
server {
        listen 80;
        server_name web1.yunjisuan.com;
        location / {
                proxy_pass http://www_server_pools;		#调用“www_server_pools”服务器池
		}
}

[root@138 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@138 ~]# systemctl restart nginx		#重启

③ 客户测试

139客户
配置hosts文件

[root@139 ~]# vim /etc/hosts
127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.25.138 web1.yunjisuan.com

使用for循环进行循环访问测试四次

[root@139 ~]# for ((i=1;i<=4;i++)); do curl http://web1.yunjisuan.com; done
192.168.25.137 web1
192.168.25.136 web1
192.168.25.137 web1
192.168.25.136 web1

#可以清晰看出权值为1时,每个服务器轮流被访问

3)多虚拟主机节点服务器案例

① 实际内网服务器配置网站

136内网服务器

[root@136 ~]# yum install nginx -y
[root@136 ~]# vim /etc/nginx/conf.d/vhost.conf
server {
        listen 80;
        server_name web1.yunjisuan.com;
        
        location / { 
                root /usr/share/nginx/html/web1;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web1/logs/access_bbs.log main;
}

server {
        listen 80;
        server_name web2.yunjisuan.com;

        location / {
                root /usr/share/nginx/html/web2;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web2/logs/access_www.log main;
}

[root@136 ~]# mkdir -p /usr/share/nginx/html/{web1,web2}/logs
[root@136 ~]# echo "`hostname -I `web1" > /usr/share/nginx/html/web1/index.html
[root@136 ~]# echo "`hostname -I `web2" > /usr/share/nginx/html/web2/index.html

[root@136 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@136 ~]# systemctl restart nginx		#重启

137内网服务器

[root@137 ~]# yum install nginx -y
[root@137 ~]# vim /etc/nginx/conf.d/vhost.conf
server {
        listen 80;
        server_name web1.yunjisuan.com;
        
        location / { 
                root /usr/share/nginx/html/web1;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web1/logs/access_bbs.log main;
}

server {
        listen 80;
        server_name web2.yunjisuan.com;

        location / {
                root /usr/share/nginx/html/web2;
                index index.html index.htm;
        }
        access_log /usr/share/nginx/html/web2/logs/access_www.log main;
}

[root@137 ~]# mkdir -p /usr/share/nginx/html/{web1,web2}/logs
[root@137 ~]# echo "`hostname -I `web1" > /usr/share/nginx/html/web1/index.html
[root@137 ~]# echo "`hostname -I `web2" > /usr/share/nginx/html/web2/index.html

[root@137 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@137 ~]# systemctl restart nginx		#重启

② 代理服务器配置负载均衡

138代理服务器

[root@138 ~]# yum install nginx -y
[root@138 ~]# vim /etc/nginx/conf.d/lb_test.conf
upstream www_server_pools {
		#定义“www_server_pools”服务器池,包含了136137两个Web节点,权值均为1
        server 192.168.25.136:80 weight=1;
        server 192.168.25.137:80 weight=1;
}
server {
        listen 80;
        server_name web1.yunjisuan.com;
        location / {
                proxy_pass http://www_server_pools;		#调用“www_server_pools”服务器池
				proxy_set_header Host $host;		#告知代理服务器如何识别多个不同虚拟主机
		}
}

server {
        listen 80;
        server_name web2.yunjisuan.com;
        location / {
                proxy_pass http://www_server_pools;		#调用“www_server_pools”服务器池
                proxy_set_header Host $host;		#告知代理服务器如何识别多个不同虚拟主机
        }
}

[root@138 ~]# nginx -t		#测试语法问题
nginx: the configuration file /etc/nginx/nginx.conf syntax is ok
nginx: configuration file /etc/nginx/nginx.conf test is successful

[root@138 ~]# systemctl restart nginx		#重启

③ 客户测试

139客户
配置hosts文件

[root@139 ~]# vim /etc/hosts
127.0.0.1   localhost localhost.localdomain localhost4 localhost4.localdomain4
::1         localhost localhost.localdomain localhost6 localhost6.localdomain6
192.168.25.138 web1.yunjisuan.com web2.yunjisuan.com

使用for循环进行循环访问测试四次

[root@139 ~]# for ((i=1;i<=4;i++)); do curl http://web1.yunjisuan.com; done
192.168.25.137 web1
192.168.25.136 web1
192.168.25.137 web1
192.168.25.136 web1

[root@139 ~]# for ((i=1;i<=4;i++)); do curl http://web2.yunjisuan.com; done
192.168.25.136 web2
192.168.25.137 web2
192.168.25.136 web2
192.168.25.137 web2

#可以清晰看出权值为1时,两个虚拟主机的每个服务器都是轮流被访问

5、故障报错

nginx反向代理报错400
故障报错原因:根据400报错以及对http协议的原理了解得知是因为请求头的原因,原因是因为upstream后面的名称有下划线使得代理无法识别。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值