Files
alisten/compose.prod.yaml
T

125 lines
4.3 KiB
YAML

services:
traefik:
image: traefik:v3.7.16
restart: unless-stopped
command:
- --providers.docker=true
- --providers.docker.exposedbydefault=false
- --providers.docker.network=proxy
- --entrypoints.web.address=:80
- --entrypoints.web.http.redirections.entrypoint.to=websecure
- --entrypoints.web.http.redirections.entrypoint.scheme=https
- --entrypoints.web.http.redirections.entrypoint.permanent=true
- --entrypoints.websecure.address=:443
- --entrypoints.websecure.http.tls.certresolver=letsencrypt
- --certificatesresolvers.letsencrypt.acme.email=${ACME_EMAIL}
- --certificatesresolvers.letsencrypt.acme.storage=/letsencrypt/acme.json
- --certificatesresolvers.letsencrypt.acme.httpchallenge.entrypoint=web
- --ping=true
- --log.format=json
ports:
- "80:80"
- "443:443"
volumes:
- /var/run/docker.sock:/var/run/docker.sock:ro
- letsencrypt:/letsencrypt
networks: [proxy]
healthcheck:
test: ["CMD", "traefik", "healthcheck", "--ping"]
start_period: 30s
start_interval: 1s
interval: 10s
timeout: 3s
retries: 3
security_opt:
- no-new-privileges:true
labels:
- traefik.enable=true
- traefik.http.middlewares.hsts.headers.stsSeconds=31536000
- traefik.http.middlewares.security-headers.headers.frameDeny=true
- traefik.http.middlewares.security-headers.headers.contentTypeNosniff=true
- traefik.http.middlewares.security-headers.headers.referrerPolicy=strict-origin-when-cross-origin
- traefik.http.middlewares.admin-ratelimit.ratelimit.average=2
- traefik.http.middlewares.admin-ratelimit.ratelimit.burst=10
- traefik.http.middlewares.admin-ratelimit.ratelimit.period=1s
- traefik.http.middlewares.admin-ratelimit.ratelimit.sourcecriterion.ipstrategy.depth=1
migrate:
networks:
- db
- backend
serve:
environment:
ALISTEN_PUBLIC_URL: https://${ALISTEN_DOMAIN}
STORAGE_PUBLIC_URL: ${STORAGE_PUBLIC_URL}
networks:
- backend
- db
- proxy
labels:
- traefik.enable=true
- traefik.http.services.serve.loadbalancer.server.port=8080
- traefik.http.routers.serve.rule=Host(`${ALISTEN_DOMAIN}`) && (PathPrefix(`/api/`) || Path(`/ws`) || PathPrefix(`/media/`))
- traefik.http.routers.serve.entrypoints=websecure
- traefik.http.routers.serve.middlewares=hsts,security-headers@docker
- traefik.http.routers.serve.service=serve
- traefik.http.routers.admin.rule=Host(`${ALISTEN_DOMAIN}`) && PathPrefix(`/api/admin/`)
- traefik.http.routers.admin.entrypoints=websecure
- traefik.http.routers.admin.priority=100
- traefik.http.routers.admin.middlewares=hsts,security-headers,admin-ratelimit@docker
- traefik.http.routers.admin.service=serve
- traefik.http.services.serve.loadbalancer.healthcheck.path=/readyz
- traefik.http.services.serve.loadbalancer.healthcheck.port=9090
- traefik.http.services.serve.loadbalancer.healthcheck.interval=1s
- traefik.http.services.serve.loadbalancer.healthcheck.timeout=1s
worker:
networks:
- backend
- db
web:
ports: !reset []
environment: !reset {}
networks:
- proxy
labels:
- traefik.enable=true
- traefik.http.routers.web.rule=Host(`${ALISTEN_DOMAIN}`)
- traefik.http.routers.web.entrypoints=websecure
- traefik.http.routers.web.middlewares=hsts,security-headers@docker
- traefik.http.services.web.loadbalancer.server.port=8080
postgres:
networks:
- db
redis:
networks:
- db
rustfs:
networks:
- proxy
- backend
labels:
- traefik.enable=true
- traefik.http.routers.storage.rule=Host(`${STORAGE_DOMAIN}`) && PathPrefix(`/${STORAGE_BUCKET_NAME}/link/`) && (Method(`GET`) || Method(`HEAD`))
- traefik.http.routers.storage.entrypoints=websecure
- traefik.http.routers.storage.middlewares=storage-headers,hsts@docker
- traefik.http.middlewares.storage-headers.headers.contentsecuritypolicy=sandbox; default-src 'none'
- traefik.http.middlewares.storage-headers.headers.contenttypenosniff=true
- traefik.http.services.storage.loadbalancer.server.port=9000
networks:
proxy:
name: proxy
backend:
name: alisten-backend
db:
name: alisten-db
volumes:
letsencrypt: