docker-compose.yml 3.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131
  1. services:
  2. postgres:
  3. image: postgres:16-alpine
  4. container_name: vidreview-db
  5. environment:
  6. POSTGRES_USER: vidreview
  7. POSTGRES_PASSWORD: vidreview123
  8. POSTGRES_DB: vidreview
  9. ports:
  10. - '5432:5432'
  11. volumes:
  12. - postgres_data:/var/lib/postgresql/data
  13. healthcheck:
  14. test: ['CMD-SHELL', 'pg_isready -U vidreview']
  15. interval: 5s
  16. timeout: 5s
  17. retries: 5
  18. # ── Init (runs once on fresh deploy) ───────────────────────────────────────
  19. init:
  20. build:
  21. context: .
  22. dockerfile: Dockerfile.api
  23. container_name: vidreview-init
  24. entrypoint: ['bash', '/scripts/init-admin.sh']
  25. environment:
  26. DB_HOST: vidreview-db
  27. DB_NAME: vidreview
  28. DB_USER: vidreview
  29. DB_PASS: vidreview123
  30. API_CONTAINER: vidreview-api
  31. OUTPUT_DIR: /seed-output
  32. ADMIN_EMAIL: admin@vidreview.local
  33. ADMIN_NAME: Admin
  34. volumes:
  35. - /var/run/docker.sock:/var/run/docker.sock:rw
  36. - /usr/bin/docker:/usr/bin/docker:rw
  37. - ./scripts:/scripts
  38. - seed_output:/seed-output
  39. depends_on:
  40. postgres:
  41. condition: service_healthy
  42. api:
  43. condition: service_healthy
  44. restart: 'no'
  45. api:
  46. build:
  47. context: .
  48. dockerfile: Dockerfile.api
  49. container_name: vidreview-api
  50. environment:
  51. DATABASE_URL: postgresql://vidreview:vidreview123@postgres:5432/vidreview
  52. JWT_SECRET: ${JWT_SECRET:-change-me-in-production}
  53. JWT_EXPIRES_IN: ${JWT_EXPIRES_IN:-7d}
  54. API_PORT: 3001
  55. NODE_ENV: production
  56. UPLOAD_DIR: /app/uploads
  57. MAX_FILE_SIZE_MB: 500
  58. ALLOWED_ORIGINS: 'https://vid.k9tech.space,http://vid.k9tech.space,http://10.147.17.128,http://192.168.1.31'
  59. FRONTEND_URL: https://vid.k9tech.space
  60. RESEND_API_KEY: ${RESEND_API_KEY:-}
  61. ports:
  62. - '3001:3001'
  63. depends_on:
  64. postgres:
  65. condition: service_healthy
  66. volumes:
  67. - uploads:/app/uploads
  68. healthcheck:
  69. test: ['CMD-SHELL', 'wget -qO- http://localhost:3001/health || exit 1']
  70. interval: 10s
  71. timeout: 5s
  72. retries: 5
  73. # ── Transcode Worker ──────────────────────────────────────────────────────
  74. worker:
  75. build:
  76. context: .
  77. dockerfile: Dockerfile.api
  78. container_name: vidreview-worker
  79. command: node src/worker/index.js
  80. environment:
  81. DATABASE_URL: postgresql://vidreview:vidreview123@postgres:5432/vidreview
  82. NODE_ENV: production
  83. UPLOAD_DIR: /app/uploads
  84. POLL_INTERVAL_MS: 2000
  85. depends_on:
  86. postgres:
  87. condition: service_healthy
  88. volumes:
  89. - uploads:/app/uploads
  90. restart: unless-stopped
  91. # ── Caddy Reverse Proxy ───────────────────────────────────────────────────
  92. # Receives HTTP traffic forwarded by Synology reverse proxy.
  93. # Routes /api/* → api container, everything else → frontend.
  94. caddy:
  95. image: caddy:2-alpine
  96. container_name: vidreview-caddy
  97. ports:
  98. - '80:80'
  99. - '443:443'
  100. volumes:
  101. - ./Caddyfile:/etc/caddy/Caddyfile:ro
  102. - caddy_data:/data
  103. - caddy_config:/config
  104. depends_on:
  105. - frontend
  106. - api
  107. frontend:
  108. build:
  109. context: .
  110. dockerfile: Dockerfile.frontend
  111. container_name: vidreview-frontend
  112. environment:
  113. NEXT_PUBLIC_API_URL: https://vid.k9tech.space/api
  114. NODE_ENV: production
  115. expose:
  116. - '3000'
  117. depends_on:
  118. api:
  119. condition: service_healthy
  120. volumes:
  121. postgres_data:
  122. uploads:
  123. seed_output:
  124. caddy_data:
  125. caddy_config: