Search code examples
dockernginxdebian

disable access via http to my docker containers


I am trying to set a debian server where I have multiple apps running in docker containers each on has it's own port.

Lets suppose that it's IP is (160.160.160.160) linked to a domain example160.com and two apps (two docker containers) running on 5500 and 6600

I have also set some reverse proxy configs so I can acces to the apps via subdomains like app5500.example160.com and app6600.example160.com.
Here's an example of one of the configs

server {
    listen 443 ssl; # managed by Certbot
    server_name app5500.example160.com;

    location / {
        proxy_pass https://127.0.0.1:80/;
        proxy_set_header Host $host;
        proxy_set_header Upgrade $http_upgrade;
        proxy_set_header Connection upgrade;
        proxy_set_header Accept-Encoding gzip;
    }

    ssl_certificate /etc/letsencrypt/live/example160.com/fullchain.pem; # managed by Certbot
    ssl_certificate_key /etc/letsencrypt/live/example160.com/privkey.pem; # managed by Certbot
    include /etc/letsencrypt/options-ssl-nginx.conf; # managed by Certbot
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem; # managed by Certbot
}

server {
    listen 80;
    server_name app5500.example160.com;
    
    if ($host = app5500.example160.com) {
        return 301 https://$host$request_uri;
    } # managed by Certbot

    return 404; # managed by Certbot
}

as you can see I did a redirection from http to https and that's working only if I try to access to http://app5500.example160.com but the issue is that I am still able to access to container via urls such as http://www.example160.com:5500 and http://160.160.160.160:5500 and I dont know how to block it in order to access to the container only via https://app5500.example160.com

I tried this solution but adding this other nginx config to redirect other subdomain but it's not working

server {
    listen 443 ssl;
    server_name *.example160.com;

    if ($host !~ ^example160\.com$) {
        return 301 https://example160.com$request_uri;
    }

    ssl_certificate /etc/letsencrypt/live/example160.com-0001/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/example160.com-0001/privkey.pem;
    include /etc/letsencrypt/options-ssl-nginx.conf;
    ssl_dhparam /etc/letsencrypt/ssl-dhparams.pem;

    return 404;
}

server {
    listen 80 default_server;
    server_name *.example160.com;

    return 301 https://example160.com$request_uri;
}

I tried even to set up a firewall with iptables and nftables but I ended up with no firewall installed because they didnt help.


Solution

  • Rather than publishing your container ports on all interfaces, bind them to localhost instead:

    docker run -p 127.0.0.1:5500:5500 ...
    

    This way they will only be accessible to your nginx proxy; there will be no way to connect to the port directly from a remote location.


    Or, run your proxy in a container (if you're not doing that already), and then there's no need to publish the container ports at all. The proxy would be able to connect to the containers directly because they would be running on the same internal network.

    You would only need to publish the proxy port(s).