Nginx之location 匹配规则详解Word文档格式.docx
- 文档编号:22091525
- 上传时间:2023-02-02
- 格式:DOCX
- 页数:19
- 大小:26.87KB
Nginx之location 匹配规则详解Word文档格式.docx
《Nginx之location 匹配规则详解Word文档格式.docx》由会员分享,可在线阅读,更多相关《Nginx之location 匹配规则详解Word文档格式.docx(19页珍藏版)》请在冰豆网上搜索。
“正则location匹配让步普通location的严格精确匹配结果;
但覆盖普通location的最大前缀匹配结果”
官方文档解释
REFER:
http:
//wiki.nginx.org/NginxHttpCoreModule#location
location
syntax:
location[=|~|~*|^~|@]/uri/{…}
default:
no
context:
server
ThisdirectiveallowsdifferentconfigurationsdependingontheURI.
(译者注:
1、differentconfigurationsdependingontheURI说的就是语法格式:
location[=|~|~*|^~|@]/uri/{…},依据不同的前缀“=”,“^~”,“~”,“~*”和不带任何前缀的(因为[A]表示可选,可以不要的),表达不同的含义,简单的说尽管location的/uri/配置一样,但前缀不一样,表达的是不同的指令含义。
2、查询字符串不在URI范围内。
例如:
/films.htm?
fid=123的URI是/films.htm。
)
Itcanbeconfiguredusingbothliteralstringsandregularexpressions.Touseregularexpressions,youmustuseaprefix:
1.“~”forcasesensitivematching
2.“~*”forcaseinsensitivematching
译文:
上文讲到location/uri/可通过使用不同的前缀,表达不同的含义。
对这些不同前缀,分下类,就2大类:
正则location,英文说法是locationusingregularexpressions和普通location,英文说法是locationusingliteralstrings。
那么其中“~”和“~*”前缀表示正则location,“~”区分大小写,“~*”不区分大小写;
其他前缀(包括:
“=”,“^~”和“@”)和无任何前缀的都属于普通location。
Todeterminewhichlocationdirectivematchesaparticularquery,theliteralstringsarecheckedfirst.
对于一个特定的HTTP请求(aparticularquery),nginx应该匹配哪个location块的指令呢(注意:
我们在nginx.conf配置文件里面一般会定义多个location的)?
匹配规则是:
先匹配普通location(再匹配正则表达式)。
注意:
官方文档这句话就明确说了,先普通location,而不是有些同学的误区“先匹配正则location”。
Literalstringsmatchthebeginningportionofthequery–themostspecificmatchwillbeused.
前面说了“普通location”与“正则location”之间的匹配规则是:
先匹配普通location,再匹配正则location。
那么,“普通location”内部(普通location与普通location)是如何匹配的呢?
简单的说:
最大前缀匹配。
原文:
1、matchthebeginningportionofthequery(说的是匹配URI的前缀部分beginningportion);
2、themostspecificmatchwillbeused(因为location不是“严格匹配”,而是“前缀匹配”,就会产生一个HTTP请求,可以“前缀匹配”到多个普通location,例如:
location/prefix/mid/{}和location/prefix/{},对于HTTP请求/prefix/mid/t.html,前缀匹配的话两个location都满足,选哪个?
原则是:
themostspecificmatch,于是选的是location/prefix/mid/{})。
Afterwards,regularexpressionsarecheckedintheorderdefinedintheconfigurationfile.Thefirstregularexpressiontomatchthequerywillstopthesearch.
这段话说了两层意思,第一层是:
“Afterwards,regularexpressionsarechecked”,意思是普通location先匹配,而且选择了最大前缀匹配后,不能就停止后面的匹配,最大前缀匹配只是一个临时的结果,nginx还需要继续检查正则location(但至于最终才能普通location的最大前缀匹配,还是正则location的匹配,截止当前的内容还没讲,但后面会讲)。
第二层是“regularexpressionsarecheckedintheorderdefinedintheconfigurationfile.Thefirstregularexpressiontomatchthequerywillstopthesearch.”,意思是说“正则location”与“正则location”内部的匹配规则是:
按照正则location在配置文件中的物理顺序(编辑顺序)匹配的(这句话就说明location并不是一定跟顺序无关,只是普通location与顺序无关,正则location还是与顺序有关的),并且只要匹配到一条正则location,就不再考虑后面的(这与“普通location”与“正则location”之间的规则不一样,“普通location”与“正则location”之间的规则是:
选择出“普通location”的最大前缀匹配结果后,还需要继续搜索正则location)。
Ifnoregularexpressionmatchesarefound,theresultfromtheliteralstringsearchisused.
这句话回答了“普通location”的最大前缀匹配结果与继续搜索的“正则location”匹配结果的决策关系。
如果继续搜索的“正则location”也有匹配上的,那么“正则location”覆盖“普通location”的最大前缀匹配(因为有这个覆盖关系,所以造成有些同学以为正则location先于普通location执行的错误理解);
但是如果“正则location”没有能匹配上,那么就用“普通location”的最大前缀匹配结果。
Forcaseinsensitiveoperatingsystems,likeMacOSXorWindowswithCygwin,literalstringmatchingisdoneinacaseinsensitiveway(0.7.7).However,comparisonislimitedtosingle-bytelocale’sonly.
Regularexpressionmaycontaincaptures(0.7.40),whichcanthenbeusedinotherdirectives.
Itispossibletodisableregularexpressionchecksafterliteralstringmatchingbyusing“^~”prefix.Ifthemostspecificmatchliterallocationhasthisprefix:
regularexpressionsaren’tchecked.
通常的规则是,匹配完了“普通location”指令,还需要继续匹配“正则location”,但是你也可以告诉Nginx:
匹配到了“普通location”后,不再需要继续匹配“正则location”了,要做到这一点只要在“普通location”前面加上“^~”符号(^表示“非”,~表示“正则”,字符意思是:
不要继续匹配正则)。
Byusingthe“=”prefixwedefinetheexactmatchbetweenrequestURIandlocation.Whenmatchedsearchstopsimmediately.E.g.,iftherequest“/”occursfrequently,using“location=/”willspeedupprocessingofthisrequestabitassearchwillstopafterfirstcomparison.
除了上文的“^~”可以阻止继续搜索正则location外,你还可以加“=”。
那么如果“^~”和“=”都能阻止继续搜索正则location的话,那它们之间有什么区别呢?
区别很简单,共同点是它们都能阻止继续搜索正则location,不同点是“^~”依然遵守“最大前缀”匹配规则,然而“=”不是“最大前缀”,而是必须是严格匹配(exactmatch)。
这里顺便讲下“location/{}”和“location=/{}”的区别,“location/{}”遵守普通location的最大前缀匹配,由于任何URI都必然以“/”根开头,所以对于一个URI,如果有更specific的匹配,那自然是选这个更specific的,如果没有,“/”一定能为这个URI垫背(至少能匹配到“/”),也就是说“location/{}”有点默认配置的味道,其他更specific的配置能覆盖overwrite这个默认配置(这也是为什么我们总能看到location/{}这个配置的一个很重要的原因)。
而“location=/{}”遵守的是“严格精确匹配exactmatch”,也就是只能匹配http:
//host:
port/请求,同时会禁止继续搜索正则location。
因此如果我们只想对“GET/”请求配置作用指令,那么我们可以选“location=/{}”这样能减少正则location的搜索,因此效率比“location/{}”高(注:
前提是我们的目的仅仅只想对“GET/”起作用)。
Onexactmatchwithliterallocationwithout“=”or“^~”prefixessearchisalsoimmediatelyterminated.
前面我们说了,普通location匹配完后,还会继续匹配正则location;
但是nginx允许你阻止这种行为,方法很简单,只需要在普通location前加“^~”或“=”。
但其实还有一种“隐含”的方式来阻止正则location的搜索,这种隐含的方式就是:
当“最大前缀”匹配恰好就是一个“严格精确(exactmatch)”匹配,照样会停止后面的搜索。
原文字面意思是:
只要遇到“精确匹配exactmatch”,即使普通location没有带“=”或“^~”前缀,也一样会终止后面的匹配。
先举例解释下,后面例题会用实践告诉大家。
假设当前配置是:
location/exact/match/test.html{配置指令块1},location/prefix/{配置指令块2}和location~\.html${配置指令块3},如果我们请求GET/prefix/index.html,则会被匹配到指令块3,因为普通location/prefix/依据最大匹配原则能匹配当前请求,但是会被后面的正则location覆盖;
当请求GET/exact/match/test.html,会匹配到指令块1,因为这个是普通location的exactmatch,会禁止继续搜索正则location。
Tosummarize,theorderinwhichdirectivesarecheckedisasfollows:
1.Directiveswiththe“=”prefixthatmatchthequeryexactly.Iffound,searchingstops.
2.Allremainingdirectiveswithconventionalstrings.Ifthismatchusedthe“^~”prefix,searchingstops.
3.Regularexpressions,intheordertheyaredefinedintheconfigurationfile.
4.If#3yieldedamatch,thatresultisused.Otherwise,thematchfrom#2isused.
这个顺序没必要再过多解释了。
但我想用自己的话概括下上面的意思“正则location匹配让步普通location的严格精确匹配结果;
但覆盖普通location的最大前缀匹配结果”。
ItisimportanttoknowthatnginxdoesthecomparisonagainstdecodedURIs.Forexample,ifyouwishtomatch“/images//test”,thenyoumustuse“/images//test”todeterminethelocation.
在浏览器上显示的URL一般都会进行URLEncode,例如“空格”会被编码为,但是Nginx的URL的匹配都是针对URLDecode之后的。
也就是说,如果你要匹配“/images//test”,你写location的时候匹配目标应该是:
“/images//test”。
Example:
location=/{
#matchesthequery/only.
[configurationA]
}
location/{
#matchesanyquery,sinceallqueriesbeginwith/,butregular
#expressionsandanylongerconventionalblockswillbe
#matchedfirst.
[configurationB]
location^~/images/{
#matchesanyquerybeginningwith/images/andhaltssearching,
#soregularexpressionswillnotbechecked.
[configurationC]
location~*\.(gif|jpg|jpeg)${
#matchesanyrequestendingingif,jpg,orjpeg.However,all
#requeststothe/images/directorywillbehandledby
#ConfigurationC.
[configurationD]
上述这4个location的配置,没什么好解释的,唯一需要说明的是location/{[configurationB]},原文的注释严格来说是错误的,但我相信原文作者是了解规则的,只是文字描述上简化了下,但这个简化容易给读者造成“误解:
先检查正则location,再检查普通location”。
“matchesanyquery,sinceallqueriesbeginwith/,butregularexpressionsandanylongerconventionalblockswillbematchedfirst.”大意是说:
“location/{}能够匹配所有HTTP请求,因为任何HTTP请求都必然是以‘/’开始的(这半句没有错误)。
但是,正则location和其他任何比‘/’更长的普通location(location/{}是普通location里面最短的,因此其他任何普通location都会比它更长,当然location=/{}和location^~/{}是一样长的)会优先匹配(matchedfirst)。
”原文作者说“butregularexpressionswillbematchedfirst.”应该只是想说正则location会覆盖这里的location/{},但依然是普通location/{}先于正则location匹配,接着再正则location匹配;
但其他更长的普通location(anylongerconventionalblocks)的确会先于location/{}匹配。
Examplerequests:
∙/->
configurationA
∙/documents/document.html->
configurationB
∙/images/1.gif->
configurationC
∙/documents/1.jpg->
configurationD
Notethatyoucoulddefinethese4configurationsinanyorderandtheresultswouldremainthesame.
需要提醒下:
这里说“inanyorder”和“…remainthesame”是因为上面只有一个正则location。
文章前面已经说了正则location的匹配是跟编辑顺序有关系的。
Whilenestedlocationsareallowedbytheconfigurationfileparser,theiruseisdiscouragedandmayproduceunexpectedresults.
实际上nginx的配置文件解析程序是允许location嵌套定义的(location/{location/uri/{}})。
但是我们平时却很少看见这样的配置,那是因为nginx官方并不建议大家这么做,因为这样会导致很多意想不到的后果。
Theprefix“@”specifiesanamedlocation.Suchlocationsarenotusedduringnormalprocessingofrequests,theyareintendedonlytoprocessinternallyredirectedrequests(seeerror_page,try_files).
文章开始说了location的语法中,可以有“=”,“^~”,“~”和“~*”前缀,或者干脆没有任何前缀,还有“@”前缀,但是后面的分析我们始终没有谈到“@”前缀。
文章最后点内容,介绍了“@”的用途:
“@”是用来定义“NamedLocation”的(你可以理解为独立于“普通location(locationusingliteralstrings)”和“正则location(locationusingregularexpressions)”之外的第三种类型),这种“NamedLocation”不是用来处理普通的HTTP请求的,它是专门用来处理“内部重定向(internallyredirected)”请求的。
这里说的“内部重定向(internallyredirected)”或许说成“forward”会好点,以为内internallyredirected是不需要跟浏览器交互的,纯粹是服务端的一个转发行为。
安装Nginx
wgethttp:
//nginx.org/download/nginx-1.4.6.tar.gz
tarzxvfnginx-1.1.0.tar.gz
./configure
make
makeinstall
需要注意的是在configure这步遇到点小麻烦:
./configure:
error:
theHTTPrewritemodulerequiresthePCRElibrary.
安装nginx的时候,rewrite模块默认是需要被安装的。
但是rewrite模块所依赖的PCRE库需要额外安装。
Youcaneitherdisablethemodulebyusing–without-http_rewrite_module
option,orinstall
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
- Nginx之location 匹配规则详解 Nginx location 匹配 规则 详解