From 6eb629891d1f8ec3228c672d3d4e45f1dbf761ab Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?=E8=B6=85=E6=B8=A1=E6=B3=95=E5=B8=AB?= <超渡法師@openab.dev> Date: Sat, 27 Jun 2026 23:47:27 +0000 Subject: [PATCH 1/2] perf(ci): use stage aliasing to skip Rust recompilation in build-agents Refactor Dockerfile.unified to use BuildKit dependency pruning: - Rename builder stage to local_builder (actual compilation) - Add global ARG BUILDER_IMAGE=local_builder (before first FROM) - Add builder alias stage (FROM ${BUILDER_IMAGE} AS builder) - When BUILDER_IMAGE is overridden in CI, BuildKit prunes local_builder - All 14 agent targets remain unchanged (COPY --from=builder) - Align build-operator.yml and smoke-test-unified.yml - Remove redundant cache-from in build-agents jobs This eliminates redundant Rust compilation in build-agents jobs, reducing each variant build from 6-14 min to <1 min. Closes #1224 --- .github/workflows/build-images.yml | 5 +--- .github/workflows/build-operator.yml | 7 ++---- .../workflows/docker-smoke-test-unified.yml | 2 +- Dockerfile.unified | 24 +++++++++++++++---- 4 files changed, 23 insertions(+), 15 deletions(-) diff --git a/.github/workflows/build-images.yml b/.github/workflows/build-images.yml index 2b8811eaa..5fcc3a042 100644 --- a/.github/workflows/build-images.yml +++ b/.github/workflows/build-images.yml @@ -121,7 +121,7 @@ jobs: with: context: . file: Dockerfile.unified - target: builder + target: local_builder platforms: ${{ matrix.platform.os }} push: true tags: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}/builder:${{ needs.matrix.outputs.tag }}-${{ matrix.platform.arch }} @@ -168,9 +168,6 @@ jobs: build-args: | BUILDER_IMAGE=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}/builder:${{ needs.matrix.outputs.tag }}-${{ matrix.platform.arch }} outputs: type=image,name=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }},push-by-digest=true,name-canonical=true,push=true - cache-from: | - type=registry,ref=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}/builder:${{ needs.matrix.outputs.tag }}-${{ matrix.platform.arch }} - type=gha,scope=builder-${{ matrix.platform.arch }} - name: Export digest run: | diff --git a/.github/workflows/build-operator.yml b/.github/workflows/build-operator.yml index b95926c09..832482785 100644 --- a/.github/workflows/build-operator.yml +++ b/.github/workflows/build-operator.yml @@ -107,7 +107,7 @@ jobs: with: context: . file: Dockerfile.unified - target: builder + target: local_builder platforms: ${{ matrix.platform.os }} # Always push builder — it's an internal image needed by build-agents. # dry_run only gates the final agent image push + manifest creation. @@ -154,10 +154,7 @@ jobs: BUILDER_IMAGE=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}/builder:${{ needs.resolve-tag.outputs.chart_version }}-${{ matrix.platform.arch }} outputs: type=image,name=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }},push-by-digest=true,name-canonical=true,push=${{ inputs.dry_run != true }} no-cache: ${{ inputs.no_cache == true }} - cache-from: | - type=registry,ref=${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}/builder:${{ needs.resolve-tag.outputs.chart_version }}-${{ matrix.platform.arch }} - ${{ inputs.no_cache != true && format('type=gha,scope=unified-builder-{0}', matrix.platform.arch) || '' }} - ${{ inputs.no_cache != true && format('type=gha,scope=unified-agent-{0}-{1}', matrix.agent, matrix.platform.arch) || '' }} + cache-from: ${{ inputs.no_cache != true && format('type=gha,scope=unified-agent-{0}-{1}', matrix.agent, matrix.platform.arch) || '' }} cache-to: ${{ inputs.no_cache != true && format('type=gha,scope=unified-agent-{0}-{1},mode=max', matrix.agent, matrix.platform.arch) || '' }} - name: Export digest diff --git a/.github/workflows/docker-smoke-test-unified.yml b/.github/workflows/docker-smoke-test-unified.yml index 8bd3c0975..87924a23f 100644 --- a/.github/workflows/docker-smoke-test-unified.yml +++ b/.github/workflows/docker-smoke-test-unified.yml @@ -30,7 +30,7 @@ jobs: with: context: . file: Dockerfile.unified - target: builder + target: local_builder load: true tags: openab-builder:local cache-to: type=gha,scope=unified-smoke-builder,mode=max diff --git a/Dockerfile.unified b/Dockerfile.unified index 4c6102cd0..0d906a789 100644 --- a/Dockerfile.unified +++ b/Dockerfile.unified @@ -1,14 +1,23 @@ # Dockerfile.unified — Single multi-target Dockerfile for all OpenAB agent variants. # Usage: docker build --target -t ghcr.io/openabdev/openab:- . # -# The shared builder compiles the openab binary once (unified mode, superset). -# Each agent target is a thin runtime layer that installs only the agent CLI. +# Architecture: +# local_builder — compiles the openab binary (only runs locally or in build-core CI job) +# builder — alias that resolves to local_builder (default) or a prebuilt registry +# image (when BUILDER_IMAGE is overridden in CI). BuildKit prunes +# local_builder when it's not needed. +# — thin runtime layer that installs only the agent CLI + copies binary +# from builder stage. + +# Global ARG — must be declared before first FROM for use in FROM instructions +ARG BUILDER_IMAGE=local_builder # ============================================================================= -# Stage: builder — compile openab binary (unified mode) +# Stage: local_builder — compile openab binary (unified mode) +# Only executed during build-core or local dev. When BUILDER_IMAGE is overridden +# (CI build-agents), BuildKit prunes this stage entirely via dependency analysis. # ============================================================================= -ARG BUILDER_IMAGE=rust:1-bookworm -FROM ${BUILDER_IMAGE} AS builder +FROM rust:1-bookworm AS local_builder WORKDIR /build COPY Cargo.toml Cargo.lock ./ COPY crates/openab-core/Cargo.toml crates/openab-core/Cargo.toml @@ -30,6 +39,11 @@ RUN cd openab-agent && printf '\n[workspace]\n' >> Cargo.toml && cargo build --r COPY agy-acp/ agy-acp/ RUN cd agy-acp && printf '\n[workspace]\n' >> Cargo.toml && cargo build --release +# ============================================================================= +# Stage: builder — resolves to either local_builder or prebuilt registry image +# ============================================================================= +FROM ${BUILDER_IMAGE} AS builder + # ============================================================================= # Stage: base-debian — shared runtime base for debian-based agents # ============================================================================= From 2a41dc1c99eb9b4e2339ebf1601d0f361d9803b5 Mon Sep 17 00:00:00 2001 From: chaodu-agent Date: Sun, 28 Jun 2026 04:39:14 +0000 Subject: [PATCH 2/2] fix(ci): add binary sanity check to builder alias stage The PR description claimed a test -x check existed in the alias stage but it was missing. Add it to catch missing binaries early when using a prebuilt registry image. --- Dockerfile.unified | 3 +++ 1 file changed, 3 insertions(+) diff --git a/Dockerfile.unified b/Dockerfile.unified index 0d906a789..588057761 100644 --- a/Dockerfile.unified +++ b/Dockerfile.unified @@ -43,6 +43,9 @@ RUN cd agy-acp && printf '\n[workspace]\n' >> Cargo.toml && cargo build --releas # Stage: builder — resolves to either local_builder or prebuilt registry image # ============================================================================= FROM ${BUILDER_IMAGE} AS builder +RUN test -x /build/target/release/openab \ + && test -x /build/openab-agent/target/release/openab-agent \ + && test -x /build/agy-acp/target/release/agy-acp # ============================================================================= # Stage: base-debian — shared runtime base for debian-based agents