web服务器如果是城池,那负载均衡就是城门
反向代理定义
可以和正向代理做比较来理解
正向代理就是你想翻墙的时候,主动挂sslocal,
就是由客户端来控制我要不要代理,以及怎么代理,决定权在client
反向代理
是在原先的web服务器前面,提前把请求拦下来,但是客户端以为挡在前面的服务器就是真实的服务器
决定权在服务器,客户段看不到实际情况
好处
比如reverseproxy被攻击了,但是所有的数据,网页,图片,可以都不在这台reverseproxy服务器上,
你要向攻击,就要攻击后面真实的web服务器或则数据库服务器,图片服务器等,对能力不足的攻击者当然就比较安全了
定义
随着网站访问量增加,单台服务器不能承担这么多用户的并发访问,必须用多台计算机协同工作
这个时候需要有人来协调这几台计算机,不能让其中一台很忙,另一台很闲
负载均衡的梦想是能平均分配将客户请求分给服务器集群中的各台电脑
实现形式
1. 用户手动选择
比如下载站里面会提供多个下载服务器地址,如果第一个服务器下载失败了(可能负载太高),用户可以选择后面的试试
2. DNS轮询方式
设置方法
就是对域名(主机名),添加多条A记录,
比如说 google.com 可以设置多个服务器指向这个主机名(域名),这样就完成了简单的负载均衡设置
原理
dns 服务器将解析请求按照A记录的顺序,随机分配到不同的ip上,也就是转到了不同的服务器
优点
简单,成本低
缺点
1. 负载分配不均衡,不靠谱,不可控,你不能平均让服务器获得用户请求
2. 如果有一台服务器挂了,就算你修改了dns解析,由于dns是缓存在不同服务器上的,所以生效要很久,
所以请求会一直引导到挂掉的服务器上,直到dns缓存更新
总结:
只适用于一些可靠性不高的服务器集群,例如图片服务器集群,纯静态网页服务器集群
3.四/七层负载均衡设备(硬件和软件都有)
第四层:传输层(tcp,udp)
第七层:应用层(http,ftp,smtp,telnet,ssh)
第四层,主要是通过硬件来实现负载均衡的
比如交换机,big-ip负载均衡交换机
软件也有比如LVS
第七层主要是通过软件实现负载均衡,比如nginx,L7SW,HAProxy
4. 复合方式(多线多地区智能DNS解析与混合负载均衡方式)
就是把以上所有的方式都用一遍,还加上一个多线多地区智能DNS
例如当深圳地区用户访问是,会将服务器解析到深圳的机房,反正就是根据区域,让你快点访问
使用dig 来查看这一过程
相关配置属性
upstream中指令
1. ip_hash (在upstream中使用)
使用环境 upstream
保证用户同时只访问一台服务器,解决session的问题
比如一开始在A服务器上登录了,然后Session也在A上,
这个时候如果你下次让它访问B,那Session就丢掉了,
所以最简单的方式不是是同步所有的集群中的session(首先浪费资源),
而是让这个用户这次访问始终在A上就行了,所以说这个功能真的好
细节:
如果使用了ip_hash功能,如果upstream4台机器中有一台服务器不能用了(比如你想维护),不能直接注释,而要使用down
因为如果直接注释,ip_hash就是对3台机器,会导致可能之前访问A的用户被调配访问B,这样就失败了,
而使用down,还是保持四台来hash,但是nginx会避免后面的用户进入第3台服务器,这是为了保证之前用户的正常使用
upstream
{
ip_hash;
server backend1.domain.com;
server backend2.domain.com;
server backend3.domain.com down;
server backend4.domain.com;
}
2. server
使用环境 upstream
weight=NUMBER 权重,值越大,表示被分配到的客户端请求越多,默认是1
max_fials=NUMBER 在参数fail_timeout制定的时间内对后端服务器请求失败的次数,如果检测到后端服务器不能连接及发生错误(404除外),则标记为失败
默认是1,如果设为0,则表示关闭这项检查
fail_timeout=TIME 在经历max_fails设置的失败次数后,暂停的时间
down 标记服务器位永久离线状态,对ip_hash有用
baskup 仅仅在飞backup服务器全部宕机或繁忙时才启用
3. upstream
使用环境: http
可以在proxy_pass, fastcgi_pass 中设置代理服务器集群,默认负载均衡方式是轮询(挨个来)
upstream的变量有
$upstram_addr #处理请求的upstream服务器地址
$upstram_status #upstream服务器的reponse status
$upstream_response_time #upstream response time,多个响应已逗号和冒号分割
$upstream_http_$HEADER #任意的http header,比如$upstream_http_host 等
$upstream_http_host 等
案例,双机高可用(两台以上的反向代理服务器)
需要两台以上的nginx负载均衡服务器来实现故障转移和高可用
第一种方式,1个备胎
就是只用一台服务器做负载均衡,然后另一台备着,一旦出现故障,切换到那台
1. www.yourdomain.com 解析到虚拟ip61.1.1.2
2. 主机61.1.1.4绑定虚拟ip 61.1.1.2
sudo ifconfig eth0:1 61.1.1.2 boradcast 61.1.1.255 netmask 255.255.255.0 up
sudo route add -host 61.1.1.2 dev eth0:1
sudo arping -I etho0 -c 3 -s 61.1.1.2 61.1.1.1
3. 用户访问61.1.1.2(虚拟ip,ip别名) 实际访问的是61.1.1.4,而备用机61.1.1.5则处于空闲状态
4. 如果61.1.1.4 发生故障备机61.1.1.5将在几秒内接管虚拟ip61.1.1.2与自己绑定,并发送ARPing包给IDC的公网网关刷新MAC地址
61.1.1.5 绑定61.1.1.2 代码和上面一样,但是应该换了执行的服务器吧
sudo ifconfig eth0:1 61.1.1.2 broadcast 61.1.1.255 netmask 255.255.255.0 up
sudo route add -host 61.1.1.2 dev eth0:1
sudo arping -I eth0 -c 3 -s 61.1.1.2 61.1.1.1
5. 这是客户端访问61.1.1.2 就解析到了 61.1.1.5
我自己的构想,比如在一个服务器上运行一个shell,然后没秒发送数据包(比如ping)给61.1.1.4,
如果失败则使用ssh远程执行61.1.1.2绑定到备用服务器61.1.1.5,如果下次访问正常了,则重新绑定会61.1.1.4
可以利用Keepalived软件来实现
跳包之所以叫心跳包是因为:它像心跳一样每隔固定时间发一次
第二种方式,两台反向代理服务器都工作
1. 设置dns轮询解析到虚拟ip 61.1.1.2 和 61.1.1.3 上
2. 正常情况下61.1.1.4绑定到61.1.1.2 ,61.1.1.5绑定到61.1.1.3
在61.1.1.4中执行
sudo ifconfig eth0:1 61.1.1.2 broadcast 61.1.1.255 netmask 255.255.255.0 up
sudo route add -host 61.1.1.2 dev eth0:1
sudo arping -I eth0 -c 3 -s 61.1.1.2 61.1.1.1
在61.1.1.5中执行
sudo ifconfig eth0:1 61.1.1.3 broadcast 61.1.1.255 netmask 255.255.255.0 up
sudo route add -host 61.1.1.3 dev eth0:1
sudo arping -I eth0 -c 3 -s 61.1.1.3 61.1.1.1
3. 用户访问61.1.1.2,61.1.1.3 是根据dns轮询来的,两台实际的反向代理服务器61.1.1.4, 61.1.1.5都处于活动状态
4. 如果其中一台挂了,另一台服务器就绑定之前那台服务器绑定的虚拟ip
比如61.1.1.4挂了,那么在61.1.1.5中就直接绑定61.1.1.2,这样61.1.1.5就同时绑定了两个虚拟ip,两个虚拟ip转到的都是这台服务器
在61.1.1.5中执行
sudo ifconfig eth0:1 61.1.1.2 broadcast 61.1.1.255 netmask 255.255.255.0 up
sudo route add -host 61.1.1.2 dev eth0:1
sudo arping -I eth0 -c 3 -s 61.1.1.2 61.1.1.1
还是利用shell来完成这个工作,对两台服务器都定时发送数据包,如果其中一台挂了,另一台远程执行绑定
shell example
[shell example](balance.sh)
配置(nginx中loadblance就是通过反向代理来设置的)
http
{
#用户客户端请求的最大单个文件字节数
client_max_body_size 10m;
#代理服务器缓存最大字节数,可以理解成先保存在代理服务器这,然后再发送被用户
client_body_buffer_size 128k;
#和后台服务器连接超时,超过就失败了,可能会有重连,反正你不能一直占着
proxy_connect_timeout 600;
#连接之后,等待服务器响应的时间
proxy_read_timeout 600;
#在规定的时候,后端服务器必须传送完
proxy_send_timeout 600;
#代理请求缓存去,主要保存request header
proxy_buffer_size 16k;
#告诉nginx 保存上面的request header一共用几个buffer,以及每个buffer最大的size
proxy_buffers 4 32k;
#如果系统很忙时可以将上面的的最大size 32k 升级成 64k,官方推荐2倍
proxy_busy_buffers_size 64k;
#proxy临时文件的大小
proxy_temp_file_write_size 64k;
Upstream php_server_pool
{
server 192.168.0.43:80 weight=4 max_fails=2 fail_timeout=30s;
server 192.168.0.44:80 weight=4 max_fails=2 fail_timeout=30s;
server 127.0.0.1:80 weight=4 max_fails=2 fail_timeout=30s;
}
Upstream message_server_pool
{
server 192.168.1.13:3245;
server 192.168.2.24:3245 down;
}
Upstream bbs_server_pool
{
server 192.168.1.15:80 weight=1 max_fail=2 fail_timeout=30s;
server 192.168.1.16:80 weight=1 max_fail=2 fail_timeout=30s;
server 192.168.1.17:80 weight=1 max_fail=2 fail_timeout=30s;
server 192.168.1.18:80 weight=1 max_fail=2 fail_timeout=30s;
}
#第一个虚拟主机,反向代理php_server_pool
server
{
listen 80;
server_name a.domain.com;
location /
{
#如果后端服务器返回502 504 执行超时等错误,自动讲求转发到upstream负载均衡pool中的另一台服务器,实现故障转移
proxy_next_upstream http_502 http_504 error timeout invalid_header;
#设置关联的Upstream
proxy_pass http://php_server_pool;
#设置显示的Host名称
proxy_set_header Host a.domain.com;
#记录客户端实际的ip地址
proxy_set_header x-Forwarded-For $remote_addr;
}
access_log /data1/logs/www.yourdamain.com_access.log;
}
#第二个虚拟主机,在部分url访问中使用message_server_pool
server
{
listen 80;
server_name b.domain.com;
#设置当访问 http://b.domain.com/message/*** 时,反向代理message_server_pool下的这组服务器
location /message/
{
proxy_pass http://message_server_pool;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $remote_addr;
}
access_log /data1/logs/b.domain.com_access.log;
}
#第三个虚拟主机,
server
{
listen 80;
# 可以设置多个域名
server_name bbs.domain.com *.bbs.domain.com c.domain.com;
location /
{
proxy_pass http://bbs_server_pool;
proxy_set_header Host $host;
proxy_set_header X-Forwarded-For $remote_addr;
}
access_log off;
}
}