nginx 配置 系列文章(持续更新中...)
一文理清 nginx 中的 location 配置(系列一)
nginx 通过 ngx_http_rewrite_module
模块支持 URI 重写、支持 if 条件判断,但不支持 else。
rewrite 只能放在 server { } 、 location { } 、 if { } 中,并且只能对域名后边的除去传递的参数外的字符串起作用,例如http://aaa.com/a/we/index.php?id=1&u=str
只对/a/we/index.php重写。语法为 rewrite regex replacement [flag];
表面看 rewrite 和 location 功能有点像,都能实现跳转,主要区别在于 rewrite 是在同一域名内更改获取资源的路径,而 location 是对一类路径做控制访问或反向代理,可以 proxy_pass 到其他机器。很多情况下 rewrite 也会写在 location 里,它们的执行顺序是:
如果其中某步 URI 被重写,则重新循环执行1-3,直到找到真实存在的文件;
如果循环超过 10
次,则返回 500 Internal Server Error
错误。
语法:if(condition) {…}
作用域: server
、location
功能:对给定的条件 condition 进行判断。如果为真,大括号内的 rewrite 指令将被执行。if 条件 (conditon) 可以是如下任何内容:
if 中的几种判断条件
=
,!=
比较的一个变量和字符串~
, ~*
与正则表达式匹配的变量,如果这个正则表达式中包含},;则整个表达式需要用” 或’ 包围-f
,!-f
检查一个文件是否存在-d
, !-d
检查一个目录是否存在-e
,!-e
检查一个文件、目录、符号链接是否存在-x
, !-x
检查一个文件是否可执行示例:
set $variable "0"; if ($variable) { # 不会执行,因为 "0" 为 false break; } # 使用变量与正则表达式匹配 没有问题 if ( $http_host ~ "^star\.igrow\.cn$" ) { break; } # 字符串与正则表达式匹配 报错 if ( "star" ~ "^star\.igrow\.cn$" ) { break; } # 检查文件类的 字符串与变量均可 if ( !-f "/data.log" ) { break; } if ( !-f $filename ) { break; }
语法:return code [text];
return code URL;
return URL;
作用域:server
,location
,if
功能:停止处理并将指定的 code 码返回给客户端。 非标准 code 码 444 关闭连接而不发送响应报头。
该指令用于检查一个条件是否符合,如果条件符合,则执行大括号内的语句。If 指令不支持嵌套,不支持多个条件 && 和 || 处理。
从0.8.42版本开始, return 语句可以指定重定向 URI (状态码可以为如下几种 301,302,303,307),
也可以为其他状态码指定响应的文本内容,并且重定向的 URI 和响应的文本可以包含变量。
有一种特殊情况,就是重定向的url可以指定为此服务器本地的 URI,这样的话,nginx 会依据请求的协议 $scheme
, server_name_in_redirect
和 port_in_redirect
自动生成完整的 URI。
示例:如果访问的 URI 以 .sh
或 .bash
结尾,则返回 403
状态码
location ~ .*\.(sh|bash)?$ { return 403; }
语法:rewrite regex replacement [flag];
作用域:server
、location
、if
功能:如果一个URI匹配指定的正则表达式regex,URI就按照 replacement 重写。
rewrite 按配置文件中出现的顺序执行。可以使用 flag 标志来终止指令的进一步处理。
如果 replacement 以 http://
、 https://
或 $ scheme
开始,将不再继续处理,这个重定向将返回给客户端。
示例:第一种情况,重写的字符串带 http://
location ^~ /redirect { # 当匹配前缀表达式 /redirect/(.*)时 请求将被临时重定向到 http://www.$1.com # 相当于 flag 写为 redirect rewrite ^/(.*)$ http://www.$1.com; return 200 "ok"; }
在浏览器中输入 127.0.0.1:8080/redirect/baidu
,则临时重定向到 www.baidu.com
后面的 return 指令将没有机会执行了。
location ^~ /redirect { rewrite ^/(.*)$ www.$1.com; return 200 "ok"; } # 发送请求如下 # curl 127.0.0.1:8080/redirect/baidu # ok
此处没有带 http://
所以只是简单的重写。请求的 URI 由 /test1/baidu 重写为 www.baidu.com
因为会顺序执行 rewrite 指令,所以 下一步执行 return 指令,响应后返回 ok
flag
有四种参数可以选择:
last
停止处理后续 rewrite 指令集,然后对当前重写的新 URI 在 rewrite 指令集上重新查找。break
停止处理后续 rewrite 指令集,并不再重新查找,但是当前location 内剩余非 rewrite 语句和 location 外的 非rewrite 语句可以执行。redirect
如果 replacement
不是以 http://
或 https://
开始,返回 302
临时重定向
permanent
返回 301
永久重定向
示例 1:
# rewrite 后面没有任何 flag 时就顺序执行 # 当 location 中没有 rewrite 模块指令可被执行时 就重写发起新一轮location 匹配 location / { # 顺序执行如下两条rewrite指令 rewrite ^/test1 /test2; rewrite ^/test2 /test3; # 此处发起新一轮 location 匹配 URI为/test3 } location = /test2 { return 200 “/test2”; } location = /test3 { return 200 “/test3”; } # 发送如下请求 # curl 127.0.0.1:8080/test1 # /test3
如果正则表达regex式中包含 “}
” 或 “;
”,那么整个表达式需要用双引号或单引号包围。
示例 2:
location / { rewrite ^/test1 /test2; rewrite ^/test2 /test3 last; # 此处发起新一轮location匹配 uri为/test3 rewrite ^/test3 /test4; proxy_pass http://www.baidu.com; } location = /test2 { return 200 "/test2"; } location = /test3 { return 200 "/test3"; } location = /test4 { return 200 "/test4"; }
发送如下请求 curl 127.0.0.1:8080/test1
返回 /test3
当如果将上面的 location / 改成如下代码
location / { rewrite ^/test1 /test2; # 此处不会发起新一轮location匹配;当是会终止执行后续rewrite模块指令重写后的 URI 为 /more/index.html rewrite ^/test2 /more/index.html break; rewrite /more/index\.html /test4; # 这条指令会被忽略 # 因为 proxy_pass 不是rewrite模块的指令 所以它不会被 break终止 proxy_pass https://www.baidu.com; }
发送请求 127.0.0.1:8080/test1
代理到 https://www.baidu.com
rewrite 后的请求参数:
如果替换字符串 replacement
包含新的请求参数,则在它们之后附加先前的请求参数。如果你不想要之前的参数,则在替换字符串 replacement
的末尾放置一个问号,避免附加它们。
# 由于最后加了个 ?,原来的请求参数将不会被追加到 rewrite 之后的 URI 后面* rewrite ^/users/(.*)$ /show?user=$1? last;
语法:rewrite_log on | off;
默认值:rewrite_log off;
作用域:http
、 server
、 location
、 if
功能:开启或关闭以 notice 级别打印 rewrite 处理日志到 error log 文件。
语法:set variable value;
默认值:none
作用域:server
、 location
、 if
定义一个变量并赋值,值可以是文本,变量或者文本变量混合体。
作用域:http
、 server
、 location
、 if
语法:uninitialized_variable_warn on | off;
默认值:uninitialized_variable_warn on
功能:控制是否记录 有关未初始化变量的警告。
本文参考/引用:
nginx配置location总结及rewrite规则写法 - Sean’s Notes - 思否
nginx rewrite 指令 - nginx 中文手册
nginx配置location总结及rewrite规则写法 - seanlook - 思否
推荐阅读:
【专题:JavaScript进阶之路】
一文理清nginx中的location配置(系列一)
JavaScript中各种源码实现(前端面试笔试必备)
深入理解 ES6 Promise
前端性能优化小结(面试干货)
ES6 尾调用和尾递归
我是Cloudy,现居上海,一只勤劳的前端攻城狮,爱专研,爱技术,爱分享。
个人笔记,整理不易,再次感谢阅读
、点赞
、收藏
和关注
!
文章有任何问题欢迎大家指出,也欢迎大家一起交流学习!