docker/unified: derive rootless image from root container - #644
Conversation
…DA build Build the root image once, then derive the rootless variant from it using a small inline Dockerfile that adds the non-root user and chowns the writable directories. This halves the number of CI jobs (4 → 2) and eliminates the redundant full CUDA compilation for the rootless variant. - remove RUN_UID build arg from build-image.sh - derive rootless image inline after root build completes - collapse variant matrix out of unified-docker.yml - push both root and rootless tags in a single CI job Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
WalkthroughThis PR modifies the unified Docker image build workflow to eliminate the Changes
Estimated code review effort🎯 3 (Moderate) | ⏱️ ~25 minutes Possibly related PRs
🚥 Pre-merge checks | ✅ 3✅ Passed checks (3 passed)
✏️ Tip: You can configure your own custom pre-merge checks in the settings. ✨ Finishing Touches🧪 Generate unit tests (beta)
Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out. Comment |
There was a problem hiding this comment.
🧹 Nitpick comments (2)
.github/workflows/unified-docker.yml (1)
102-109: Define the base tag once.
DOCKER_IMAGE_TAGandBASE_TAGare the same value, but they're assembled in two different steps. Hoisting that to a job-level env would remove an easy build/push drift point the next time the tag format changes.Also applies to: 121-121
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In @.github/workflows/unified-docker.yml around lines 102 - 109, Define a single base tag env var at the job level (e.g., BASE_TAG) and use it wherever the image tag is needed instead of constructing the same string in multiple steps; specifically, replace the duplicated assembly of DOCKER_IMAGE_TAG in the step that sets DOCKER_IMAGE_TAG and the separate BASE_TAG usage (referenced as DOCKER_IMAGE_TAG and BASE_TAG in the diff) by hoisting BASE_TAG = ghcr.io/mostlygeek/llama-swap:unified-${{ matrix.backend }} into the job env and change DOCKER_IMAGE_TAG to reference that BASE_TAG (and update the other occurrence at the second location that also constructs the tag).docker/unified/build-image.sh (1)
257-275: Add one smoke test for the rootless tag before declaring success.The verification block above only exercises
${DOCKER_IMAGE_TAG}. Since the workflow pushes${ROOTLESS_TAG}immediately afterward, a permissions/runtime regression in the derived image would currently ship without CI ever running it.🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed. In `@docker/unified/build-image.sh` around lines 257 - 275, After building the rootless image (ROOTLESS_TAG), run a small smoke test before printing success: pull/run the image using the same runtime flags as used for ${DOCKER_IMAGE_TAG} (e.g., docker run --rm -u 10001 or equivalent) and execute a lightweight command that verifies startup and filesystem permissions (for example check that /app and /models are accessible as UID 10001 and that the process can run a health command); if the container fails or permission checks fail, exit non‑zero and print the container logs. Insert this check immediately after the docker buildx build --load -t "${ROOTLESS_TAG}" ... EOF block and before the final echo "Rootless image built: ${ROOTLESS_TAG}" so the script only declares success when the smoke test passes.
🤖 Prompt for all review comments with AI agents
Verify each finding against the current code and only fix it if needed.
Nitpick comments:
In @.github/workflows/unified-docker.yml:
- Around line 102-109: Define a single base tag env var at the job level (e.g.,
BASE_TAG) and use it wherever the image tag is needed instead of constructing
the same string in multiple steps; specifically, replace the duplicated assembly
of DOCKER_IMAGE_TAG in the step that sets DOCKER_IMAGE_TAG and the separate
BASE_TAG usage (referenced as DOCKER_IMAGE_TAG and BASE_TAG in the diff) by
hoisting BASE_TAG = ghcr.io/mostlygeek/llama-swap:unified-${{ matrix.backend }}
into the job env and change DOCKER_IMAGE_TAG to reference that BASE_TAG (and
update the other occurrence at the second location that also constructs the
tag).
In `@docker/unified/build-image.sh`:
- Around line 257-275: After building the rootless image (ROOTLESS_TAG), run a
small smoke test before printing success: pull/run the image using the same
runtime flags as used for ${DOCKER_IMAGE_TAG} (e.g., docker run --rm -u 10001 or
equivalent) and execute a lightweight command that verifies startup and
filesystem permissions (for example check that /app and /models are accessible
as UID 10001 and that the process can run a health command); if the container
fails or permission checks fail, exit non‑zero and print the container logs.
Insert this check immediately after the docker buildx build --load -t
"${ROOTLESS_TAG}" ... EOF block and before the final echo "Rootless image built:
${ROOTLESS_TAG}" so the script only declares success when the smoke test passes.
ℹ️ Review info
⚙️ Run configuration
Configuration used: Path: .coderabbit.yaml
Review profile: CHILL
Plan: Pro
Run ID: fcc9cb99-b193-4bc7-8f5b-3dbbefaf7f85
📒 Files selected for processing (2)
.github/workflows/unified-docker.ymldocker/unified/build-image.sh
…#644) Build the root image once, then derive the rootless variant from it using a small inline Dockerfile that adds the non-root user and chowns the writable directories. This halves the number of CI jobs (4 → 2) and eliminates the redundant full CUDA compilation for the rootless variant. - remove RUN_UID build arg from build-image.sh - derive rootless image inline after root build completes - collapse variant matrix out of unified-docker.yml - push both root and rootless tags in a single CI job Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Build the root image once, then derive the rootless variant from it using a small inline Dockerfile that adds the non-root user and chowns the writable directories. This halves the number of CI jobs (4 → 2) and eliminates the redundant full CUDA compilation for the rootless variant. - remove RUN_UID build arg from build-image.sh - derive rootless image inline after root build completes - collapse variant matrix out of unified-docker.yml - push both root and rootless tags in a single CI job Co-authored-by: Claude Sonnet 4.6 <noreply@anthropic.com>
Build the root image once, then derive the rootless variant from it using a small inline Dockerfile that adds the non-root user and chowns the writable directories. This halves the number of CI jobs (4 → 2) and eliminates the redundant full CUDA compilation for the rootless variant.