nginx deny to allow a single IP

Juicy asked:

I’m trying to set up an nginx config that allows only one source IP to access /admin.

I tried the following nginx.conf:

user root;

events {

http {
  server {
    listen       5000;

    location /admin {
      deny all;
      return 200;

What I was expecting:

Only requests originating from would receive the 200 OK response. Other requests would receive a 403 Unauthorised.

What I’m seeing:

Regardless of the source IP, I’m getting a 200 OK response.

$ docker run -it -v /tmp/test/nginx.conf:/etc/nginx/nginx.conf -p nginx:alpine
$ curl localhost:5000/admin -v
*   Trying
* Connected to localhost ( port 5000 (#0)
> GET /admin HTTP/1.1
> Host: localhost:5000
> User-Agent: curl/7.58.0
> Accept: */*
< HTTP/1.1 200 OK
< Server: nginx/1.15.11
< Date: Sun, 14 Apr 2019 20:33:32 GMT
< Content-Type: text/plain
< Content-Length: 0
< Connection: keep-alive

How can I whitelist a certain IP address for a path in nginx?

My answer:

The return statement is processed in the nginx rewrite phase, which is before the access phase where access control is checked.

To solve the problem, put in a real configuration for your virtual server instead of a “test” configuration. For instance, set a document root and put an index.html file in it, or proxy_pass to a web application.

View the full question and any other answers on Server Fault.

Creative Commons License
This work is licensed under a Creative Commons Attribution-ShareAlike 3.0 Unported License.