# ============================================ # OpenCode WebUI - Frontend # ============================================ # 纯前端静态文件 + Caddy 反向代理 API # ---- Stage 1: 构建前端 ---- # 前端产物是静态文件,和目标 CPU 架构无关。 # 多架构镜像构建时让 Node builder 始终跑在构建机原生平台,避免 arm64 通过 QEMU 重跑 npm/vite 构建。 FROM --platform=$BUILDPLATFORM node:22-alpine AS builder ARG NPM_REGISTRY=https://registry.npmjs.org/ ARG NPM_REGISTRY_FALLBACK=https://registry.npmmirror.com/ WORKDIR /app COPY package.json package-lock.json ./ RUN set -eux; \ npm config set registry "${NPM_REGISTRY}"; \ npm config set fetch-retries 5; \ npm config set fetch-retry-factor 2; \ npm config set fetch-retry-mintimeout 10000; \ npm config set fetch-retry-maxtimeout 120000; \ npm config set audit false; \ npm config set fund false; \ if npm ci --ignore-scripts; then \ exit 0; \ fi; \ echo "npm ci failed on ${NPM_REGISTRY}, retrying with ${NPM_REGISTRY_FALLBACK}"; \ npm cache clean --force; \ npm config set registry "${NPM_REGISTRY_FALLBACK}"; \ npm ci --ignore-scripts COPY . . RUN node scripts/copy-material-icons.mjs ENV VITE_API_BASE_URL=/api RUN npm run build # ---- Stage 2: Caddy 运行时 ---- FROM caddy:2-alpine # 前端静态文件 COPY --from=builder /app/dist /srv # Caddy 配置(默认 + standalone) COPY docker/Caddyfile /etc/caddy/Caddyfile COPY docker/Caddyfile.standalone /etc/caddy/Caddyfile.standalone EXPOSE 3000 CMD ["caddy", "run", "--config", "/etc/caddy/Caddyfile"]