From fcfdafe3b05a0007ba7c584a83e95b8ab9fe7cc1 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mar=C3=ADa=20A=2E=20Matienzo?= Date: Thu, 11 Dec 2025 17:24:16 -0800 Subject: [PATCH 1/3] build multiplatform images for testing --- .github/workflows/build.yml | 141 +++++++++++++++++++++++++++------- .github/workflows/release.yml | 56 ++++++-------- 2 files changed, 134 insertions(+), 63 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index fc13444..ee67ce5 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -3,21 +3,32 @@ name: Build / Test / Push on: push: branches: - - '*' + - '**' + workflow_call: workflow_dispatch: +env: + BUILD_SUFFIX: -build-${{ github.run_id }}_${{ github.run_attempt }} + DOCKER_METADATA_SET_OUTPUT_ENV: 'true' + jobs: build: - runs-on: ubuntu-latest + runs-on: ${{ matrix.runner }} outputs: - build-image: ${{ steps.build-meta.outputs.tags }} + build-image-arm: ${{ steps.gen-output.outputs.image-arm64 }} + build-image-x64: ${{ steps.gen-output.outputs.image-x64 }} + strategy: + fail-fast: false + matrix: + include: + - platform: linux/amd64 + runner: ubuntu-24.04 + - platform: linux/arm64 + runner: ubuntu-24.04-arm steps: - name: Checkout code uses: actions/checkout@v4 - - name: Set up QEMU - uses: docker/setup-qemu-action@v3 - - name: Set up Docker Buildx uses: docker/setup-buildx-action@v3 @@ -28,37 +39,105 @@ jobs: username: ${{ github.actor }} password: ${{ secrets.GITHUB_TOKEN }} - - name: Produce the build image tag - id: build-meta + - id: build-meta + name: Docker meta + uses: docker/metadata-action@v5 + with: + images: ghcr.io/${{ github.repository }} + tags: type=sha,suffix=${{ env.BUILD_SUFFIX }} + + # Build cache is shared among all builds of the same architecture + - id: cache-meta + name: Docker meta uses: docker/metadata-action@v5 with: images: ghcr.io/${{ github.repository }} - tags: type=sha,suffix=-build-${{ github.run_id }}_${{ github.run_attempt }} + tags: type=raw,value=buildcache-${{ runner.arch }} + + - id: get-registry + name: Get the sanitized registry name + run: | + echo "registry=$(echo '${{ steps.build-meta.outputs.tags }}' | cut -f1 -d:)" | tee -a "$GITHUB_OUTPUT" + + - id: set_build_url + name: Set BUILD_URL + run: | + echo "build_url=${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" | tee -a "$GITHUB_OUTPUT" - - name: Build and push the untested image + - id: build + name: Build/push the arch-specific image uses: docker/build-push-action@v6 with: - push: true + platforms: ${{ matrix.platform }} + build-args: | + BUILD_TIMESTAMP=${{ github.event.repository.updated_at }} + BUILD_URL=${{ steps.set_build_url.outputs.build_url }} + GIT_REF_NAME=${{ github.ref_name }} + GIT_SHA=${{ github.sha }} + GIT_REPOSITORY_URL=${{ github.repositoryUrl }} + cache-from: type=registry,ref=${{ steps.cache-meta.outputs.tags }} + cache-to: type=registry,ref=${{ steps.cache-meta.outputs.tags }},mode=max labels: ${{ steps.build-meta.outputs.labels }} - tags: ${{ steps.build-meta.outputs.tags }} - provenance: true - cache-from: type=gha - cache-to: type=gha + provenance: mode=max + sbom: true + tags: ${{ steps.get-registry.outputs.registry }} + outputs: type=image,push-by-digest=true,push=true + + - id: gen-output + name: Write arch-specific image digest to outputs + run: | + echo "image-${RUNNER_ARCH,,}=${{ steps.get-registry.outputs.registry }}@${{ steps.build.outputs.digest }}" | tee -a "$GITHUB_OUTPUT" + + merge: + runs-on: ubuntu-24.04 + needs: + - build + env: + DOCKER_APP_IMAGE_ARM64: ${{ needs.build.outputs.build-image-arm }} + DOCKER_APP_IMAGE_X64: ${{ needs.build.outputs.build-image-x64 }} + outputs: + build-image: ${{ steps.meta.outputs.tags }} + build-image-arm: ${{ needs.build.outputs.build-image-arm }} + build-image-x64: ${{ needs.build.outputs.build-image-x64 }} + steps: + - name: Checkout code + uses: actions/checkout@v4 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + + - name: Login to GitHub Container Registry + uses: docker/login-action@v3 + with: + registry: ghcr.io + username: ${{ github.actor }} + password: ${{ secrets.GITHUB_TOKEN }} + + - name: Docker meta + id: meta + uses: docker/metadata-action@v5 + with: + images: ghcr.io/${{ github.repository }} + tags: | + type=sha,suffix=-build-${{ github.run_id }}_${{ github.run_attempt }} + + - name: Push the multi-platform image + run: | + docker buildx imagetools create \ + --tag "$DOCKER_METADATA_OUTPUT_TAGS" \ + "$DOCKER_APP_IMAGE_ARM64" "$DOCKER_APP_IMAGE_X64" test: - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 needs: - - build + - merge env: COMPOSE_FILE: docker-compose.yml:docker-compose.ci.yml - DOCKER_APP_IMAGE: ${{ needs.build.outputs.build-image }} + DOCKER_APP_IMAGE: ${{ needs.merge.outputs.build-image }} steps: - name: Checkout code uses: actions/checkout@v4 - - name: Set up QEMU - uses: docker/setup-qemu-action@v3 - - name: Set up Docker Compose uses: docker/setup-compose-action@v1 @@ -102,14 +181,21 @@ jobs: if-no-files-found: error push: - runs-on: ubuntu-latest + runs-on: ubuntu-24.04 needs: - - build + - merge - test + env: + DOCKER_APP_IMAGE: ${{ needs.merge.outputs.build-image }} + DOCKER_APP_IMAGE_ARM64: ${{ needs.merge.outputs.build-image-arm }} + DOCKER_APP_IMAGE_X64: ${{ needs.merge.outputs.build-image-x64 }} steps: - name: Checkout code uses: actions/checkout@v4 + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + - name: Login to GitHub Container Registry uses: docker/login-action@v3 with: @@ -128,9 +214,6 @@ jobs: type=raw,value=latest,enable={{is_default_branch}} - name: Retag and push the image - uses: docker/build-push-action@v6 - with: - push: true - labels: ${{ steps.branch-meta.outputs.labels }} - tags: ${{ steps.branch-meta.outputs.tags }} - cache-from: type=registry,ref=${{ needs.build.outputs.build-image }} + run: | + docker buildx imagetools create \ + $(jq -cr '.tags | map("--tag " + .) | join(" ")' <<< "$DOCKER_METADATA_OUTPUT_JSON") $DOCKER_APP_IMAGE_ARM64 $DOCKER_APP_IMAGE_X64 diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index b0ae377..a5a9e26 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -3,18 +3,26 @@ name: Push Release Tags on: push: tags: - - '*' + - '**' + workflow_call: workflow_dispatch: +env: + DOCKER_METADATA_SET_OUTPUT_ENV: 'true' + jobs: - verify: + retag: runs-on: ubuntu-latest - outputs: - base_image: ${{ steps.get-base-image.outputs.tags }} steps: - name: Checkout code uses: actions/checkout@v4 + - name: Set up QEMU + uses: docker/setup-qemu-action@v3 + + - name: Set up Docker Buildx + uses: docker/setup-buildx-action@v3 + - name: Login to GitHub Container Registry uses: docker/login-action@v3 with: @@ -30,33 +38,13 @@ jobs: tags: type=sha - name: Verify that the image was previously built - run: docker pull "$BASE_IMAGE" env: BASE_IMAGE: ${{ steps.get-base-image.outputs.tags }} - - retag: - runs-on: ubuntu-latest - needs: - - verify - steps: - - name: Checkout code - uses: actions/checkout@v4 - - - name: Set up QEMU - uses: docker/setup-qemu-action@v3 - - - name: Set up Docker Buildx - uses: docker/setup-buildx-action@v3 - - - name: Login to GitHub Container Registry - uses: docker/login-action@v3 - with: - registry: ghcr.io - username: ${{ github.actor }} - password: ${{ secrets.GITHUB_TOKEN }} + run: | + docker manifest inspect "$BASE_IMAGE" - name: Produce release tags - id: meta + id: tag-meta uses: docker/metadata-action@v5 with: images: ghcr.io/${{ github.repository }} @@ -67,10 +55,10 @@ jobs: type=semver,pattern={{major}}.{{minor}} type=semver,pattern={{version}} - - name: Retag and push the image - uses: docker/build-push-action@v6 - with: - push: true - labels: ${{ steps.meta.outputs.labels }} - tags: ${{ steps.meta.outputs.tags }} - cache-from: type=registry,ref=${{ needs.verify.outputs.base_image }} + - name: Retag the pulled image + env: + BASE_IMAGE: ${{ steps.get-base-image.outputs.tags }} + run: | + docker buildx imagetools create \ + $(jq -cr '.tags | map("--tag " + .) | join(" ")' <<< "$DOCKER_METADATA_OUTPUT_JSON") \ + "$(echo "$BASE_IMAGE" | cut -f1 -d:)" From cce9b5dc72e40b8b557048cfd08adcca8e601cc5 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mar=C3=ADa=20A=2E=20Matienzo?= Date: Fri, 12 Dec 2025 09:32:26 -0800 Subject: [PATCH 2/3] address pr feedback --- .github/workflows/build.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index ee67ce5..f59cd2d 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -48,7 +48,7 @@ jobs: # Build cache is shared among all builds of the same architecture - id: cache-meta - name: Docker meta + name: Fetch build cache metadata uses: docker/metadata-action@v5 with: images: ghcr.io/${{ github.repository }} From 8045cf89a72ce348187dca75c34b83ce76bc6264 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Mar=C3=ADa=20A=2E=20Matienzo?= Date: Tue, 16 Dec 2025 13:06:15 -0800 Subject: [PATCH 3/3] address PR feedback and clean up --- .github/workflows/build.yml | 6 +++--- .github/workflows/release.yml | 3 --- 2 files changed, 3 insertions(+), 6 deletions(-) diff --git a/.github/workflows/build.yml b/.github/workflows/build.yml index f59cd2d..099c63e 100644 --- a/.github/workflows/build.yml +++ b/.github/workflows/build.yml @@ -40,7 +40,7 @@ jobs: password: ${{ secrets.GITHUB_TOKEN }} - id: build-meta - name: Docker meta + name: Produce the build image tag uses: docker/metadata-action@v5 with: images: ghcr.io/${{ github.repository }} @@ -89,7 +89,7 @@ jobs: echo "image-${RUNNER_ARCH,,}=${{ steps.get-registry.outputs.registry }}@${{ steps.build.outputs.digest }}" | tee -a "$GITHUB_OUTPUT" merge: - runs-on: ubuntu-24.04 + runs-on: ubuntu-latest needs: - build env: @@ -128,7 +128,7 @@ jobs: "$DOCKER_APP_IMAGE_ARM64" "$DOCKER_APP_IMAGE_X64" test: - runs-on: ubuntu-24.04 + runs-on: ubuntu-latest needs: - merge env: diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index a5a9e26..b9a9c62 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -17,9 +17,6 @@ jobs: - name: Checkout code uses: actions/checkout@v4 - - name: Set up QEMU - uses: docker/setup-qemu-action@v3 - - name: Set up Docker Buildx uses: docker/setup-buildx-action@v3