Nginx Location是什么?
Nginx接受到的请求后,请求发送到什么地方是有Nginx locaiton来定义的。
Nginx Location 规则
语法如下:
location optional_modifier location_match { . . . }
类型 | 功能修饰符 | 示例 |
---|---|---|
前缀字符串 | None = ^~ |
location /prefix location = /exactmatch location ^~ /longestmatchnotcheckreg |
正则表达式 | ~ ~* |
location ~ /regularsensitive locaiton ~* /regularinsensitive |
Location匹配优先级(官方文档)
以下是nginx文档中location的匹配过程,英文加上翻译。
步骤 | English | 中文 |
---|---|---|
1 | Test the URI against all prefix strings. | 将 URI 与所有前缀字符串进行匹配。 |
2 | The = (equals sign) modifier defines an exact match of the URI and a prefix string. If the exact match is found, the search stops. | "=(等号) 修饰符用于精确匹配 URI 和前缀字符串。如果找到精确匹配,搜索停止。 |
3 | If the ^~ (caret-tilde) modifier prepends the longest matching prefix string, the regular expressions are not checked. | 如果 “^~(插入波浪号)” 修饰符前置于最长匹配的前缀字符串,将不会检查正则表达式。 |
4 | Store the longest matching prefix string. | 存储最长匹配的前缀字符串。 |
5 | Test the URI against regular expressions. | 将 URI 与正则表达式进行匹配。 |
6 | Stop processing when the first matching regular expression is found and use the corresponding location. | 当找到第一个匹配的正则表达式时停止处理,并使用相应的位置。 |
7 | If no regular expression matches, use the location corresponding to the stored prefix string. | 如果没有匹配的正则表达式,使用与存储的前缀字符串相对应的位置。 |
Location 匹配优先级(通俗讲解)
文档中写的比较简洁,理解起来可能有些问题。下面是我总结的比较通俗的讲解:
- 先匹配前缀表达式,后匹配正则表达式。
- 前缀表达式如果匹配到严格匹配
location = /exactmatch , 则直接结束; - 前缀表达式命中多条,则选择最长的, 如果最长的有正则中止修饰符
location ^~ /longestmatchnotcheckreg , 则结束; - 顺序匹配正则表达式,一但匹配,则结束;
- 上面的正则表达式没有匹配到,则使用前面第三步最长的那条前缀规则,并结束;
- 什么也没有,就只好使用默认的;
类型 | 功能修饰符 | 示例 | 匹配规则 |
---|---|---|---|
前缀字符串 | None = ^~ |
location /prefix location = /exactmatch location ^~ /longestmatchnotcheckreg |
匹配到则直接命中 匹配到且为最长前缀则命中 匹配到且最长,然后没有正则命中 ,该规则才命中 |
正则表达式 | ~ ~* |
location ~ /regularsensitive locaiton ~* /regularinsensitive |
匹配到的第一个 |
注意点
大小写敏感
如果需要让windows也区分大小写,可以将第一个的规则修改为
location ~ /abc{ return 200 /abc; } location ~* /Abc{ return 200 /Abc; }
示例
location /a{ return 200 prefix:a; } location = /abc { return 200 prefix:exact; } location ^~ /abcd { return 200 prefix:ab:withRegStop; } location /abcde{ return 200 prefix:abcde; } location ~ /ab { return 200 regular:ab; } location ~ /abcd { return 200 regular:abcd; }
curl 请求结果
# 匹配到前缀 /a, 仅匹配到一个,则为最终结果 $curl -sS pma.test/a prefix:a # 匹配到最长前缀 /a,不是完全匹配,也没有正则中止符,因此继续正则匹配,匹配到 ~ /ab $curl -sS pma.test/ab regular:ab # 匹配到前缀 /a, = /abc, 因为/abc完全匹配,因此最终为 = /abc $ curl -sS pma.test/abc prefix:exact # 匹配到前缀 /a, ^~ /abcd, 没有完全匹配,最长匹配为 /abcd, 同时又正则终止符,因此最终结果为 ^~ /abcd $ curl -sS pma.test/abcd prefix:ab:withRegStop # 匹配到前缀 /a, ^~ /agcd, /abcde, 没有完全匹配,因此最长前缀匹配是 /abcde, 但是没有正则终止符,则继续正则匹配,匹配到的第一个正则为 ~ /ab, 因此最终结果为 ~ /ab $ curl -sS pma.test/abcde regular:ab # 与上面一样 $ curl -sS pma.test/abcdef regular:ab
参考:
- nginx locaiton doc
- regex modifiers