From 20ee5a7b5971bf2a146e08eb188b03d9748a3e61 Mon Sep 17 00:00:00 2001 From: Alex Luong Date: Fri, 14 Aug 2026 23:41:48 +0700 Subject: [PATCH 1/3] chore(release): pin GoReleaser and migrate off deprecated config MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The release workflow ran `goreleaser-action@v4` with `version: latest`, so every tag push built with whatever GoReleaser shipped that morning — v1.2.0 happened to use 2.17.1, unchosen. `goreleaser check` also failed on three deprecations, meaning a future release could break with no warning and nowhere to catch it but a tag push. - Pin to v2.17.1 (the version v1.2.0 actually released with) and bump the action to v6. - archives: `format` -> `formats`. Drops the windows->zip `format_overrides`, which was dead — builds are `goos: [linux]` only, so it could never fire. - dockers + docker_manifests -> dockers_v2. One buildx build now covers both platforms and pushes the manifest in a single step, so the Dockerfile copies binaries from `$TARGETPLATFORM/`. `sbom: false` keeps the published manifest to the same two platform entries as today; SBOM attestations would show up as extra "unknown/unknown" platforms on Docker Hub. - Drop DOCKER_CLI_EXPERIMENTAL, only needed by the old docker_manifests path. `goreleaser check` is clean and `goreleaser release --snapshot` builds both images: correct architectures, version ldflags stamped, all binaries and the entrypoint present. Co-Authored-By: Claude Opus 5 (1M context) --- .github/workflows/release.yml | 10 ++--- build/.goreleaser.yaml | 69 +++++++++++------------------------ build/Dockerfile.goreleaser | 8 ++-- 3 files changed, 32 insertions(+), 55 deletions(-) diff --git a/.github/workflows/release.yml b/.github/workflows/release.yml index e5404d9b7..674a4f7b4 100644 --- a/.github/workflows/release.yml +++ b/.github/workflows/release.yml @@ -8,9 +8,6 @@ on: jobs: release: runs-on: ubuntu-latest - env: - # https://goreleaser.com/customization/docker_manifest/ - DOCKER_CLI_EXPERIMENTAL: "enabled" steps: - name: Code checkout uses: actions/checkout@v5 @@ -40,9 +37,12 @@ jobs: with: go-version: 1.26.5 - name: Run GoReleaser - uses: goreleaser/goreleaser-action@v4 + uses: goreleaser/goreleaser-action@v6 with: - version: latest + # Pinned deliberately: an unpinned "latest" means every tag push builds + # with whatever GoReleaser shipped that morning, and a breaking change + # surfaces mid-release, after the tag exists. + version: "v2.17.1" args: release -f build/.goreleaser.yaml --clean env: GITHUB_TOKEN: ${{ secrets.GITHUB_TOKEN }} diff --git a/build/.goreleaser.yaml b/build/.goreleaser.yaml index 82ac9cdcf..c6c7f2d29 100644 --- a/build/.goreleaser.yaml +++ b/build/.goreleaser.yaml @@ -70,7 +70,7 @@ builds: - arm64 archives: - - format: tar.gz + - formats: [tar.gz] # this name template makes the OS and Arch compatible with the results of `uname`. name_template: >- {{ .ProjectName }}_ @@ -79,10 +79,6 @@ archives: {{- else if eq .Arch "386" }}i386 {{- else }}{{ .Arch }}{{ end }} {{- if .Arm }}v{{ .Arm }}{{ end }} - # use zip for windows archives - format_overrides: - - goos: windows - format: zip changelog: sort: asc @@ -91,53 +87,32 @@ changelog: - "^docs:" - "^test:" -dockers: - - goos: linux - goarch: amd64 +dockers_v2: + - images: + - "hookdeck/outpost" + tags: + - "{{ .Tag }}" + - "latest" dockerfile: ./build/Dockerfile.goreleaser ids: - outpost - - outpost-server - extra_files: - - build/entrypoint.sh - image_templates: - - "hookdeck/outpost:latest-amd64" - - "hookdeck/outpost:{{ .Tag }}-amd64" - build_flag_templates: - - "--pull" - - "--label=org.opencontainers.image.created={{.Date}}" - - "--label=org.opencontainers.image.name={{.ProjectName}}" - - "--label=org.opencontainers.image.revision={{.FullCommit}}" - - "--label=org.opencontainers.image.version={{.Version}}" - - "--label=repository=https://github.com/hookdeck/outpost" - - "--label=homepage=https://hookdeck.com" - - "--platform=linux/amd64" - - goos: linux - goarch: arm64 - dockerfile: ./build/Dockerfile.goreleaser - ids: - outpost-arm64 + - outpost-server - outpost-server-arm64 extra_files: - build/entrypoint.sh - image_templates: - - "hookdeck/outpost:latest-arm64" - - "hookdeck/outpost:{{ .Tag }}-arm64" - build_flag_templates: + platforms: + - linux/amd64 + - linux/arm64 + # Keep the published manifest to just the two platforms. Enabling SBOM adds + # attestation entries that surface as "unknown/unknown" platforms on Docker Hub. + sbom: false + flags: - "--pull" - - "--label=org.opencontainers.image.created={{.Date}}" - - "--label=org.opencontainers.image.name={{.ProjectName}}" - - "--label=org.opencontainers.image.revision={{.FullCommit}}" - - "--label=org.opencontainers.image.version={{.Version}}" - - "--label=repository=https://github.com/hookdeck/outpost" - - "--label=homepage=https://hookdeck.com" - - "--platform=linux/arm64/v8" -docker_manifests: - - name_template: "hookdeck/outpost:latest" - image_templates: - - "hookdeck/outpost:latest-amd64" - - "hookdeck/outpost:latest-arm64" - - name_template: "hookdeck/outpost:{{ .Tag }}" - image_templates: - - "hookdeck/outpost:{{ .Tag }}-amd64" - - "hookdeck/outpost:{{ .Tag }}-arm64" + labels: + org.opencontainers.image.created: "{{ .Date }}" + org.opencontainers.image.name: "{{ .ProjectName }}" + org.opencontainers.image.revision: "{{ .FullCommit }}" + org.opencontainers.image.version: "{{ .Version }}" + repository: "https://github.com/hookdeck/outpost" + homepage: "https://hookdeck.com" diff --git a/build/Dockerfile.goreleaser b/build/Dockerfile.goreleaser index a02a38b91..3c782cc6c 100644 --- a/build/Dockerfile.goreleaser +++ b/build/Dockerfile.goreleaser @@ -5,9 +5,11 @@ FROM gcr.io/distroless/base-debian13:nonroot # Copy statically linked shell from busybox for entrypoint script COPY --from=busybox /bin/sh /bin/sh -# Copy all binaries -COPY outpost /usr/local/bin/outpost -COPY outpost-server /usr/local/bin/outpost-server +# Copy all binaries. GoReleaser stages each platform's artifacts under +# $TARGETPLATFORM/ in the build context, since one buildx build covers both arches. +ARG TARGETPLATFORM +COPY $TARGETPLATFORM/outpost /usr/local/bin/outpost +COPY $TARGETPLATFORM/outpost-server /usr/local/bin/outpost-server # Copy entrypoint script COPY build/entrypoint.sh /usr/local/bin/entrypoint.sh From a039cbd9092c9473f7d39c5df0af6ebf70b82d78 Mon Sep 17 00:00:00 2001 From: Alex Luong Date: Fri, 14 Aug 2026 23:48:53 +0700 Subject: [PATCH 2/3] chore(release): disable buildx provenance attestations `sbom: false` alone was not enough. Verified by pushing the same context to a scratch repo: the manifest came back with linux/amd64, linux/arm64, and two `unknown/unknown` entries. GoReleaser never passes `--provenance`, so buildx applies its default of attaching provenance whenever it pushes, independent of the `sbom` setting. With `--provenance=false` the pushed manifest is exactly the two platform entries, matching what dockers/docker_manifests publishes today. Co-Authored-By: Claude Opus 5 (1M context) --- build/.goreleaser.yaml | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-) diff --git a/build/.goreleaser.yaml b/build/.goreleaser.yaml index c6c7f2d29..32edd7fef 100644 --- a/build/.goreleaser.yaml +++ b/build/.goreleaser.yaml @@ -104,11 +104,16 @@ dockers_v2: platforms: - linux/amd64 - linux/arm64 - # Keep the published manifest to just the two platforms. Enabling SBOM adds - # attestation entries that surface as "unknown/unknown" platforms on Docker Hub. + # Keep the published manifest to just the two platform entries, matching what + # the dockers/docker_manifests setup produced. Attestations are published as + # extra manifest entries that show up as "unknown/unknown" platforms on Docker + # Hub, and both sources have to be turned off: sbom drops --attest=type=sbom, + # and --provenance=false overrides buildx's default of attaching provenance + # whenever it pushes. GoReleaser never passes --provenance itself. sbom: false flags: - "--pull" + - "--provenance=false" labels: org.opencontainers.image.created: "{{ .Date }}" org.opencontainers.image.name: "{{ .ProjectName }}" From eadc12c460f09dcd7e5b7a2baa1136de145cbb32 Mon Sep 17 00:00:00 2001 From: Alex Luong Date: Sat, 15 Aug 2026 00:17:13 +0700 Subject: [PATCH 3/3] chore(release): trim the attestation comment Co-Authored-By: Claude Opus 5 (1M context) --- build/.goreleaser.yaml | 8 ++------ 1 file changed, 2 insertions(+), 6 deletions(-) diff --git a/build/.goreleaser.yaml b/build/.goreleaser.yaml index 32edd7fef..ff4ecc9ed 100644 --- a/build/.goreleaser.yaml +++ b/build/.goreleaser.yaml @@ -104,12 +104,8 @@ dockers_v2: platforms: - linux/amd64 - linux/arm64 - # Keep the published manifest to just the two platform entries, matching what - # the dockers/docker_manifests setup produced. Attestations are published as - # extra manifest entries that show up as "unknown/unknown" platforms on Docker - # Hub, and both sources have to be turned off: sbom drops --attest=type=sbom, - # and --provenance=false overrides buildx's default of attaching provenance - # whenever it pushes. GoReleaser never passes --provenance itself. + # No attestations, so the manifest keeps the same two platform entries as + # today. Takes both switches — buildx adds provenance on its own. sbom: false flags: - "--pull"