Docker Buildx Stale Rust Binary Cache
SkillCloud & infraFix deployed Rust binaries not reflecting code changes when using docker buildx. Use when: (1) Code changes are verified locally (tests pass) but production behavior doesn't change after deploy, (2) Docker image has a new tag but contains old compiled binary, (3) Dockerfile uses multi-stage build with dependency pre-compilation layer and source copy layer. Docker buildx layer caching can serve stale compilation output even when source files change, especially with cross-compilation (--platform linux/amd64).
Available today. Use it from your connected AI after setup.
No other account needed.
Connect ahel once, and every AI you use reads what you have installed.
Then ask your AI: use the Docker Buildx Stale Rust Binary Cache skill
What this skill tells your AI
The instructions your AI receives, as published by divinevideo/divine-mobile in .agents/skills/docker-buildx-stale-rust-binary/SKILL.md and read by ahel’s review.
Problem
Docker buildx may serve stale compiled Rust binaries from layer cache even when source
files have changed. The image gets a new tag and pushes successfully, but contains the
old compiled binary. This is especially common with cross-platform builds
(--platform linux/amd64 on ARM Macs).
Context / Trigger Conditions
- Dockerfile uses multi-stage pattern: copy Cargo.toml → build deps → copy source → build
- Using
docker buildx build --pushwith--platform linux/amd64 - Code changes verified locally (tests pass) but production shows old behavior
- Image digest from cached build differs from
--no-cachebuild - Adding a simple response header in code and it doesn't appear in production
Solution
Always use --no-cache when deploying code changes:
# WRONG — may use cached compilation layer with old code
docker buildx build --platform linux/amd64 --target api \
-t registry/image:tag --push .
# CORRECT — forces full recompilation
docker buildx build --platform linux/amd64 --target api \
--no-cache -t registry/image:tag --push .
Verification
Compare image digests between cached and no-cache builds:
# Build with cache
docker buildx build --platform linux/amd64 --target api \
-t registry/image:cached --push . 2>&1 | grep "pushing manifest"
# Note the sha256 digest
# Build without cache
docker buildx build --platform linux/amd64 --target api \
--no-cache -t registry/image:nocache --push . 2>&1 | grep "pushing manifest"
# Note the sha256 digest
# If digests differ, the cached build had stale code
Example
Typical Dockerfile pattern vulnerable to this:
# Layer 1: Copy manifests (cached if Cargo.toml unchanged)
COPY Cargo.toml Cargo.lock ./
COPY crates/*/Cargo.toml crates/
# Layer 2: Build dependencies (cached — this is the good cache)
RUN cargo build --release && rm -rf src crates
# Layer 3: Copy actual source (SHOULD invalidate on source change)
COPY crates crates
COPY bin bin
# Layer 4: Rebuild with actual source
RUN touch crates/*/src/lib.rs && cargo build --release
The issue: buildx's content-addressable cache may match Layer 4's output from a previous build if the intermediate representations happen to collide, especially during cross-compilation where the build environment state is more complex.
Notes
- This primarily affects
--platformcross-compilation builds (ARM → x86) - Native-platform builds are less likely to hit this issue
- The
--no-cacheflag adds ~5-10 minutes to Rust builds but guarantees fresh compilation - Alternative: use
--cache-fromwith explicit cache scoping to avoid stale layers - Consider adding a build-time env var (like commit hash) that forces layer invalidation:
ARG BUILD_HASH RUN echo $BUILD_HASH && cargo build --release
Signals
- GitHub stars
- 264
- Forks
- 55
- Last commit
- Sep 2026
ahel review
S4info
community integration — published by divinevideo, not docker
Automated review, not a security audit. Ruleset v1.
Advanced
- Catalog kind
- skill
- Gateway key
docker-buildx-stale-rust-binary- Source
- github.com/divinevideo/divine-mobile