- Build stage keeps Bun for fast installs; appends `npm install --package-lock-only`
to generate an ephemeral package-lock.json immediately after `bun run build:all`.
- Runtime stage removes BUN_VERSION ARG/ENV, the bun.sh curl install, and
`bun install --frozen-lockfile --production`. Replaces with:
COPY --from=build /app/package.json /app/package-lock.json ./
RUN npm ci --omit=dev --ignore-scripts
- --ignore-scripts rationale: postinstall (scripts/postinstall.js) writes ~/.ccs/
config — not needed in Docker context. bcrypt v6+ is pure-JS, no native compile.
- package-lock.json already in .gitignore (line 33); never committed.
- docker/Dockerfile.integrated unchanged — no Bun present there (alpine + npm).
- Targets: image size reduction >= 300 MB by eliminating ~130 MB Bun binary + installer.
* feat(docker): parameterize Dockerfile.integrated with ARG FLAVOR=minimal|full
Add FLAVOR build arg that gates the AI CLI install layer (claude-code,
gemini-cli, grok-cli, opencode) so one Dockerfile produces both the
minimal (< 350 MB) and full (< 600 MB) integrated images.
Use BuildKit cache mount for /root/.npm to speed up repeated builds.
Part of #1251 (P1 — publish integrated images).
* feat(docker): emit startup deprecation warning in legacy ccs-dashboard entrypoint
Prepend a [WARN] line to stderr on every container start so operators
running ghcr.io/kaitranntt/ccs-dashboard:latest are notified to migrate
to ghcr.io/kaitranntt/ccs:latest. Sunset window: 2 releases. See #1251.
* test(docker): add image-size.sh budget assertion + unit test suite
image-size.sh: asserts docker image inspect .Size against a byte budget.
Usage: image-size.sh <image:tag> <max-bytes>
Budgets: minimal=350 MB (367001600), full=600 MB (629145600)
image-size-logic.test.sh: 6 mock-docker unit tests covering pass/fail
boundaries, bad arg count, and non-integer input. All 6 pass locally.
Part of #1251 (P1).
* ci(docker): extend docker-release.yml to publish ccs:latest and ccs:full
- Add publish-integrated job with matrix flavor: [minimal, full]
- minimal -> ghcr.io/kaitranntt/ccs:<ver> + :latest (when promoted)
- full -> ghcr.io/kaitranntt/ccs:full-<ver> + :full (when promoted)
- Multi-arch: linux/amd64 + linux/arm64 via buildx
- Scoped GHA cache per flavor to avoid cross-contamination
- Add promote_to_latest workflow_dispatch input (default false)
- rc.1 soak: first publish only pushes immutable version tag
- Mutable :latest/:full promoted only on release event OR explicit opt-in
- Add smoke-test job (post-publish) for each flavor
- Pulls the just-published version tag
- Asserts image size via tests/docker/image-size.sh
- Boots container, waits for healthcheck, probes :3000 and :8317
- Keep publish-dashboard job unchanged (legacy 2-release sunset)
- Updated labels to note deprecation status
All jobs run on self-hosted cliproxy runners. Part of #1251 (P1).
* docs(docker): document new image tags, add ccs-dashboard deprecation notices
docker/README.md:
- Add "Choosing an image" table (ccs:latest / ccs:full / ccs-dashboard deprecated)
- Update Quick Start section to use ccs:latest as primary example
- Add legacy image note with sunset timeline
CHANGELOG.md:
- Add Unreleased > ### Deprecated entry for ccs-dashboard:latest
pointing to migration path and #1251
README.md:
- Add one-line deprecation banner near top routing users to ccs:latest
Part of #1251 (P1).
Replace direct volume mountpoint writes (requires root) with docker cp
which works without elevated permissions. Fix malformed npx bcrypt
command — use require('bcrypt') with Node module resolution. Add
security note about not committing password hashes to docker-compose.
- Add test assertion for --host auth reminder message
- Use Node module resolution for bcrypt in README (not hardcoded path)
- Replace cat|grep with direct grep in verification commands
Users deploying via ccs docker up hit silent failures when accessing
the dashboard remotely: empty providers, wrong version badge (v5.0.0),
no CLIProxy detected. Root cause is the dashboard auth middleware
blocking non-localhost API access.
Added sections:
- Dashboard auth setup (required for remote access)
- Auth token migration from previous deployments
- Post-deployment verification checklist
- Troubleshooting: empty dashboard, 0 clients, ETXTBSY race
Closes#841
- document the new ccs docker command suite and remote host staging path
- clarify how the existing prebuilt image differs from the integrated CLI flow
- record issue #812 in the project roadmap
Refs #812