visionA/docker-compose.stage.yml
jim800121chen eb66a7287a feat(deploy): visionA Cloud dev / stage docker compose + Caddy/nginx + 部署腳本
新增雲端版部署設定(Phase 0.6 dev + Phase 0.7 stage 分兩套):

dev 環境(docker-compose.dev.yml):
- 5 service all-in-one(postgres + member-center + visionA-backend + frontend + Caddy)
- Caddy 自動 HTTPS for localhost
- .env.dev.example 範本(使用者拷出 .env.dev 後 docker compose up -d)
- Makefile dev-with-mc 9 個 target

stage 環境(docker-compose.stage.yml + docker/Dockerfile.stage):
- multi-stage build(node22 frontend + go1.26 backend × 2 + nginx-alpine runtime)
  最終 image 319 MB,含 nginx + nodejs + tini + bash
- entrypoint.stage.sh 4 process 共命運(nginx + api-server + remote-proxy +
  next.js standalone)用 wait -n + SIGTERM trap
- nginx.stage.conf:白名單 server_name stage-9527.innovedus.com + 444 default_server
  + /healthz 例外(127.0.0.0/8 only)+ /api/ 與 /storage/ 強制 no-store
  + /tunnel/connect WS upgrade + 100M body / 3600s timeout
- 對外 mapping 0.0.0.0:9527:80(公司 host nginx 在外層處理 HTTPS termination
  — Let's Encrypt stage-9527.innovedus.com 自動續簽)
- named volume visiona-data(不用 bind mount,因 stage docker daemon 在 host root
  無 mkdir 權限)

部署腳本(scripts/deploy-stage.sh):
- 仿 edge-ai-platform/scripts/deploy-docker.sh 早期 save/load 模式
- 為什麼不用 internal registry:公司 192.168.0.130:5000 開了 auth、無帳密
- 流程:buildx --load → docker save | gzip → DOCKER_HOST docker load → compose up
- 含 --rollback <tag> / --skip-build / --no-push / --skip-deploy 選項
- timestamp + git SHA tag 留 rollback 餘地

文件(docs/):
- DEV-SETUP.md:dev 環境一鍵起步驟
- SMOKE-TEST.md:手動煙測 checklist(OIDC flow / pairing / tunnel)
- STAGE-DEPLOY.md:stage 完整手冊(架構圖 / 環境前置 / 部署 step / rollback /
  7 種故障排除 / 緊急救回 POC)

.env.stage.example 對齊 backend A1 改造:
- VISIONA_OIDC_CLIENT_SECRET 留空(PKCE-only public client)
- VISIONA_OIDC_SERVICE_CLIENT_ID/_SECRET 留空(Phase 1 預留鉤子)
- 所有 secret 用 placeholder(CHANGE_ME_OPENSSL_RAND_HEX_32)

.dockerignore:避免 node_modules / .next / .git 等進 build context

Co-Authored-By: Claude Opus 4.7 (1M context) <noreply@anthropic.com>
2026-05-01 11:22:44 +08:00

57 lines
2.4 KiB
YAML
Raw Blame History

This file contains ambiguous Unicode characters

This file contains Unicode characters that might be confused with other characters. If you think that this is intentional, you can safely ignore this warning. Use the Escape button to reveal them.

# visionA — stage 環境 docker-compose
#
# 使用情境:
# - 此檔放在 stage host/opt/visiona/docker-compose.stage.yml或由 deploy-stage.sh 從 dev 機透過 DOCKER_HOST 直接執行,--project-directory 指向 dev repo root 也可)
# - .env.stage 同目錄(不進 git由人工放上去
# - image 由 deploy-stage.sh 透過 docker save | DOCKER_HOST docker load 直接打進 stage docker daemon
# (沒有 registry pull — 公司 internal registry 開了 auth 暫不採用;見 deploy-stage.sh "SAVE_LOAD" 區塊)
#
# 部署流程:
# 1. 開發機跑 scripts/deploy-stage.sh
# → buildx --load 進本機 daemon
# → docker save | gzip | DOCKER_HOST=tcp://... docker load
# 2. docker compose -f docker-compose.stage.yml up -d透過 DOCKER_HOST 在 stage 上執行)
#
# Container 對外只開 :9527 → 容器內 nginx :80。
# 公司 host nginx 在外層 termination HTTPSstage-9527.innovedus.com:9527 LE 證書)。
services:
visiona:
# local imagesave/load 模式)— 不帶 registry prefixdocker compose 不會試著去 pull
image: visiona:stage
pull_policy: never
container_name: visiona
restart: unless-stopped
# 公司 host nginx 期望 upstream 是 host:9527 → 這裡 host port 必須是 9527
ports:
- "0.0.0.0:9527:80"
env_file:
- .env.stage
# local-fs 雛形儲存:用 named volume不用 bind mount
# 為什麼不用 bind mount /opt/visiona/data
# - compose 從 dev 機透過 DOCKER_HOST 執行,相對路徑會解成 dev 機路徑
# - stage docker daemon 在 host root 沒 mkdir 權限(試過 bind /opt/visiona 失敗)
# named volume 由 docker 自己管,存在 stage host 的 docker volume 區(通常 /var/lib/docker/volumes/
# 升級到 S3 backend 後可拿掉
volumes:
- visiona-data:/data
# 直接讓 container healthcheck 接管Dockerfile 已定義 /healthz 探測)
# 這裡不重複 healthcheck但補 logging driver 限制磁碟用量
logging:
driver: json-file
options:
max-size: "50m"
max-file: "5"
# 注意:不掛 /etc/localtime公司 stage host 與 container 都用 UTC
# 如需指定時區,改用 env TZ=Asia/TaipeiDockerfile 已裝 tzdata
# top-level named volume — 對應 service 的 visiona-data 引用
volumes:
visiona-data:
driver: local