Skip to content

ci: only build a release candidate when a release will actually happen - #6

Merged
StoneyJackson merged 1 commit into
mainfrom
ci/skip-release-build-when-no-release
Jul 27, 2026
Merged

ci: only build a release candidate when a release will actually happen#6
StoneyJackson merged 1 commit into
mainfrom
ci/skip-release-build-when-no-release

Conversation

@StoneyJackson

Copy link
Copy Markdown
Member

Every push to main built and tested the image, including infra-only merges that release nothing — the App-token merge earlier today spent a full build to publish nothing at all.

Path filtering cannot decide this: a releasing commit touching only docs would skip the build and leave the publish step with no image. The release decision is what matters, so semantic-release is asked in dry-run first and the build is guarded on its answer. The build still precedes the real release, so a broken image can never be published.

Unlike plcc-ng-devcontainer this workflow is a single job, so the guard is on steps rather than a separate build job.

Guarded with != 'false' so an unexpected or empty output still builds: skipping a needed build breaks publishing, an extra build only costs time.

Also fails loudly if the dry run and the real release ever disagree. Without that the failure would be silent and wrong: with no image built, the publish step's FROM ...:latest would pull the previous release's image and push it under the new version tags.

Every push to main built and tested the image, including infra-only
merges that release nothing — the App-token merge earlier today spent a
full build to publish nothing at all.

Path filtering cannot decide this: a releasing commit touching only docs
would skip the build and leave the publish step with no image. The
release decision is what matters, so semantic-release is asked in dry-run
first and the build is guarded on its answer. The build still precedes
the real release, so a broken image can never be published.

Unlike plcc-ng-devcontainer this workflow is a single job, so the guard
is on steps rather than a separate build job.

Guarded with != 'false' so an unexpected or empty output still builds:
skipping a needed build breaks publishing, an extra build only costs time.

Also fails loudly if the dry run and the real release ever disagree.
Without that the failure would be silent and wrong: with no image built,
the publish step's `FROM ...:latest` would pull the previous release's
image and push it under the new version tags.

Co-Authored-By: Claude Opus 5 <noreply@anthropic.com>
Copilot AI review requested due to automatic review settings July 27, 2026 19:09
@StoneyJackson
StoneyJackson merged commit ab0b15f into main Jul 27, 2026
4 checks passed
@StoneyJackson
StoneyJackson deleted the ci/skip-release-build-when-no-release branch July 27, 2026 19:10

Copilot AI left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Pull request overview

This PR updates the main-branch release workflow to avoid building the devcontainer image unless semantic-release indicates that the current commit will produce a release, reducing wasted build time on non-releasing merges.

Changes:

  • Adds a semantic-release dry run step to determine whether a release is planned.
  • Guards GHCR login and the devcontainer build/test step based on the dry-run result.
  • Adds a safety check intended to fail if the dry run and the real release disagree.
Comments suppressed due to low confidence (2)

.github/workflows/release.yml:74

  • Same guard issue as the GHCR login step: with != 'false', an unset/empty new_release_published output will cause the image build to run even when semantic-release indicates there is no release. Using an explicit == 'true' check (with a failure fallback) should allow infra-only/no-release merges to skip the expensive build.
      - name: Build and test devcontainer image
        if: steps.plan.outputs.new_release_published != 'false'
        uses: devcontainers/ci@v0.3

.github/workflows/release.yml:93

  • This mismatch check is currently looking for steps.plan.outputs.new_release_published == 'false', but the dry-run action commonly leaves the output unset when no release happens (instead of emitting 'false'). That means this safeguard may never trigger in the mismatch scenario it is meant to catch.

Consider treating anything other than an explicit 'true' (with a successful dry-run outcome) as “predicted no release”.

      - name: Fail if the dry run and the real release disagreed
        if: steps.semantic.outputs.new_release_published == 'true' && steps.plan.outputs.new_release_published == 'false'
        run: |

💡 Add Copilot custom instructions for smarter, more guided reviews. Learn how to get started.

Comment on lines 64 to 66
- name: Log in to GHCR
if: steps.plan.outputs.new_release_published != 'false'
uses: docker/login-action@v3
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants