mastercontainer: block the docker network gateway on the login endpoints

The `/api/auth/login` and `/api/auth/getlogin` endpoints are already blocked
for the nextcloud container. However containers that reach the mastercontainer
via the host use the gateway ip of the `nextcloud-aio` network as source
address, so requests from them were not caught by the existing matcher.

The gateway ip is now read in start.sh and exported as DOCKER_NETWORK_GATEWAY
so that it can be used via `remote_ip` in both Caddyfiles.

Note that this needs a second matcher block instead of an additional line in
the existing one because matchers of different types inside one named matcher
are AND'ed together, which would never match. Also `remote_host` only resolves
host names, hence the built-in `remote_ip` matcher is used for the ip.

If the `nextcloud-aio` network does not exist yet - it only gets created by the
php code once the containers get started for the first time - the value falls
back to localhost, which is a no-op for the matcher, and the actual gateway ip
gets applied on the next restart of the mastercontainer.

Signed-off-by: Simon L. <szaimen@e.mail.de>
This commit is contained in:
Simon L.
2026-08-05 11:59:13 +02:00
parent 858c4df728
commit 4aea53cb2d
3 changed files with 38 additions and 4 deletions
+12 -2
View File
@@ -36,11 +36,21 @@ https://:8443 {
import headers.Caddyfile
header Strict-Transport-Security max-age=31536000;
@denied {
@denied-host {
path /api/auth/login /api/auth/getlogin
remote_host nextcloud-aio-nextcloud
}
abort @denied
abort @denied-host
# The gateway ip of the nextcloud-aio network is used as source address by containers
# that reach the mastercontainer via the host, so it needs to be blocked as well.
# The variable gets set in start.sh and falls back to localhost if the network
# does not exist yet. In that case it gets applied on the next container restart.
@denied-gateway {
path /api/auth/login /api/auth/getlogin
remote_ip {$DOCKER_NETWORK_GATEWAY}
}
abort @denied-gateway
root * /var/www/docker-aio/php/public
php_fastcgi unix//run/php.sock
+12 -2
View File
@@ -26,11 +26,21 @@
https://:8080 {
import headers.Caddyfile
@denied {
@denied-host {
path /api/auth/login /api/auth/getlogin
remote_host nextcloud-aio-nextcloud
}
abort @denied
abort @denied-host
# The gateway ip of the nextcloud-aio network is used as source address by containers
# that reach the mastercontainer via the host, so it needs to be blocked as well.
# The variable gets set in start.sh and falls back to localhost if the network
# does not exist yet. In that case it gets applied on the next container restart.
@denied-gateway {
path /api/auth/login /api/auth/getlogin
remote_ip {$DOCKER_NETWORK_GATEWAY}
}
abort @denied-gateway
root * /var/www/docker-aio/php/public
php_fastcgi unix//run/php.sock
+14
View File
@@ -436,6 +436,20 @@ if [ -d "/mnt/docker-aio-config/caddy/locks" ]; then
rm -rf /mnt/docker-aio-config/caddy/locks/*
fi
# Get the gateway ip of the nextcloud-aio network which is used by the Caddyfiles.
# Containers that reach the mastercontainer via the host use it as source address,
# so it needs to be blocked in addition to the nextcloud container itself.
# A network can have multiple gateways (e.g. one for IPv4 and one for IPv6), so get them all.
# remote_ip accepts multiple space separated values.
DOCKER_NETWORK_GATEWAY="$(su-exec www-data docker network inspect nextcloud-aio --format '{{range .IPAM.Config}}{{if .Gateway}}{{.Gateway}} {{end}}{{end}}' 2>/dev/null | sed 's| *$||')"
if [ -z "$DOCKER_NETWORK_GATEWAY" ]; then
# The network gets created by the php code when the containers get started for the first time,
# so it might not exist yet. Fall back to localhost which is a no-op for the matcher and
# apply the actual gateway ip on the next container restart.
DOCKER_NETWORK_GATEWAY="127.0.0.1"
fi
export DOCKER_NETWORK_GATEWAY
# Fix the Caddyfile format
caddy fmt --overwrite /acme.Caddyfile
caddy fmt --overwrite /internal.Caddyfile