From 5b364b8669c555c23f2f71d712ea550b6dda8011 Mon Sep 17 00:00:00 2001 From: Alexey Karimov Date: Mon, 24 Aug 2026 18:40:36 +0500 Subject: [PATCH] fix(release): set dist allow-dirty = ["ci"] to stop dependabot breaking releases MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit Second occurrence of the same failure. PR #11 bumped `actions/checkout` 6 -> 7 across every workflow, which again rewrote the six pins inside `.github/workflows/release.yml` — a cargo-dist GENERATED file that the `plan` job verifies byte-for-byte. `dist plan` has been failing on main since it merged, and because `plan` is the first job of the real release workflow, the next `vX.Y.Z` tag push would have failed before building an artefact. PR #10 fixed the first occurrence by regenerating the file, and left a comment asking reviewers not to merge such PRs. That did not hold, and it cannot: the PR is generated weekly, dependabot cannot be told to skip a single file, and no published cargo-dist emits a newer checkout pin (0.32.0 is the latest on both crates.io and upstream GitHub), so there is no version to upgrade into. The mismatch is structural, so the guard has to go rather than the pin. With `allow-dirty = ["ci"]`, dist stops verifying release.yml and the file keeps dependabot's `@v7`. That ends the recurrence outright rather than deferring it: every workflow now agrees on v7, so no bump is proposed, and the next action major won't fail `plan` either. The tradeoff is real and is documented next to the key and in CLAUDE.md: dist config changes (targets, installers, publish-jobs, cargo-dist-version) no longer propagate to the workflow on their own, and nothing warns. Editing any of them now requires re-running `dist generate` in the same change. Verified: `dist plan` exits 0 and still emits the full artefact set for all five target triples, with release.yml left on `checkout@v7`. 🤖 Generated with [Claude Code](https://claude.com/claude-code) --- .github/dependabot.yml | 15 +++++++-------- CLAUDE.md | 9 +++++++++ Cargo.toml | 15 +++++++++++++++ 3 files changed, 31 insertions(+), 8 deletions(-) diff --git a/.github/dependabot.yml b/.github/dependabot.yml index 6680c60..a3cb180 100644 --- a/.github/dependabot.yml +++ b/.github/dependabot.yml @@ -33,14 +33,13 @@ updates: # GitHub Actions pinned in the CI / release / npm-publish / mirror workflows. # - # REVIEWER TRAP: `.github/workflows/release.yml` is GENERATED by cargo-dist and - # is verified against the generator by the `plan` job. Dependabot cannot be - # told to skip a single file, so it will keep proposing action bumps inside - # that file — and `plan` will keep failing them. Do NOT merge such a PR: `plan` - # is also the FIRST job of the real release workflow, so a mismatched - # release.yml breaks the next `vX.Y.Z` tag push, not just the PR. Drop the - # release.yml hunks and keep the rest; the file only changes when - # `cargo-dist-version` is bumped and `dist generate` is re-run. + # NOTE: bumps here also rewrite action pins inside + # `.github/workflows/release.yml`, which is GENERATED by cargo-dist. That used + # to fail the `plan` job (and, because `plan` is the first job of the real + # release workflow, broke tag releases — twice: PR #1, then PR #11). Cargo.toml + # now sets `allow-dirty = ["ci"]`, so dist no longer verifies that file and + # these PRs are safe to merge. The tradeoff is written up next to that key: if + # you change the dist config, re-run `dist generate` yourself. - package-ecosystem: "github-actions" directory: "/" schedule: diff --git a/CLAUDE.md b/CLAUDE.md index 4a3dcfb..6e8f25c 100644 --- a/CLAUDE.md +++ b/CLAUDE.md @@ -155,6 +155,15 @@ Releases are tag-driven: pushing a `vX.Y.Z` tag runs `release.yml` (cargo-dist builds the target triples + a GitHub Release with shell/powershell/npm/homebrew installers), then `mirror-to-s3.yml` mirrors to `download.bugsee.com/cli//`. +`release.yml` is GENERATED by cargo-dist from `[workspace.metadata.dist]` — do +not hand-edit it for anything except the action pins dependabot manages. That +config sets `allow-dirty = ["ci"]`, so `dist plan` no longer verifies the file +against the generator (dependabot's action bumps kept breaking that check, and +with it tag releases). The cost is that dist-config changes no longer propagate +on their own: after editing `targets`, `installers`, `publish-jobs`, or +`cargo-dist-version`, run `dist generate` and commit the regenerated workflow in +the SAME change, or the release will still run the old plan. + New capabilities are activated by integrators via a version FLOOR: each integrator pins a minimum CLI version and only uses a new command/flag when the resolved binary meets it. So shipping a feature is a two-step rollout — publish the CLI at diff --git a/Cargo.toml b/Cargo.toml index d59ab28..9bb2900 100644 --- a/Cargo.toml +++ b/Cargo.toml @@ -36,6 +36,21 @@ lto = "thin" [workspace.metadata.dist] # The preferred dist version to use in CI (Cargo.toml SemVer syntax) cargo-dist-version = "0.32.0" +# Stop `dist plan` from verifying `.github/workflows/release.yml` byte-for-byte +# against the generator. +# +# WHY: dependabot bumps action pins across ALL workflows and cannot be told to +# skip one file, so it keeps rewriting `actions/checkout@vN` inside the +# dist-GENERATED release.yml. `plan` is the first job of the release workflow, +# so merging such a PR breaks the next `vX.Y.Z` tag push — that happened twice +# (PR #1, then PR #11). No published cargo-dist emits a newer checkout pin, so +# there is no version to upgrade into; the mismatch is unavoidable. +# +# COST: release.yml is no longer auto-verified, so a change to the dist config +# BELOW (targets, installers, publish-jobs, ...) will NOT be reflected in the +# workflow and nothing will warn you. After editing any of it, re-run +# `dist generate` and commit the result in the same change. +allow-dirty = ["ci"] # CI backends to support ci = "github" # The installers to generate for each app