164 lines
4.2 KiB
YAML
164 lines
4.2 KiB
YAML
version: "3.9"
|
|
|
|
services:
|
|
s1ne:
|
|
build:
|
|
context: .
|
|
dockerfile: Dockerfile
|
|
container_name: s1ne-s-1
|
|
restart: unless-stopped
|
|
|
|
env_file:
|
|
- .env
|
|
|
|
environment:
|
|
PYTHONUNBUFFERED: "1"
|
|
PYTHONDONTWRITEBYTECODE: "1"
|
|
APP_ENV: ${APP_ENV:-production}
|
|
LOG_LEVEL: ${LOG_LEVEL:-INFO}
|
|
SQLITE_CACHE_PATH: ${SQLITE_CACHE_PATH:-/app/data/cache.sqlite3}
|
|
AUDIO_CACHE_TTL: ${AUDIO_CACHE_TTL:-600}
|
|
SEARCH_CACHE_TTL: ${SEARCH_CACHE_TTL:-600}
|
|
SOURCE_METADATA_CACHE_TTL: ${SOURCE_METADATA_CACHE_TTL:-1800}
|
|
RECOMMENDATION_CACHE_TTL: ${RECOMMENDATION_CACHE_TTL:-900}
|
|
NEGATIVE_CACHE_TTL: ${NEGATIVE_CACHE_TTL:-90}
|
|
AUDIO_NEGATIVE_CACHE_TTL: ${AUDIO_NEGATIVE_CACHE_TTL:-90}
|
|
CACHE_CLEANUP_INTERVAL_SECONDS: ${CACHE_CLEANUP_INTERVAL_SECONDS:-300}
|
|
CACHE_CLEANUP_BATCH_SIZE: ${CACHE_CLEANUP_BATCH_SIZE:-1000}
|
|
YTDLP_CONCURRENCY: ${YTDLP_CONCURRENCY:-5}
|
|
SEARCH_YTDLP_CONCURRENCY: ${SEARCH_YTDLP_CONCURRENCY:-3}
|
|
AUDIO_YTDLP_CONCURRENCY: ${AUDIO_YTDLP_CONCURRENCY:-2}
|
|
RECOMMENDATION_YTDLP_CONCURRENCY: ${RECOMMENDATION_YTDLP_CONCURRENCY:-3}
|
|
YTDLP_PLAYER_CLIENTS: ${YTDLP_PLAYER_CLIENTS:-web,android,mweb,ios}
|
|
TRUSTED_PROXY_CIDRS: ${TRUSTED_PROXY_CIDRS}
|
|
PROXY_FILE: ${PROXY_FILE:-/app/proxies.txt}
|
|
PROXY_USER: ${PROXY_USER:-}
|
|
PROXY_PASS: ${PROXY_PASS:-}
|
|
PROXY_RETRY_ATTEMPTS: ${PROXY_RETRY_ATTEMPTS:-3}
|
|
MEDIA_TOKEN_SECRET: ${MEDIA_TOKEN_SECRET}
|
|
MEDIA_TOKEN_BIND_ANONYMOUS_ID: ${MEDIA_TOKEN_BIND_ANONYMOUS_ID:-true}
|
|
|
|
volumes:
|
|
- yt_music_data:/app/data
|
|
- ${PROXY_FILE_HOST:-./proxies.txt}:/app/proxies.txt:ro
|
|
|
|
expose:
|
|
- "8003"
|
|
|
|
command:
|
|
[
|
|
"uvicorn",
|
|
"app:app",
|
|
"--host", "0.0.0.0",
|
|
"--port", "8003",
|
|
"--workers", "1",
|
|
"--loop", "uvloop",
|
|
"--http", "httptools",
|
|
"--proxy-headers",
|
|
"--forwarded-allow-ips", "${TRUSTED_PROXY_CIDRS}",
|
|
"--timeout-keep-alive", "30",
|
|
"--timeout-graceful-shutdown", "30",
|
|
"--limit-concurrency", "256",
|
|
"--backlog", "2048"
|
|
]
|
|
networks:
|
|
- yt_music_proxy
|
|
|
|
tmpfs:
|
|
- /tmp:size=256m,mode=1777
|
|
|
|
security_opt:
|
|
- no-new-privileges:true
|
|
|
|
cap_drop:
|
|
- ALL
|
|
|
|
pids_limit: 256
|
|
|
|
healthcheck:
|
|
test:
|
|
[
|
|
"CMD",
|
|
"curl",
|
|
"--fail",
|
|
"--silent",
|
|
"--show-error",
|
|
"http://127.0.0.1:8003/healthz"
|
|
]
|
|
interval: 30s
|
|
timeout: 5s
|
|
start_period: 20s
|
|
retries: 3
|
|
|
|
logging:
|
|
driver: json-file
|
|
options:
|
|
max-size: "10m"
|
|
max-file: "5"
|
|
|
|
# No Caddy labels here.
|
|
# s1ne is now internal-only; Nginx is its only HTTP caller.
|
|
|
|
nginx:
|
|
image: nginx:alpine
|
|
container_name: s1ne-nginx
|
|
restart: unless-stopped
|
|
|
|
depends_on:
|
|
s1ne:
|
|
condition: service_healthy
|
|
|
|
networks:
|
|
- yt_music_proxy
|
|
|
|
volumes:
|
|
# Full main config, not /etc/nginx/conf.d/default.conf.
|
|
- ./nginx.conf:/etc/nginx/nginx.conf:ro
|
|
- ./static:/usr/share/nginx/html:ro
|
|
tmpfs:
|
|
- /var/cache/nginx:size=64m
|
|
- /var/run:size=8m
|
|
|
|
security_opt:
|
|
- no-new-privileges:true
|
|
|
|
pids_limit: 128
|
|
|
|
healthcheck:
|
|
test:
|
|
[
|
|
"CMD-SHELL",
|
|
"wget -q -O /dev/null http://127.0.0.1/healthz || exit 1"
|
|
]
|
|
interval: 30s
|
|
timeout: 5s
|
|
start_period: 10s
|
|
retries: 3
|
|
|
|
logging:
|
|
driver: json-file
|
|
options:
|
|
max-size: "10m"
|
|
max-file: "5"
|
|
|
|
labels:
|
|
# Caddy routes the public domain to Nginx port 80.
|
|
caddy: ${APP_DOMAIN}
|
|
caddy_ingress_network: yt_music_proxy
|
|
caddy.encode: zstd gzip
|
|
caddy.request_body.max_size: 256KB
|
|
caddy.header.-Server: ""
|
|
caddy.header.X-Content-Type-Options: "nosniff"
|
|
caddy.header.X-Frame-Options: "DENY"
|
|
caddy.header.Referrer-Policy: "strict-origin-when-cross-origin"
|
|
caddy.header.Permissions-Policy: "camera=(), microphone=(), geolocation=()"
|
|
caddy.header.Strict-Transport-Security: "max-age=31536000"
|
|
caddy.reverse_proxy: "{{upstreams 80}}"
|
|
|
|
volumes:
|
|
yt_music_data:
|
|
|
|
networks:
|
|
yt_music_proxy:
|
|
external: true
|