Nginx提供静态内容
本节介绍如何配置NGINX和NGINX Plus以提供静态内容,如何定义搜索哪些路径以查找请求的文件,如何设置索引文件以及如何调整NGINX和NGINX Plus以及内核,以便最佳性能。
根目录和索引文件
该root
伪指令指定将用于搜索文件的根目录。为了获得请求文件的路径,NGINX将请求URI附加到root
伪指令指定的路径。该指令可以被放置于内的任何级别,或上下文。在下面的示例中,该指令是为虚拟服务器定义的。它适用于不包含该指令以显式重新定义根的所有块:http {}
server {}
location {}
root
location {}
root
server {
root /www/data;
location / {
}
location /images/ {
}
location ~ \.(mp3|mp4) {
root /www/media;
}
}
在这里,NGINX 在文件系统/images/
的/www/data/images/
目录中搜索以URI开头的URI 。但是,如果URI以.mp3
或.mp4
扩展名结尾,则NGINX会在/www/media/
目录中搜索文件,因为它是在匹配location
块中定义的。
如果请求以斜杠结尾,NGINX会将其视为对目录的请求,并尝试在目录中查找索引文件。该index
指令定义索引文件的名称(默认值为index.html
)。继续该示例,如果请求URI为/images/some/path/
,则NGINX传送文件(/www/data/images/some/path/index.html
如果存在)。如果不是,则默认情况下NGINX返回HTTP代码。要将NGINX配置为返回自动生成的目录列表,请在伪指令中包含参数:404 (Not Found)
on
autoindex
location /images/ {
autoindex on;
}
您可以在index
指令中列出多个文件名。NGINX按照指定的顺序搜索文件,并返回找到的第一个文件。
location / {
index index.$geo.html index.htm index.html;
}
$geo
这里使用的变量是通过geo
指令设置的自定义变量。变量的值取决于客户端的IP地址。
为了返回索引文件,NGINX检查其存在,然后对通过将索引文件的名称附加到基本URI所获得的URI进行内部重定向。内部重定向将导致对位置的新搜索,并可能最终到达另一个位置,如以下示例所示:
location / {
root /data;
index index.html index.php;
}
location ~ \.php {
fastcgi_pass localhost:8000;
#...
}
在此,如果请求中的URI是/path/
,并且/data/path/index.html
不存在但/data/path/index.php
存在,则将内部重定向到/path/index.php
映射到第二个位置。结果,该请求被代理。
尝试几种选择
该try_files
伪指令可用于检查指定的文件或目录是否存在;NGINX会进行内部重定向,否则会返回指定的状态码。例如,要检查是否存在与请求URI相对应的文件,请使用try_files
伪指令和$uri
变量,如下所示:
server {
root /www/data;
location /images/ {
try_files $uri /images/default.gif;
}
}
该文件以URI的形式指定,该URI使用在当前位置或虚拟服务器的上下文中设置的root
或alias
指令进行处理。在这种情况下,如果不存在与原始URI对应的文件,则NGINX将内部重定向到由最后一个参数指定的URI,返回/www/data/images/default.gif
。
最后一个参数也可以是状态代码(直接在等号后)或位置名称。在以下示例中,404
如果try_files
指令的任何参数都无法解析到现有文件或目录,则将返回错误。
location / {
try_files $uri $uri/ $uri.html =404;
}
在下一个示例中,如果原始URI或带有尾随斜杠的URI都无法解析到现有文件或目录中,则该请求将被重定向到指定的位置,该位置会将其传递给代理服务器。
location / {
try_files $uri $uri/ @backend;
}
location @backend {
proxy_pass http://backend.example.com;
}
有关更多信息,请观看“ 内容缓存”网络研讨会,以了解如何显着提高网站的性能,并深入了解NGINX的缓存功能。
优化性能以提供内容
加载速度是提供任何内容的关键因素。对您的NGINX配置进行小的优化可能会提高生产率并帮助达到最佳性能。
启用 sendfile
默认情况下,NGINX自行处理文件传输,并在发送文件之前将文件复制到缓冲区中。启用sendfile
指令可以消除将数据复制到缓冲区的步骤,并可以将数据从一个文件描述符直接复制到另一个文件描述符。另外,为防止一个快速连接完全占用工作进程,您可以使用sendfile_max_chunk
指令将单个sendfile()
调用中传输的数据量(在此示例中为1
MB)限制为:
location /mp3 {
sendfile on;
sendfile_max_chunk 1m;
#...
}
启用 tcp_nopush
将tcp_nopush
指令与指令一起使用。这样一来,NGINX即可在通过数据获取数据块后立即在一个数据包中发送HTTP响应标头。sendfile
on;
sendfile()
location /mp3 {
sendfile on;
tcp_nopush on;
#...
}
启用 tcp_nodelay
该tcp_nodelay
指令允许覆盖Nagle的算法,该算法最初旨在解决速度较慢的网络中的小数据包问题。该算法将多个小数据包合并为一个较大的数据包,并以200
ms的延迟发送数据包。如今,在处理大型静态文件时,无论数据包大小如何,都可以立即发送数据。延迟还会影响在线应用程序(SSH,在线游戏,在线交易等)。默认情况下,tcp_nodelay
伪指令设置为on
,这意味着Nagle的算法被禁用。仅在保持活动连接时使用此伪指令:
location /mp3 {
tcp_nodelay on;
keepalive_timeout 65;
#...
}
优化积压队列
重要的因素之一是NGINX可以处理传入连接的速度。一般规则是,建立连接后,将其放入侦听套接字的“侦听”队列中。在正常负载下,队列很小或根本没有队列。但是在高负载下,队列会急剧增长,从而导致性能不均匀,连接断开和延迟增加。
显示监听队列
要显示当前侦听队列,请运行以下命令:
netstat -Lan
输出可能类似于以下内容,该结果表明在端口上的侦听队列中, 80
在已10
配置的最大128
队列连接数中,存在不可接受的连接。这种情况是正常的。
Current listen queue sizes (qlen/incqlen/maxqlen)
Listen Local Address
0/0/128 *.12345
10/0/128 *.80
0/0/128 *.8080
相反,在以下命令中,不可接受的连接数(192
)超过了限制128
。当网站流量很大时,这是很常见的。为了获得最佳性能,您需要增加操作系统和NGINX配置中排队等待NGINX接受的最大连接数。
Current listen queue sizes (qlen/incqlen/maxqlen)
Listen Local Address
0/0/128 *.12345
192/0/128 *.80
0/0/128 *.8080
调整操作系统
将net.core.somaxconn
内核参数的值从其默认值(128
)增加到足以引起大量流量的高值。在此示例中,将其增加到4096
。
-
对于FreeBSD,运行命令:
sudo sysctl kern.ipc.somaxconn=4096
-
对于Linux:
-
运行命令:
sudo sysctl -w net.core.somaxconn=4096
-
使用文本编辑器将以下行添加到
/etc/sysctl.conf
:net.core.somaxconn = 4096
-
调优NGINX
如果将somaxconn
内核参数设置为大于的值512
,请将backlog
参数更改为NGINX listen
指令以匹配:
server {
listen 80 backlog=4096;
# ...
}