nginx 基本知识
location 匹配url
- 优先级:
- [精确匹配(同等类型顺序越前,优先级越高)]
- [开头匹配(同等类型长度越长,优先级越高)]
- [正则匹配(同等类型顺序越前,优先级越高)]
- [通用匹配(同等类型长度越长,优先级越高)]
- 语法规则:location [=|^~|~|~*] /uri/ {…} 先匹配普通location,在匹配正则location
| 类型 | 操作符 | 含意 |
|---|---|---|
| 精确匹配 | = | = /hello :完全相等 |
| 开头匹配 | ^~ | ^~ /hello/yesno : uri以某个常规字符串开头,理解为匹配url路径即可,无需考虑编解码 |
| 正则匹配 | ~ | ~ /hello/y[a-e][e-z] : 开头表示区分大小写的正则匹配 |
| 正则匹配 | ~* | location ~* /hello/y[a-e][a-z][1-9] : 开头表示不区分大小写的正则匹配 |
| 正则匹配 | !~ | 开头表示区分大小写的不匹配的正则匹配 |
| 正则匹配 | !~* | 开头表示不区分大小写的不匹配的正则匹配 |
| 通用匹配 | / | /hello/no : 任何请求都会被匹配到 |
设置静态资源的过期时间
服务器静态资源是否过期 存在两个判断机制的:
- 新鲜度检测阶段:需要依赖响应头的Cache-Control/Expires,通过才会返回200(from cache)
- 资源二次校验阶段:校验资源一致性,Last-Modified/ETag 这两个数据用于确定数据是否改变.如果一致返回304,如果不一致返回200,当然,如果没有找到返回404
expires指令用来对浏览器本地缓存的控制,指令可以放置在http {},server {},location {}或位置{}块内的if语句中
- 当没有设置expires指令时:
curl -I http://0.0.0.0/logo.png
HTTP/1.1 200 OK
Server: nginx/1.10.3 (Ubuntu)
Date: Fri, 22 Jun 2018 03:16:20 GMT
Content-Type: image/png
Content-Length: 18
Connection: keep-alive
Pragma: public
Cache-Control: public
- 当设置expires指令时:
curl -I http://0.0.0.0/logo.png
HTTP/1.1 200 OK
Server: nginx/1.10.3 (Ubuntu)
Date: Fri, 22 Jun 2018 03:16:20 GMT
Content-Type: image/png
Content-Length: 18
Connection: keep-alive
Pragma: public
Cache-Control: public
Expires: Sun, 22 Jul 2018 03:16:20 GMT
Cache-Control: max-age=2592000
遇到的坑(一直没有效果)
- 想着是否还需要额外的模块支持
- 参数是否增加的不够全(还要加请求头)
- location匹配是否有错误
- 各种变着法的换其它各种形式的写法
server_name问题(要写明name,不然只会匹配 location / {…}规则)
- 没有添加 0.0.0.0
- http://0.0.0.0/ 可正常访问
- http://localhost/ 可正常访问
- http://127.0.0.1/ 可正常访问
- http://0.0.0.0/hello 不可正常访问
- http://localhost/hello 可正常访问
- http://127.0.0.1/hello 不可正常访问
- 新添加 0.0.0.0后
- http://0.0.0.0/ 可正常访问
- http://localhost/ 可正常访问
- http://127.0.0.1/ 可正常访问
- http://0.0.0.0/hello 可正常访问
- http://localhost/hello 可正常访问
- http://127.0.0.1/hello 不可正常访问
- 没有添加 0.0.0.0
解决的方法:原因居然是server_name 没有加0.0.0.0(在命令行和浏览器中测试都是使用0.0.0.0)
缓存服务器设置(配置proxy_cahe):只是针对API后端,所以才需要 proxy_pass或者 uwsgi_pass配置才生效
- 参数说明:
| 指令 | 指令与参数值 | 含意 |
|---|---|---|
| proxy_cache_path | /tmp/nginx | cache这个zone的文件要存放的目录,会在已经的路径下生成一个目录 |
| proxy_cache_path | levels=1:2 | 表示缓存目录的第一级目录是1个字符,第二级目录是2个字符. 即/tmp/nginx/a/1b这种形式 |
| proxy_cache_path | keys_zone=cache:10m | zone名称为cache1,分配的内存大小为10MB |
| proxy_cache_path | inactive=1d | 这个zone中的缓存文件如果在1天内都没有被访问,那么文件会被cache manager进程删除掉 |
| proxy_cache_valid | 200 304 30m | 设置状态码为200和304的响应可以进行缓存,并且缓存时间为30分钟 |
| upstream_cache_status | MISS | 未命中,请求被传送到后端 |
| upstream_cache_status | HIT | 缓存命中 |
| upstream_cache_status | EXPIRED | 缓存已经过期请求被传送到后端 |
| upstream_cache_status | UPDATING | 正在更新缓存,将使用旧的应答 |
| upstream_cache_status | STALE | 后端将得到过期的应答 |
| upstream_cache_status | BYPASS | 缓存被绕过了 |
遇到的坑(也一直没有效果)
- proxy_pass http://0.0.0.0/; # uwsgi启动的话,则将对应的proxy设置换成uwsgi即可
查看是否生效
curl -I http://0.0.0.0/logo.png X-Cache: MISS X-Cache: HIT # 第二次请求,如果是HIT,则表示缓存生效
最终配置如下:
proxy_cache_path /tmp/nginx levels=1:2 keys_zone=cache:10m inactive=60m;
map $sent_http_content_type $expires {
default off;
text/html epoch;
text/css max;
application/javascript max;
image/png 2d;
~*\.(jpg|jpeg|png|gif|ico|css|js|pdf)(\?|$) 7d;
}
server {
listen 80;
server_name 0.0.0.0 localhost ;
location = /hello {
return 302 https://www.baidu.com;
}
# expires 1d;
# location ~* .*\.(ico|css|js|gif|jpe?g|png|woff|woff2|eot|svg|ttf|)$ {
# expires 1d;
# }
# location ~* \.(jpg|jpeg|png|gif){
# expires 1d;
# }
# location = /logo.png {
# root /usr/share/nginx/html;
# expires 30d;
# access_log off;
# log_not_found off;
# add_header Pragma public;
# add_header Cache-Control "public"; # 任何系统都可以缓存它们
# }
# expires $expires; # 这种方式在chrome,firefox没有Expires,在命令行中就有
location / {
root /usr/share/nginx/html;
index index.html;
if ($request_uri ~* "\.(ico|css|js|gif|jpe?g|png)$") {
expires 30d;
access_log off;
add_header Cache-Control "public";
}
proxy_cache cache;
proxy_cache_valid 200 301 304 30m;
proxy_pass http://0.0.0.0:8000;
# 缓存 key 的值
proxy_cache_key $host$uri$is_args$args;
# proxy_cache_key "$scheme$request_method$host$request_uri";
proxy_cache_use_stale updating error timeout invalid_header http_500 http_502 http_503 http_504;
expires 1m;
# 将缓存的状态添加到 Header 中
add_header X-Cache '$upstream_cache_status';
}
}
缓存服务器设置发生在:API后端和Nginx静态文件分离情况的配置文件(适用后端接口不是实时的改变的)
uwsgi_cache_path /tmp/nginx_cache/ levels=1:2 keys_zone=mycache:10m max_size=10g inactive=10m use_temp_path=off;
# the upstream component nginx needs to connect to
upstream uwsgi {
server unix:/code/app.sock; # for a file socket
}
# configuration of the server
server {
# the port your site will be served on
listen 80;
server_name 0.0.0.0;
charset utf-8;
# add_header Accept-Ranges bytes;
# add_header Content-Encoding identity;
# add_header Accept-Encoding identity;
# add_header Range bytes=0-;
client_max_body_size 75M; # adjust to taste
# Django media
location /media {
alias /code/media; # your Django project's media files - amend as required
if ($request_uri ~* "\.(ico|gif|jpe?g|png|woff|woff2|eot|svg|ttf|mp4)$") {
expires 3d;
access_log off;
add_header Cache-Control "public";
}
}
location /static {
alias /code/static; # your Django project's static files - amend as required
if ($request_uri ~* "\.(css|js)$") {
expires 1d;
access_log off;
add_header Cache-Control "public";
}
}
location /favicon.ico {
alias /code/media/logo.png; # your Django project's static files - amend as required
}
# / 必须放在最后,不能覆盖静态url配置
location / {
add_header X-uWSGI-Cache $upstream_cache_status;
# server cache
uwsgi_cache mycache;
uwsgi_cache_valid 200 301 1m;
slice 1m;
proxy_set_header Range $slice_range;
proxy_set_header Range $http_range;
# proxy_cache_valid 200 301 304 30m;
uwsgi_cache_key $request_uri;
# client cache
expires 3d;
uwsgi_pass uwsgi;
include /etc/nginx/uwsgi_params; # the uwsgi_params file you installed
}
}