-
Notifications
You must be signed in to change notification settings - Fork 0
Expand file tree
/
Copy pathdocker-compose.yml
More file actions
103 lines (100 loc) · 3.85 KB
/
Copy pathdocker-compose.yml
File metadata and controls
103 lines (100 loc) · 3.85 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
# Titen — local dev / single-host deploy via Docker Compose.
#
# Two-container architecture:
# - web: SvelteKit SSR server (Bun + adapter-node) — serves pages + proxies /api
# - api: Rust Axum backend — API, scheduling, Threads integration
#
# Default: build from source. For production, set image tags in .env:
# WEB_IMAGE=ghcr.io/codecoradev/titen:latest-web
# API_IMAGE=ghcr.io/codecoradev/titen:latest-api
# docker compose pull && docker compose up -d
#
# SQLite database persists to a bind-mounted volume (./data/).
#
# Usage:
# cp .env.example .env # fill in TITEN_API_KEY + OAuth creds
# docker compose up --build # build locally + start
#
# Production: set TRAEFIK_ENABLED=true + TITEN_HOST + join an external
# Traefik network (TRAEFIK_NETWORK). When TRAEFIK_ENABLED=false the web
# service publishes its port to the host (local dev).
#
# NOTE: The web container (SvelteKit) handles all HTTP routing. /api/* and
# /health requests are forwarded to the api container via Docker internal
# network. Traefik only needs to route to the web service.
services:
web:
image: ${WEB_IMAGE:-}
build:
context: .
dockerfile: Dockerfile
target: web
container_name: titen-web
restart: unless-stopped
ports:
- "${WEB_PORT:-3000}:3000"
environment:
- HOST=0.0.0.0
- PORT=3000
- ORIGIN=${APP_URL:-http://localhost:3000}
- API_INTERNAL=http://api:7845
depends_on:
- api
labels:
# ── Traefik reverse-proxy + auto-HTTPS ────────────────────────
- "traefik.enable=${TRAEFIK_ENABLED:-false}"
- "traefik.docker.network=${TRAEFIK_NETWORK:-traefik-public}"
- "traefik.http.routers.titen-web.rule=Host(`${TITEN_HOST:-titen.azfirazka.com}`)"
- "traefik.http.routers.titen-web.entrypoints=${TRAEFIK_ENTRYPOINTS:-websecure}"
- "traefik.http.routers.titen-web.tls=true"
- "traefik.http.routers.titen-web.tls.certresolver=${CERTRESOLVER:-myresolver}"
- "traefik.http.services.titen-web.loadbalancer.server.port=3000"
networks:
- default
- traefik
api:
image: ${API_IMAGE:-}
build:
context: .
dockerfile: Dockerfile
target: api
container_name: titen-api
restart: unless-stopped
# API is NOT exposed to the host in production — only accessible from
# the web container via Docker network on port 7845.
expose:
- "7845"
volumes:
# Bind-mount SQLite so the DB survives container rebuilds.
- ./data:/data
environment:
- RUST_LOG=${RUST_LOG:-titen_api=info,tower_http=info}
- TITEN_DB_PATH=/data/titen.db
- TITEN_HOST=0.0.0.0
- TITEN_PORT=7845
- TITEN_API_KEY=${TITEN_API_KEY:-}
- TITEN_CORS_ORIGINS=${TITEN_CORS_ORIGINS:-}
- TITEN_ENCRYPTION_KEY=${TITEN_ENCRYPTION_KEY:-}
- TITEN_REQUIRE_ENCRYPTION=${TITEN_REQUIRE_ENCRYPTION:-false}
- TITEN_COOKIE_SECURE=${TITEN_COOKIE_SECURE:-false}
- TITEN_SCHEDULER_INTERVAL_SECS=${TITEN_SCHEDULER_INTERVAL_SECS:-60}
- TITEN_S3_ENDPOINT=${TITEN_S3_ENDPOINT:-}
- TITEN_S3_BUCKET=${TITEN_S3_BUCKET:-}
- TITEN_S3_ACCESS_KEY=${TITEN_S3_ACCESS_KEY:-}
- TITEN_S3_SECRET_KEY=${TITEN_S3_SECRET_KEY:-}
- TITEN_S3_REGION=${TITEN_S3_REGION:-}
- TITEN_S3_PUBLIC_URL=${TITEN_S3_PUBLIC_URL:-}
networks:
- default
networks:
default:
name: titen
# External Traefik network — must already exist in production (created by
# the Traefik stack). The web container joins it so Traefik can route :3000.
# For local-only compose without Traefik, create once:
# docker network create traefik-public
# Or use: docker compose up (without TRAEFIK_ENABLED) — the traefik
# network is only required when TRAEFIK_ENABLED=true.
traefik:
name: ${TRAEFIK_NETWORK:-traefik-public}
external: ${TRAEFIK_EXTERNAL:-false}