nginx负载均衡

  • 1.负载均衡如何实现流量分发
  • 2.负载均衡如何配置
  • 3.负载均衡调度算法
  • 4.后端web节点在负载均衡调度中的状态
  • 5.实现会话保持
  • ip_hash 做会话保持
  • redis来实现会话保持
  • 6.负载均衡根据不同设备调度至不同集群


1.负载均衡如何实现流量分发

nginx如何代理多台服务器?

添加多个proxy_pass参数是行不通的,location中只能出现一次proxy_pass,不能出现多个

nginx配置负载多个ip 多个nginx负载均衡_服务器


这时就需要⽤到nginx反向代理衍⽣的功能,负载均衡


负载均衡如何实现流量的分发:

1.需要用到两个模块:proxy_pass模块与upstream模块
2.先将相同业务的web服务器定义为⼀组upstream资源池
3.再通过proxy_pass的⽅式,代理到这⼀组upstream资源池上,即可实现负载均衡功能
4.⽤户请求负载均衡,负载均衡将请求分散的打到后端的多个web节点

nginx配置负载多个ip 多个nginx负载均衡_nginx_02


2.负载均衡如何配置

例:
负载均衡:192.168.51.164
web节点1:192.168.51.163
web节点2:192.168.51.165
将客户端的请求分发到两台不同的web节点上

1.负载均衡端配置

vim /etc/nginx/conf.d/lb.conf

upstream web {                 #定义虚拟资源池,名称叫web,⾥⾯有两台web服务器
	server 192.168.51.163:80;
	server 192.168.51.165:80;

}

server {
	listen 80;
	server_name www.test.com;
	
	location / {
	proxy_pass http://web; #调⽤upstream资源池定义的名称
	include proxy_params;  #包含优化参数
  }
  
}


nginx -t 
systemctl reload nginx

2.web节点1配置

vim /etc/nginx/conf.d/proxy.conf

server {
	listen 80;
	server_name www.test.com;
	root /html;

	location / {
			index index.html;
	}

}

#重载nginx
nginx -t 
systemctl reload nginx


#准备文件
echo 'this is node1...'>/html/index.html

3.web节点2配置

vim /etc/nginx/conf.d/proxy.conf

server {
	listen 80;
	server_name www.test.com;
	root /html;

	location / {
			index index.html;
	}

}


#重载nginx
nginx -t 
systemctl reload nginx


#准备文件
echo 'this is node2....'>/html/index.html

4.查看测试结果

访问www.test.com

nginx配置负载多个ip 多个nginx负载均衡_负载均衡_03

刷新一次,就来到了web节点2上

nginx配置负载多个ip 多个nginx负载均衡_nginx_04


再刷新一次就来到了web节点1上

nginx配置负载多个ip 多个nginx负载均衡_服务器_05


3.负载均衡调度算法

nginx配置负载多个ip 多个nginx负载均衡_php_06


1.轮询:将⽤户请求调度到不同的web节点,一个节点一次,公平调度算法。(默认使用的调度算法)

upstream test {
	server 192.168.10.10:80;
	server 192.168.10.20:80;
}

2.加权轮询:根据后端的节点性能情况,调整他们的负载值,weight值越大,被访问的几率越大,能者多劳。

upstream test {
	server 192.168.10.10:80 weight=5;
	server 192.168.10.20:80 weight=3;
}

3.ip_hash: 将客户端绑定⾄某⼀个指定的后端服务节点。 ( 做会话保持 ) 不管刷新多少次都在同一个节点上

upstream test {
	ip_hash;
	server 192.168.10.10:80;
	server 192.168.10.20:80;
}

4.least_conn: 谁的连接数少,就将请求发给谁。( 动态的调度 )

upstream test {
    least_conn;
	server 192.168.10.10:80;
	server 192.168.10.20:80;
}

4.后端web节点在负载均衡调度中的状态

nginx配置负载多个ip 多个nginx负载均衡_nginx_07


down

当后端节点状态为down表示,当前节点不启用,请求将不再发给它

backup
当作备胎,upstream资源池中所有的节点都无法使用时,它才会顶替上去
但凡有一个节点恢复正常,它都将被停掉

max_fails与fail_timeout一般这两个状态连用
例:max_fails=3 fail_timeout=10s
表示10秒内请求失败超过3次,则认定这个节点不可用
但是还会一直监控它的可用性,当检测到他可用时,还会将客户端请求发给它

max_conns
限制最多能接收多少连接

例:
upstream name {
server 192.168.51.163 down;
server 192.168.51.165;
}

例:
upstream name {
server 192.168.51.163 backup;
server 192.168.51.165;
}

例:
upstream name {
server 192.168.51.163:80 weight=5 max_fails=3 fail_timeout=10s max_conns=1000;
server 192.168.51.165:80 weight=3 max_fails=3 fail_timeout=10s max_conns=1000; 
}

5.实现会话保持

存在的问题:将相同业务的后端节点加入负载均衡后,在客户端进行登录操作的时候,会发现不管在哪个节点都无法登陆

解决方案:做会话保持
1.粘性session: ip_hash 始终定向⾄某⼀个后端web节点。
2.session共享: 将session通过存储到指定⼀个位置,⽽不是存储⾄本地,后端所有节点都通过这个位置进行验证 ( redis )

1.粘性session: ip_hash 始终定向⾄某⼀个后端web节点。

2.session复制: 每次session发⽣变化时,就通过⼴播的形式通知给集群中的其他服务器,使得集群中所有节点的session⼀致。

3.session共享: 将session通过存储到指定⼀个位置,⽽不是存储⾄本地。 ( redis ) o(1)

4.session持久化:就session信息写到数据库中。 ( 例如wordpress是写到数据库。) o(N)

数据库o(N)级别,例如检索一条数据需要1秒,那么检索1000条数据,就需要1000秒
数据库o(1)级别,查一条数据需要1秒,查1000条数据也是一秒

ip_hash 做会话保持

这里使用phpmyadmin进行会话保持演示:
负载均衡:192.168.51.164
phpmyadmin节点1:192.168.51.163
phpmyadmin节点2:192.168.51.165

节点1与节点2 都按以下步骤进行配置

1.下载phpmyadmin
 wget https://files.phpmyadmin.net/phpMyAdmin/5.0.2/phpMyAdmin-5.0.2-all-languages.zip
 
 解压到指定目录
unzip phpMyAdmin-5.0.2-all-languages.zip -d /html




2.修改phpmyadmin的配置,指定程序连接数据库的IP地址
cd /html/phpMyAdmin-5.0.2-all-languages

创建配置文件
cp config.sample.inc.php config.inc.php

编辑配置文件
vim config.inc.php 

/* Server parameters */
$cfg['Servers'][$i]['host'] = '192.168.xx.xxx';  #此处是数据库服务器的地址




3.配置nginx
vim /etc/nginx/conf.d/www.phpmy.com.conf

server {
 	listen 80;
 	server_name www.phpmy.com;
 	root /html/phpMyAdmin-5.0.2-all-languages;
 	
 		location / {
			 index index.php;
		 }
		 
		 location ~ \.php$ {
			 fastcgi_pass 127.0.0.1:9000;
			 fastcgi_param SCRIPT_FILENAME $document_root$fastcgi_script_name;
			 include fastcgi_params;
			 }
	}



4.重载nginx
nginx -t
systemctl reload nginx

负载均衡配置

在这里做了会话保持,就会解决无法登陆的问题,但是只能访问固定的一个web节点,无法轮询

upstream web {
	ip_hash;    #做会话保持
	server 192.168.51.163:80;
	server 192.168.51.165:80;

}

server {
	listen 80;
	server_name www.phpmy.com;


	location / {
		proxy_pass http://web;
		include proxy_params;
	
		}

}

修改客户端的hosts文件
192.168.51.164 www.phpmy.com


redis来实现会话保持

redis配置

1.部署redis
yum install redis -y

2.配置redis,让别的服务器可以访问到它
vim /etc/redis.conf

bind 127.0.0.1 192.168.xx.xxx  
#redis部署在哪台服务器,这里就写哪个服务器的地址192.168.xx.xxx 
#让其他服务器可以通过192.168.xx.xxx来访问redis
#或者配置成允许别⼈通过192.168.xx.0/⽹段访问redis数据库也可以

3.启动redis,并将其加⼊开机⾃启动。
systemctl start redis
systemctl enable redis
netstat -lntp |grep 6379

每个web端配置
修改所有的web服务器中php的配置

