enchance
enchance

Reputation: 30501

NGINX location block with limited number of path segments

I have a path which starts with ~* /api/v1/(?<endpoint>.*). But I realize this can be misused. Is there a way to limit the number of path segments after the /api/v1 to only 3 while still being able to retain any GET variables if any?

So these will pass:

these won't:

I'm only looking at a total of 3 path segments max after /api/v1. Anything more than that shouldn't match. Is this possible in a location block? I'm open to suggestions.

After this I use proxy_pass on the capture group to pass it on to my FastAPI backend along with any GET variables which might exist so /api/v1/foo/bar gets received as /foo/bar.

Update: Added GET variables I forgot earlier.

Upvotes: 2

Views: 182

Answers (1)

Richard Smith
Richard Smith

Reputation: 49792

Looking at the regular expression in your question, you will need to change the .* sequence (which matches anything), into a sequence that only matches one, two, or three path elements.

For example:

[^/]+(/[^/]+){0,2}

For completeness, you should use the ^ and $ anchors as you are matching to an entire string. Note that the query string is not part of the normalised URI tested by a location statement.

Finally, Nginx requires any expression containing braces to be protected by quotes.


So, you could use a regular expression location as follows to match only the permitted URLs:

location ~* "^/api/v1/(?<endpoint>[^/]+(/[^/]+){0,2})$" {
    ...
}

A URL with too many path elements will be processed by some other location block. Generally, if no regular expression location matches a URL, the prefix location with the longest matching prefix will be used.

So, the following prefix location will match any URL that begins with /api/v1/ but does not match the regular expression location above, including those URLs with too many path elements:

location /api/v1/ { 
    return 444; 
}

Upvotes: 0

Related Questions