I’m trying to optimize my ‘location’ directives and cannot find a good way of determining if a specific location match is even attempted. Using echo inside the location block doesn’t help here.
The NGINX ngx_http_core_module documentation is somewhat confusing.
To use regular expressions, you must use a prefix:
-
~For case sensitive matching -
~*For case insensitive matching
How the match is performed:
-
Directives with the
=prefix that match the query exactly. If found, searching stops. -
All remaining directives with conventional strings. If this match used the
^~prefix, searching stops. -
Regular expressions, in the order they are defined in the configuration file.
-
If #3 yielded a match, that result is used. Otherwise, the match from #2 is used.
Number 2 here says “conventional strings” but then says it can be used with the ^~ prefix. Doesn’t ~ imply a RegExp? If not, how does it determine what is an isn’t a RegExp?
Specifically, I want the following:
-
Serve anything out of literal
/assetsdirectly. STOP SEARCH. -
Serve anything matching RegExp
\.php$|/$via fast-CGI STOP SEARCH. -
Serve everything else directly via literal
/
This way, there is only a / match attempt for non-dynamic files served from outside of assets.
I have:
location ^~ /assets {} # search-terminating literal? or regex?
location ~ \.php$|/$ {}
location / {} # is this match always attempted?
From the document, it looks as though the actual order would be 1-3-2, always running the literal / match. Yes, this optimization won’t make any difference for real performance, but I just want to clear up some ambiguity.
From the wiki:
So, this will be matched first:
location ~ \.php$ {}Even though assets are served out of
location / {}Inside the php block you also want to secure against malicious uploads before passing to fastcgi:
As you can see nginx works a little bit differently than you might expect.