1.先修改php.ini 使⽤redis⽅式存储session,然后配置redis的地址及端⼝信息
vim /etc/php.ini

 [Session]
 ;session.save_handler = files #将默认的注释掉,使⽤ ;来进⾏注释
 
 #新增如下两条:
session.save_handler = redis
session.save_path = "tcp://192.168.xx.xxx:6379"    #redis的地址



2. vim /etc/php-fpm.d/www.conf     #注释掉如下两⾏

 ;php_value[session.save_handler] = files
 ;php_value[session.save_path] = /var/lib/php/session


3.重启php-fpm
 systemctl restart php-fpm

负载均衡配置

使用轮询的机制就可以

upstream web {
	server 192.168.51.163:80;
	server 192.168.51.165:80;

}

server {
	listen 80;
	server_name www.phpmy.com;


	location / {
		proxy_pass http://web;
		include proxy_params;
	
		}

}


nginx -t
systemctl reload nginx

然后刷新就可以查看会话保持的效果

这里我把数据库和其中一台web节点部署在了一台服务器上了,所以显示localhost

nginx配置负载多个ip 多个nginx负载均衡_nginx_08

nginx配置负载多个ip 多个nginx负载均衡_nginx_09


可以看到redis中存的session

nginx配置负载多个ip 多个nginx负载均衡_负载均衡_10


6.负载均衡根据不同设备调度至不同集群

不同的设备所访问的后端服务器不同

例:

nginx配置负载多个ip 多个nginx负载均衡_服务器_11

准备环境

lb作为负载均衡,统⼀调度:
 他需要根据⽤户来源的设备进行判断:
      如果⽤户是⼿机端,则调度到后端192.168.51.163的8080 、8081
      如果⽤户是电脑端,则调度到后端的192.168.51.165的9090、9091
      
		web01作为⼿机端集群,多端⼝⽅式:
		web1 8080: phone-8080
		web2 8081: phone-8081
		
		web02作为电脑端集群,多端⼝的⽅式:
		web1 9090: pc-9090
		web2 9091: pc-9091

负载均衡配置

1.编辑nginx配置文件

vim /etc/nginx/conf.d/lb.conf
 
upstream phone {
	server 192.168.51.163:8080;
	server 192.168.51.163:8081;

}

upstream pc {
        server 192.168.51.165:9090;
        server 192.168.51.165:9091;

}


server {
	listen 80;
	server_name www.agent.com;


	location / {
		#根据$http_user_agent参数判断,如果你是⼿机端,我们就进⼊该判断,由phone集群处理
		
		if ( $http_user_agent ~* "iphone|android|ipad"){   
			proxy_pass http://phone;
		}
		
		proxy_pass http://pc;     #如果不是⼿机端,则直接由pc集群处理
		include proxy_params;
	
		}
}

2.重载nginx
nginx -t
systemctl reload nginx

手机web端配置

1.准备文件
mkdir web_8080
mkdir web_8081

echo 'phone-8080'> /html/web_8080/index.html
echo 'phone-8081'> /html/web_8081/index.html


2.编辑nginx配置文件
vim /etc/nginx/conf.d/www.agent.com.conf 

server {
	listen 8080;
	server_name www.agent.com;
	root /html/web_8080;


	location / {
		index index.html;

	}
}
server {
        listen 8081;
        server_name www.agent.com;
        root /html/web_8081;


        location / {
                index index.html;

        }       
}

3.重载nginx
nginx -t
systemctl reload nginx

电脑web端配置

1.准备文件
mkdir web_9090
mkdir web_9091

echo pc-9090'> /html/web_9090/index.html
echo 'pc-9091'> /html/web_9091/index.html


2.编辑nginx配置文件
vim /etc/nginx/conf.d/www.agent.com.conf 

server {
	listen 9090;
	server_name www.agent.com;
	root /html/web_9090;


	location / {
		index index.html;

	}
}
server {
        listen 9091;
        server_name www.agent.com;
        root /html/web_9091;


        location / {
                index index.html;

        }       
}

3.重载nginx
nginx -t
systemctl reload nginx

查看效果

手机端访问:

nginx配置负载多个ip 多个nginx负载均衡_服务器_12

nginx配置负载多个ip 多个nginx负载均衡_nginx_13


电脑端访问:

nginx配置负载多个ip 多个nginx负载均衡_nginx配置负载多个ip_14


nginx配置负载多个ip 多个nginx负载均衡_服务器_15