Restrict access to nginx server location to a specific Docker container with "allow" directive Restrict access to nginx server location to a specific Docker container with "allow" directive docker docker

Restrict access to nginx server location to a specific Docker container with "allow" directive


Think differently :)

Do bind a nginx-server (vhost) on port 10080 in addition - that server does offer the status location and what you need.

Server on 80/443 is also there and ONLY that one is bound/exposed to host ( exposed to the outer world ).

Since datadog is part of your docker-network / service network, it can still access 10080 in the internal network, but nobody else from the outer network.

Bulletproof, easy - no strings attached.


Since we are running the service through docker-compose and our issue being we don't know the IP of the agent. So the simple solution is to know the IP before starting. And that means assigning our agent a specific IP

Here is a update docker-compose to do that

version: '2'services:  flask:    restart: always    image: me/flask-app    command: /home/app/flask/start_app.sh    expose:      - "8080"  nginx:    restart: always    build: ./nginx    command: /runtime/start_nginx.sh    ports:      - "80:80"      - "443:443"    expose:      - "81"    volumes:      - app-static:/app-static:ro    links:      - flask:flask    networks:      agent:        ipv4_address: 172.25.0.101      default:  datadog-agent:    image: me/datadog-agent    env_file: ./datadog-agent/dev.env    links:        - flask        - nginx    volumes:      - /var/run/docker.sock:/var/run/docker.sock      - /proc/mounts:/host/proc/mounts:ro      - /sys/fs/cgroup:/host/sys/fs/cgroup:ro    networks:      agent:        ipv4_address: 172.25.0.100networks:  agent:    driver: bridge    ipam:      config:      - subnet: 172.25.0.0/24

Now you can do two possible things

server {  listen 172.25.0.101:81;  location /nginx_status {    stub_status on;    access_log off;    allow 127.0.0.1;    allow 172.25.0.100;    deny all;  }}

You can listen only on 172.25.0.101 which is accessible only container running on agent network. Also you can add allow 172.25.0.100 to only allow the agent container to be able to access this.


There are two (easier) ways to go about it.

First one is docker-compose but since I already have a setup running since 2 years which doesn't use docker-compose, I went for the 2nd way.

Second way is Allow Directive with a range of IPs.

Eg:

    location /stub_status {        stub_status;        allow 172.18.0.0/16;   # This is my local docker IP range        allow 192.168.0.0/16;  $ This is my production server IP range        deny all;              # deny all other hosts    }

I am not security expert, but mostly 192.168.* IP range is for local networks, not sure about 172.18.* range though.

To get more idea about this IP range thing and CIDR stuff, refer below linkshttp://nginx.org/en/docs/http/ngx_http_access_module.html

https://www.ripe.net/about-us/press-centre/understanding-ip-addressing