diff --git a/README.md b/README.md index 0c9a3a5..cceab08 100644 --- a/README.md +++ b/README.md @@ -72,6 +72,10 @@ docker compose ps By default, the API is available at `http://localhost:17777/api`. Swagger UI is available at `http://localhost:17777/api/doc`. The default bind address is suitable for a reverse proxy on the Docker host. +The backend resolves the Docker host gateway when it starts. Uvicorn trusts +forwarded headers only from this gateway and the loopback interface. This lets +audit and security records contain the client IP address. Keep `BACKEND_BIND` +on `127.0.0.1` and let the reverse proxy provide the public endpoint. ## Store persistent data diff --git a/compose.yaml b/compose.yaml index e8bbfb7..392cbfc 100644 --- a/compose.yaml +++ b/compose.yaml @@ -56,6 +56,10 @@ services: build: context: . restart: unless-stopped + environment: + TRUST_HOST_PROXY: "1" + extra_hosts: + - "host.docker.internal:host-gateway" command: ["drivershub", "--config", "/app/config/config.json", "--banner-service-url", "http://bannergen:8700/banner"] volumes: - ./config:/app/config diff --git a/docker/entrypoint.sh b/docker/entrypoint.sh index 3bba72b..0348e10 100755 --- a/docker/entrypoint.sh +++ b/docker/entrypoint.sh @@ -2,6 +2,15 @@ # Start a compiled program. set -eu +if [ "${TRUST_HOST_PROXY:-0}" = "1" ]; then + proxy_ip="$(getent ahostsv4 host.docker.internal | sed -n '1{s/[[:space:]].*//;p;}')" + if [ -z "$proxy_ip" ]; then + echo "Cannot resolve the trusted Docker host gateway." >&2 + exit 1 + fi + export FORWARDED_ALLOW_IPS="127.0.0.1,$proxy_ip" +fi + if [ "${1:-}" = "drivershub" ]; then shift exec /app/drivershub "$@"