fix: replace FORWARDED_ALLOW_IPS with nginx map, add .dockerignore

HTTPS proxy handling moved entirely to nginx (map $http_x_forwarded_proto).

- .dockerignore to exclude models/data/lora/output from build context
- nginx: manifest.json returns proper JSON for PWA, favicon returns 204
- docker-compose: drop version key, remove FORWARDED_ALLOW_IPS env var
- README: update HTTPS troubleshooting (nginx map handles it now)
This commit is contained in:
Daniel Cox
2026-08-12 10:05:53 +09:30
parent 74b98d2c1e
commit 4af38a9ddc
5 changed files with 49 additions and 12 deletions

24
.dockerignore Normal file
View File

@@ -0,0 +1,24 @@
# Model weights (mounted at runtime via volumes)
models/
data/
lora/
output/
# Git history
.git/
# Python cache
__pycache__/
*.pyc
*.pyo
*.egg-info/
.venv/
# Docker config (not needed inside image)
docker/docker-compose.yml
docker/nginx.conf
docker/README.md
# IDE / OS
.DS_Store
.vscode/

View File

@@ -121,7 +121,7 @@ docker run --gpus all -p 7860:7860 \
|----------|---------|-------------|
| `GRADIO_SERVER_PORT` | `7860` | Port for the WebUI server |
| `GRADIO_ROOT_PATH` | `""` | URL prefix when behind a reverse proxy (e.g., `/webui`) |
| `FORWARDED_ALLOW_IPS` | `*` | IPs allowed to set `X-Forwarded-Proto`. Set to `*` when behind a Docker reverse proxy so Gradio generates `https://` file URLs. |
| `VOXCPM_LANG` | `zh` | Default UI language (`zh` or `en`) |
## Reverse Proxy
@@ -154,4 +154,4 @@ docker compose -f docker/docker-compose.yml logs -f training-webui
- **WebUI not accessible**: Check that port 80 (nginx) or 7860 (direct) isn't blocked by a firewall.
- **WebSocket errors behind proxy**: Ensure your proxy forwards `Upgrade` and `Connection` headers (the included nginx.conf handles this).
- **Health check failing**: Ensure nginx is running — `curl http://localhost/` should return `OK`.
- **Mixed-content / audio not playing over HTTPS**: Gradio generates `http://` file URLs because uvicorn doesn't trust the `X-Forwarded-Proto` header from the Docker bridge network. The compose file sets `FORWARDED_ALLOW_IPS=*` to fix this. If you run without compose, pass `-e FORWARDED_ALLOW_IPS=*` to `docker run`.
- **Mixed-content / audio not playing over HTTPS**: The nginx config uses `map $http_x_forwarded_proto` to pass the correct protocol through to Gradio. This ensures `https://` file URLs are generated when accessed via HTTPS through a load balancer.

View File

@@ -1,5 +1,3 @@
version: "3.8"
services:
training-webui:
build:
@@ -32,11 +30,7 @@ services:
environment:
- GRADIO_SERVER_PORT=7860
- GRADIO_ROOT_PATH=/webui # Matches nginx location block
# Tell uvicorn to trust X-Forwarded-Proto from any IP (nginx in Docker
# connects from 172.x.x.x, not 127.0.0.1). Without this, Gradio
# generates http:// file URLs even when accessed over HTTPS, causing
# mixed-content errors that block audio playback in the browser.
- FORWARDED_ALLOW_IPS=*
# - VOXCPM_LANG=en # Uncomment for English UI (default: zh)
restart: unless-stopped
nginx:

View File

@@ -1,19 +1,40 @@
# Preserve X-Forwarded-Proto from upstream load balancer (e.g. AWS ALB).
# If ALB already set it to "https", pass that through instead of $scheme
# (which is "http" since ALB→nginx is unencrypted). Falls back to $scheme
# when accessed directly (no upstream proxy).
map $http_x_forwarded_proto $forwarded_proto {
default $http_x_forwarded_proto;
"" $scheme;
}
server {
listen 80;
server_name _;
absolute_redirect off;
# Health check for load balancers (AWS ALB, etc.)
location = / {
return 200 'OK\n';
add_header Content-Type text/plain;
}
location = /manifest.json {
return 200 '{"name":"VoxCPM Training","short_name":"VoxCPM","start_url":"/webui/"}';
default_type application/json;
}
location = /favicon.ico {
return 204;
access_log off;
}
location /webui/ {
proxy_pass http://training-webui:7860/;
proxy_set_header Host $host;
proxy_set_header X-Real-IP $remote_addr;
proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
proxy_set_header X-Forwarded-Proto $scheme;
proxy_set_header X-Forwarded-Proto $forwarded_proto;
# WebSocket support (required for Gradio)
proxy_http_version 1.1;

View File

@@ -1323,9 +1323,7 @@ with gr.Blocks(title="VoxCPM LoRA WebUI", theme=gr.themes.Soft(), css=custom_css
)
if __name__ == "__main__":
# Ensure lora directory exists
os.makedirs("lora", exist_ok=True)
port = int(os.environ.get("GRADIO_SERVER_PORT", "7860"))
root_path = os.environ.get("GRADIO_ROOT_PATH", "")