0

This is the URL I need to match.

https://example.com/wp-login.php https://example.com/wp-login.php?action=lostpassword https://example.com/?s= https://example.com/?s=xxxxxxx 

This is the location matching rule I am using, it does not work, what is wrong please?

location ~* ^/(?:wp-login\.php|\?s\=) { deny all; } 

2 Answers 2

1

This is the common nginx novices error. Neither location nor rewrite directives works with the whole request URI. Both of them works with the normalized request URI which does not include the query string part at all (description of what URI normalization is can be found in the location directive documentation). That means you can't check the query string using location directive at all.

Usually what you are asking for can be achieved checking the $arg_<name> nginx variable value, something like

if ($arg_s) { return 403; } 

Unfortunately there is no way to distinct an empty query argument value from the absence of such an argument (well, at least without using third party modules like lua-nginx-module, where that difference can be actually checked against an empty string or a nil value). Fortunately an original request URI is available to you via the $request_uri internal variable, so you can do something like

if ($request_uri ~ \?(.*&)?s=) { return 403; } location = /wp-login.php { deny all; } 

or even use a single $request_uri variable matching against a regex pattern like:

if ($request_uri ~ /wp-login\.php|\?(.*&)?s=) { return 403; } 

(this should be placed at the server configuration level)

Sign up to request clarification or add additional context in comments.

1 Comment

Would be really strange if it won't ;) If you'd ever need to adopt this to emulate a series of allow/deny statements, check this answer.
0

With your shown samples and attempts please try following regex.

(?:wp-login\.php(?:\?action=\S+)?$|\?s=(?:\S+)?)$ 

Here is the Online demo for regex.

Explanation: Adding detailed explanation for above.

(?: ##Starting 1st non-capturing group from here. wp-login\.php ##matching wp-login.php here. (?:\?action=\S+)?$ ##In a non-capturing group matching ?action= followed by non-spaces and keeping this as an optional match. | ##Putting OR condition either any of above OR following should match. \?s= ##Matching literal ? followed by s= (?:\S+)? ##In a non-capturing group matching 1 or more non-spaces and keeping this match as an optional one. )$ ##closing very first non-capturing group here. 

3 Comments

It seems that it does not work in nginx location. Test match failed.
@Lorraine1996, I have seen link you have given, I am really not sure how mu h reliable these online sites are for nginx(telling you from my htaccess experience where most of the sites fail for regex and rules but I am no expert in nging). If you see regex link provided in answer regex is matching your shown samples perfectly there. Kindly do let me know in case of any queries here.
I did the same test on the web server, running nginx -t did not prompt a syntax error, but the ?s=xxxxxxx match failed and wp-login.php matched successfully.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.