上一篇文章咱们用echo模块作了试验,此次咱们来看看官方文档,这是地址: http://nginx.org/en/docs/http/ngx_http_core_module.html#location , 我尝试着翻译以下。html
Syntax:nginx 语法正则表达式 |
location [ location |
---|---|
Default:express 默认bash |
— |
Context:app 使用场景/语境memcached |
server , location |
Sets configuration depending on a request URI. 基于请求uri的配置规则this
The matching is performed against a normalized URI, after decoding the text encoded in the “%XX
” form, resolving references to relative path components “.
” and “..
”, and possible compression of two or more adjacent slashes into a single slash. 匹配针对从"%xx"格式的文本解码以后的正常的uri生效,解析相对路径引用 "." 和 "..",以及将两个或更多的相邻的斜杠压缩成单斜杠。spa
A location can either be defined by a prefix string, or by a regular expression. Regular expressions are specified with the preceding “~*
” modifier (for case-insensitive matching), or the “~
” modifier (for case-sensitive matching). To find location matching a given request, nginx first checks locations defined using the prefix strings (prefix locations). Among them, the location with the longest matching prefix is selected and remembered. Then regular expressions are checked, in the order of their appearance in the configuration file. The search of regular expressions terminates on the first match, and the corresponding configuration is used. If no match with a regular expression is found then the configuration of the prefix location remembered earlier is used.操作系统
Location 能够用前缀字符串定义,或者正则表达式。正则表达式前面带有 ~* 修饰 (大小写不敏感匹配) ,或者 ~ 修饰 (大小写敏感匹配). 为了找到和一个给定的请求相匹配的location,nginx 首先检查 带了前缀字符串的location(也叫前缀location). 在它们当中,拥有最长的匹配前缀的location将被选中并被记录下来。而后按照在配置文件中的前后顺序,依次检查正则表达式。正则表达式的搜索会在第一个匹配的时候终止,而后相应的配置将被使用。若是没有命中正则表达式,则会使用以前被记录下来的前缀location。
location
blocks can be nested, with some exceptions mentioned below.
location 模块能够被嵌套,如下是一些例外状况:
For case-insensitive operating systems such as macOS and Cygwin, matching with prefix strings ignores a case (0.7.7). However, comparison is limited to one-byte locales. 对于大小写不敏感的操做系统,例如macOS和Cygwin,匹配前缀字符串会忽略一个大写(0.7.7版本). 然而,比较被限制在单字节的地方。
Regular expressions can contain captures (0.7.40) that can later be used in other directives. 正则表达式能够包含匹配,这些匹配能够在后续其余指令中被用到的。(0.7.40版本)
If the longest matching prefix location has the “^~
” modifier then regular expressions are not checked. 若是最长的匹配到的前缀location带有 ^~ 修饰符,那么正则表达式将不会被检查。
Also, using the “=
” modifier it is possible to define an exact match of URI and location. If an exact match is found, the search terminates. For example, if a “/
” request happens frequently, defining “location = /
” will speed up the processing of these requests, as search terminates right after the first comparison. Such a location cannot obviously contain nested locations.
同时,使用 '=' 修饰符可能定义一个精准匹配的uri和location. 若是找到了一个精准匹配,那么查询就会终止。例如,若是一个 '/' 请求常常出现,那么定义 'location = /' 将加快处理这些请求的速度,由于搜索会在第一次比较以后就结束。这种location很显然不能包含嵌套的location.
In versions from 0.7.1 to 0.8.41, if a request matched the prefix location without the “=
” and “^~
” modifiers, the search also terminated and regular expressions were not checked.
在 0.7.1 到 0.8.41 的版本中,若是一个请求命中了 不含有 '=' 或 '^~' 修饰符的前缀location,搜索也会终止,且正则表达式不会被检查到。
Let’s illustrate the above by an example: 让咱们用一个例子来展现以上的内容:
location = / { [ configuration A ] } location / { [ configuration B ] } location /documents/ { [ configuration C ] } location ^~ /images/ { [ configuration D ] } location ~* \.(gif|jpg|jpeg)$ { [ configuration E ] }
The “/
” request will match configuration A, the “/index.html
” request will match configuration B, the “/documents/document.html
” request will match configuration C, the “/images/1.gif
” request will match configuration D, and the “/documents/1.jpg
” request will match configuration E.
'/' 请求将会匹配到 配置A (精准匹配)
'/index.html' 请求将匹配到 配置B (没有命中精准匹配,没有命中前缀匹配,也没有命中正则匹配,最后命中默认匹配)
'/documents/document.html' 请求将命中 配置C (没有命中精准匹配,命中了前缀匹配 /documents/,继续查找正则匹配,没有命中,使用前缀匹配)
'/images/1.gif' 请求将命中 配置D (没有命中精准匹配,命中了前缀匹配 ^~ /images/,这个匹配带了 ^~修饰符,不查找正则匹配,直接使用该前缀匹配)
'/documents/1.jpg' 请求将命中 配置E (没有命中精准匹配,同时命中了 /documents 和 ~* \.(gif|jpg|jpeg)$,后面这个最长,被记录下来,继续查找正则匹配,没有命中,使用以前记录下的最长的前缀匹配,配置E。
The “@
” prefix defines a named location. Such a location is not used for a regular request processing, but instead used for request redirection. They cannot be nested, and cannot contain nested locations.
'@' 前缀至关于给一个location命了名. 这种location不会用来处理常规的请求,可是会用来请求重定向。它们不能够被嵌套,也不能够包含嵌套location.
If a location is defined by a prefix string that ends with the slash character, and requests are processed by one of proxy_pass, fastcgi_pass, uwsgi_pass, scgi_pass, memcached_pass, or grpc_pass, then the special processing is performed. In response to a request with URI equal to this string, but without the trailing slash, a permanent redirect with the code 301 will be returned to the requested URI with the slash appended. If this is not desired, an exact match of the URI and location could be defined like this:
若是一个location用一个前缀字符串,并以一个斜杠\结束,且这些请求被 proxy_pass, fastcgi_pass, uwsgi_pass, scgi_pass, memcached_pass 或者 grpc_pass中的一个处理,那么特殊的处理将被执行。在响应 带有和这个字符串相等,但没有最后的斜杠\ 的uri的请求时,会返回一个带有301状态码的永久重定向 给请求的uri,并带上最后的斜杠\。若是不但愿这样,能够对uri的精准匹配以及location定义以下: (这样就不会跳转301了)
location /user/ { proxy_pass http://user.example.com; } location = /user { proxy_pass http://login.example.com; }
修饰符(modifier)
location [ = | ~ | ~* | ^~ ] uri { ... }
根据不一样的修饰符能够分为两大类
2.1 前缀location (prefix location)
2.1.1 无修饰符的普通location,例如 location /abc, location /abc/
2.1.2 带=的精准匹配location,例如 location =/abc
2.1.3 带^~表示以某个常规字符串开头的,非正则表达式location,例如 location ^~ /abc
2.2 正则表达式location (regular expressions location)
2.2.1 ~ 区分大小写的正则location
2.2.2 ~* 不区分大小写的正则location
3.1 nginx会首先检查 前缀location
3.1.1 若是命中,拥有最长的匹配字符串的location将被选中并被记录下来。
3.1.1.1 若是最长前缀匹配location的修饰符是^~时,就不会检查正则location了,直接选择该location为最终location。若是不是,则进入下一步正则匹配。
3.1.2 若是没有命中,则进入下一步正则匹配。
3.2 若是存在正则location时,按照配置的前后顺序(重要!)依次匹配URI。
3.2.1 若是找到匹配的正则location就再也不继续往下,并选择该location做为最终的结果。
3.2.2 若是没有找到匹配的正则location,则会使用以前被记录下来的前缀location (若是有的话)。
3.3 若是存在精准匹配location,且请求的uri跟其彻底匹配,选择该精准匹配location做为最终的location。
精准匹配 > ^~修饰符最长前缀匹配 > 正则匹配 > 无修饰符普通最长前缀匹配 > 通用匹配 /
注意,在同一个Server中,不能同时存在带有相同字符串的 ^~ 修饰符前缀location 和 无修饰符普通前缀location,以下
server { listen 80; server_name www.test1.com; root /opt/wwwroot/test; location /fullpath { echo 'prefix fullpath with no modifier'; } location ^~ /fullpath { echo 'prefix fullpath with ^~ modifier'; } }
若是这两个同时打开,在 nginx -t 命令检查nginx 配置时,会报 emerg 级别错误
2019/11/05 14:01:52 [emerg] 22355#22355: duplicate location "/fullpath" in /etc/nginx/sites-enabled/default:165
可是,将第二个location 改成 ^~ /fullpath/ 就OK了。