一.什么是nginx
Nginx (engine x) 是一个 高性能的 HTTP和 反向代理web服务器,是一款由俄罗斯的程序设计师Igor Sysoev使用c语言开发的 轻量级的 Web 服务器/反向代理服务器及 电子邮件(IMAP/POP3)代理服务器,官方测试nginx能够支支撑5万并发链接,在BSD-like 协议下发行,运行非常稳定。其特点是占有 内存少, 并发能力强,资源消耗非常低,事实上nginx的并发能力确实在同类型的网页服务器中表现较好,中国大陆使用nginx网站用户有:百度、京东、腾讯、淘宝等
二.为什么使用Nginx
在传统的Web项目中,并发量小,用户使用的少,所以在低并发的情况下,用户可以直接访问tomcat服务器,然后tomcat服务器返回消息给用户,而在互联网项目下,因单个tomcat默认并发量有限制。如果请求量过大,会产生如下问题:
(1).Tomcat 默认配置的最大请求数是 150,也就是说同时支持 150 个并发,当然了,也可以将其改大
(2).当某个应用拥有 250 个以上并发的时候,应考虑应用服务器的集群
(3).具体能承载多少并发,需要看硬件的配置,CPU 越多性能越高,分配给 JVM 的内存越多性能也就越高,但也会加重 GC 的负担
(4).操作系统对于进程中的线程数有一定的限制:
Windows 每个进程中的线程数不允许超过 2000
Linux 每个进程中的线程数不允许超过 1000
(在 Java 中每开启一个线程需要耗用 1MB 的 JVM 内存空间用于作为线程栈之用)
(5).Tomcat的最大并发数是可以配置的,实际运用中,最大并发数与硬件性能和CPU数量都有很大关系的。更好的硬件,更多的处理器都会使Tomcat支持更多的并发
maxThreads="150" 最大并发数
minSpareThreads="10"//初始化时创建的线程数
maxSpareThreads="500"//一旦创建的线程超过这个值,Tomcat就会关闭不再需要的socket线程
所以,当并发数过大时,Tomcat就不足以支持我们的项目了,那么我们就可以使用nginx来替代tomcat,因为nginx具有高并发、高性能,可扩展性好,高可靠性,热部署,内存消耗少,成本低,稳定性高,支持重写机制,BSD许可证等特点
Nginx专为性能优化而开发,性能是其最重要的考量,实现上非常注重效率 。它支持内 核Poll模型,能经受高负载的考验,有报告表明能支持高达 50,000个并发连接数。
Nginx具有很高的稳定性,其它HTTP服务器当遇到访问的峰值,或者有人恶意发起慢速连接时,也很可能会导致服务器物理内存耗尽频繁交换,失去响应只能重启服务器。例如当前Apache一旦上到200个以上进程,web响应速度就明显非常缓慢了。而Nginx采取了分阶段资源分配技术,使得它的CPU与内存占用率非常低。
Nginx官方表示保持 10,000个没有活动的连接,它只占2.5M内存,所以类似DOS这样的攻击对Nginx来说基本上是毫无用处的。
就稳定性而言,nginx比lighttpd更胜一筹。
Nginx支持热部署,它的启动特别容易, 并且几乎可以做到7*24不间断运行,即使运 行数个月也不需要重新启动。你还能够在不间断服务的情况下,对软件版本进行进行升级。
Nginx采用master-slave模型,能够充分利用SMP的优势,且能够减少工作进程在磁 盘I/O的阻塞延迟。
Nginx代码质量非常高,代码很规范,手法成熟, 模块扩展也很容易。
Nginx采用了一些os提供的最新特性如对sendfile (Linux2.2+),accept-filter(FreeBSD4.1+),TCP_DEFER_ACCEPT (Linux 2.4+)的支持,从而大大提高了性能
特点:
1.高并发(High Concurrency)
是互联网分布式系统架构设计中必须考虑的因素之一,它通常是指,通过设计保证系统能够同时并行处理很多请求,高并发相关常用的一些指标有响应时间(Response Time),吞吐量(Throughput),每秒查询率QPS(Query Per Second),并发用户数等
官方测试能够支撑5万并发连接,在实际生产环境中跑到2~3万并发连接数
响应时间
系统对请求做出响应的时间。例如系统处理一个HTTP请求需要200ms,这个200ms就是系统的响应时间
吞吐量
单位时间内处理的请求数量
QPS
每秒响应请求数。在互联网领域,这个指标和吞吐量区分的没有这么明显
并发用户数
同时承载正常使用系统功能的用户数量
2.高可用(High Availability)
通常来描述一个系统经过专门的设计,从而减少停工时间,而保持其服务的高度可用性。
(一直都能用 99.9999%)
3.高性能
是指服务响应时间快,(CPU/处理器/内存)特别是在高并发下响应时间不会急剧增加
4.内存消耗少
在3万并发连接下,开启的10个Nginx 进程才消耗150M内存(15M*10=150M)
5.配置文件简单
风格跟程序一样通俗易懂
6.成本低
Nginx为开源软件,可以免费使用。而购买F5 BIG-IP、NetScaler等硬件负载均衡交换机则需要十多万至几十万人民币
7.支持重写机制
能够根据域名、URL的不同,将 HTTP 请求分到不同的后端服务器群组
8.内置的健康检查功能
如果 Nginx Proxy 后端的某台 Web 服务器宕机了,不会影响前端访问
9.节省带宽
支持 GZIP 压缩,可以添加浏览器本地缓存的 Header 头
10.稳定性高
用于反向代理,宕机的概率微乎其微
三.nginx可以用来做什么
1.http服务器
Nginx是一个http服务可以独立提供http服务,可以做网页静态资源服务器
2.虚拟主机
虚拟主机是用来映射网站域名和网站代码文件夹的关系.它可以通过server配置, 每个server表示一个虚拟机主机,实现在一台服务器虚拟出多个网站,例如个人网站使用的虚拟主机
基于端口的,不同的端口
基于域名的,不同域名
标准虚拟主机配置
http {
#默认的虚拟机主机
server {
listen 80 default;
server_name localhost;
access_log logs/default.access.log main;
location / {
index index.html;
root /var/www/default/htdocs;
}
}
#www.domain1.com对应的虚拟主机
server {
listen 80;
server_name www.domain1.com;
#access_log logs/domain1.access.log main;
location / {
index index.html;
root /var/www/domain1.com/htdocs;
}
}
#www.domain2.com对应的虚拟主机
server {
listen 80;
server_name www.domain2.com;
access_log logs/domain2.access.log main;
location / {
index index.html;
root /var/www/domain2.com/htdocs;
}
}
}
建议的配置方式
建议将每个虚拟主机放置到一个文件中,以上全部配置在主配置文件中可能不小心修改掉配置文件导致nginx.conf文件出错. 可以使include指令将每个虚拟主机放在一个单独的配置文件中,
将nginx服务器目录结构设置为:
nginx
nginx.conf
vhost
-- www.domain1.com.conf
-- www.domain2.com.conf
每个.conf结尾的文件中保存一个虚拟主机(server)的配置信息.在nginx.conf中通过include指令包含这些配置文件
在nginx/config/nginx.conf中的配置
http {
#默认的虚拟机主机
server {
listen 80 default;
server_name _ *;
access_log logs/default.access.log main;
location / {
index index.html;
root /var/www/default/htdocs;
}
}
include vhost/*.conf;
}
在nginx/config/vhost/www.domain1.com.conf中的配置
server {
listen 80;
server_name www.domain1.com;
access_log logs/domain1.access.log main;
location / {
index index.html;
root /var/www/domain1.com/htdocs;
}
}
在nginx/config/vhost/www.domain2.com.conf中的配置
server {
listen 80;
server_name www.domain2.com;
access_log logs/domain2.access.log main;
location / {
index index.html;
root /var/www/domain2.com/htdocs;
}
}
3.反向代理,负载均衡服务器
反向代理说明
反向代理(Reverse Proxy)方式是指以代理服务器来接受internet上的连接请求,然后将请求转发给内部网络上的服务器,并将从服务器上得到的结果返回给internet上请求连接的客户端,此时代理服务器对外就表现为一个反向代理服务器
web前端服务器: 代理服务器可以作为前端服务器处理静态资源
web后端服务器: web前端服务器无法处理的动态请求发送给后台web服务器处理
特点
反向代理又称为Web服务器加速,是针对Web服务器提供加速功能的。它作为代理Cache,但并不针对浏览器用户,而针对一台或多台特定Web服务器(这也是反向代理名称的由来)。代理服务器可以缓存一些web的页面,降低了web服务器的访问量,所以可以降低web服务器的负载。web服务器同时处理的请求数少了,响应时间自然就快了。同时代理服务器也存了一些页面,可以直接返回给客户端,加速客户端浏览
正向代理说明
是一个位于客户端和原始服务器(origin server)之间的服务器,为了从原始服务器取得内容,客户端向代理发送一个请求并指定目标(原始服务器),然后代理向原始服务器转交请求并将获得的内容返回给客户端,客户端才能使用正向代理
正向代理和反向代理区别
正向代理, 是在客户端的,比如需要访问某些国外网站,我们可能需要购买vpn,并且 vpn是在我们的用户浏览器端设置的(并不是在远端的服务器设置),浏览器先访问vpn地址,vpn地址转发请求,并最后将请求结果原路返回来
反向代理是作用在服务器端的,是一个虚拟ip(VIP),对于用户的一个请求,会转发到多个后端处理器中的一台来处理该具体请求
负载均衡说明
负载均衡( 将服务器接收到的请求按照规则分发的过程,称为负载均衡)是高可用网络基础架构的的一个关键组成部分,有了负载均衡,我们通常可以将我们的应用服务器部署多台,然后通过负载均衡将用户的请求分发到不同的服务器用来提高网站、应用、数据库或其他服务的性能以及可靠性。 比如:当网站的访问量达到一定程度后,单台服务器不能满足用户的请求时,需要用多台服务器做集群,这时可以使用nginx做反向代理。并且多台服务器可以平均分担负载,不会因为某台服务器负载高宕机而某台服务器闲置的情况
具体配置
#当用户访问php文件时,将该请求交给apache服务器处理php文件
server {
#侦听192.168.8.x的80端口
listen 80;
server_name www.xxx.cn;
#对php后缀的进行请求
location ~ .*\.php$ {
#定义服务器的默认网站根目录位置
root /root;
#定义首页索引文件的名称
index index.php index.html index.htm;
#请求转向apache服务器,apache服务器运行在81端口上
proxy_pass http://localhost:81;
#以下是一些反向代理的配置可删除.
proxy_redirect off;
#后端的Web服务器可以通过X-Forwarded-For获取用户真实IP
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
#允许客户端请求的最大单文件字节数
client_max_body_size 10m;
#缓冲区代理缓冲用户端请求的最大字节数,
client_body_buffer_size 128k;
#nginx跟后端服务器连接超时时间(代理连接超时)
proxy_connect_timeout 90;
#连接成功后,后端服务器响应时间(代理接收超时)
proxy_read_timeout 90;
#设置代理服务器(nginx)保存用户头信息的缓冲区大小
proxy_buffer_size 4k;
#proxy_buffers缓冲区,网页平均在32k以下的话,这样设置
proxy_buffers 4 32k;
#高负荷下缓冲大小(proxy_buffers*2)
proxy_busy_buffers_size 64k;
#设定缓存文件夹大小,大于这个值,将从upstream服务器传
proxy_temp_file_write_size 64k;
}
}
工作中的使用
建议将代理相关的配置放在一个单独的文件中,在需要使用的地方,引入即可
proxy.conf
#存放代理配置的nginx/conf/proxy.conf: 其他的server虚拟主机都可以使用该配置.
#以下是一些反向代理的配置可删除.
proxy_redirect off;
#后端的Web服务器可以通过X-Forwarded-For获取用户真实IP
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
#允许客户端请求的最大单文件字节数
client_max_body_size 10m;
#缓冲区代理缓冲用户端请求的最大字节数,
client_body_buffer_size 128k;
#nginx跟后端服务器连接超时时间(代理连接超时)
proxy_connect_timeout 90;
#连接成功后,后端服务器响应时间(代理接收超时)
proxy_read_timeout 90;
#设置代理服务器(nginx)保存用户头信息的缓冲区大小
proxy_buffer_size 4k;
#proxy_buffers缓冲区,网页平均在32k以下的话,这样设置
proxy_buffers 4 32k;
#高负荷下缓冲大小(proxy_buffers*2)
proxy_busy_buffers_size 64k;
#设定缓存文件夹大小,大于这个值,将从upstream服务器传
proxy_temp_file_write_size 64k;
代理配置文件
使用代理配置文件:
server {
listen 80;
server_name www.xxx.cn;
#对php后缀的进行请求
location ~ .*\.php$ {
#定义服务器的默认网站根目录位置
root /root;
#定义首页索引文件的名称
index index.php index.html index.htm;
#请求转向apache服务器,apache服务器运行在81端口上
proxy_pass http://localhost:81;
#以下是一些反向代理的配置可删除.
include proxy.conf;
}
}
4.动静分离
当用户请求js,css等静态资源时有当前nginx服务器处理, 请求动态脚本代码时由其他的服务器处理(反向代理),动静分离充分利用各自的优势完成高性能访问
#配置Nginx动静分离,定义的静态页面直接从Nginx发布目录读取。
location ~ .*\.(gif|jpg|jpeg|bmp|png|ico|txt|js|css)$
{
#expires定义用户浏览器缓存的时间为3天,如果静态页面不常更新,可以设置更长,这样可以节省带宽和缓解服务器的压力
expires 3d;
}
#动态页面交给其他服务器处理
location ~ .*\.(php|jsp|cgi)?$
{
#发送给其他服务器处理
}
5.做集群
同一个业务,部署在多个服务器上,将一个应用程序,部署到多台服务器上面,然后在这些服务器的前面通过负载均衡服务器来择优选择哪一台服务器去执行;(保证高可用)
6.集群/分布式环境下session处理策略
集群是个物理形态,分布式是个工作方式
分布式:一个业务分拆多个子业务,部署在不同的服务器上
集群:同一个业务,部署在多个服务器上
6.1为什么要处理session?
这个问题想必大多数朋友都知道,在搭建完集群或者分布式环境之后,如果不做任何处理的话,网站将频繁的出现用户未登录的现象。比如:集群中有A、B两台服务器,用户第一次访问网站时,Nginx将用户请求分发到A服务器,这时A服务器给用户创建了一个Session,当用户第二次访问网站时,假设Nginx将用户请求分发到了B服务器上,而这时B服务器并不存在用户的Session,所以就会出现用户未登录的情况,这对用户来说是不可忍受的。
所以我们在搭建集群/分布式环境之后,必须考虑的一个问题就是用户访问产生的session如何处理,即session的共享机制
6.2 解决方案
将处理Session的方式大致分为三种:
(1).Session保持(也有人叫黏性Session)
(2).Session复制
(3).Session共享
6.2.1 Session保持(或者叫黏性Session)
Session保持(会话保持)就是将用户锁定到某一个服务器上。比如上面说的例子,用户第一次请求时,负载均衡器(Nginx)将用户的请求分发到了A服务器上,如果负载均衡器(Nginx)设置了Session保持的话,那么用户以后的每次请求都会分发到A服务器上,相当于把用户和A服务器粘到了一块,这就是Session保持的原理。Session保持方案在所有的负载均衡器都有对应的实现。而且这是在负载均衡这一层就可以解决Session问题。
优点
非常简单,不需要对session做任何处理
缺点
负责不均衡了:
由于使用了Session保持,很显然就无法保证负载的均衡
缺乏容错性:
如果后端某台服务器宕机,那么这台服务器的Session丢失,被分配到这台服务请求的用户还是需要重新登录,所以没有彻底的解决问题
实现方式
以Nginx为例,在upstream模块配置ip_hash属性即可实现粘性Session
容错性,是指软件检测应用程序所运行的软件或硬件中发生的错误并从错误中恢复的能力,通常可以从系统的可靠性、可用性、可测性等几个方面来衡量
6.2.2 Session复制
针对Session保持的容错性缺点,我们可以在所有服务器上都保存一份用户的Session信息。这种将每个服务器中的Session信息复制到其它服务器上的处理办法就称为会话复制。当任何一台服务器上的session发生改变时,该节点会把session的所有内容序列化,然后广播给所有其它节点,不管其他服务器需不需要session,以此来保证Session同步。
优点
可容错,各个服务器间的Session能够实时响应
缺点
将session广播同步给成员,会对网络负荷造成一定压力
6.2.3 Session共享
SpringSession+Redis方式实现
7.web缓存
Nginx可以对不同的文件做不同的缓存处理,配置灵活,并且支持FastCGI_Cache,主要用于对FastCGI的动态程序进行缓存。配合着第三方的ngx_cache_purge,对制定的URL缓存内容可以的进行增删管理