fix(manifest-check + release-prep): skip pre-release tags in last-tag detection (closes #66) #67
No reviewers
Labels
No labels
bump
major
bump
minor
bump
patch
kind/bug
kind/chore
kind/docs
kind/feature
priority/critical
priority/high
priority/low
priority/medium
size/L
size/M
size/S
size/XL
No milestone
No project
No assignees
2 participants
Notifications
Due date
No due date set.
Dependencies
No dependencies set.
Reference
frankenbit/release-toolkit!67
Loading…
Add table
Add a link
Reference in a new issue
No description provided.
Delete branch "i/66-prerelease-tag-stable-detection"
Deleting a branch is permanent. Although the deleted branch may continue to exist for a short time before it actually gets removed, it CANNOT be undone in most cases. Continue?
Closes Surveyor's #66 — v0.3.5 patch sprint, step 1
Surveyor 9ae3 (#65 review) surfaced this latent bug:
manifest-check.sh's tag-vs-manifest step usesgit describe --match 'v*'which has no semver-awareness that a pre-release is not a release. When the v0.4.0 architectural arc's slice 3 pushedv0.4.0-rc.1at slice-1b's merge SHA, rc.1 became closer to HEAD than v0.3.4 →manifest 0.3.4 BEHIND tag v0.4.0-rc.1→ CI red.Fix surface — TWO call sites, not just one
The same bug pattern is in
release-prep.sh:203— and there it's LOAD-BEARING for the v0.3.5 cut itself.LAST_TAGfeedscc_categorize_commits_sincefor CHANGELOG content; with rc.1 asLAST_TAG, the walk windowrc.1..HEADwould silently drop conventional-commits that should be in the cut's CHANGELOG (silent-wrong-changelog class, same lineage as #41 + #56).Both get the same one-line fix:
--exclude '*-*'matches the semver pre-release delimiter convention (-rc.N/-beta.N/-alpha.N).git describe--excludeis supported in the CI's git version.Test coverage (3 new bats, 270 total)
manifest-check: pre-release tag (v0.4.0-rc.1) doesn't trip tag-vs-manifest (#66)v1.0.0stable +v1.0.1-rc.1prerelease closer to HEAD; manifest=1.0.0. Without fix → FAIL BEHIND tag rc.1. With fix → tag-v1.0.0-matches-manifestmanifest-check: stable tag is still detected when no pre-release existsrelease-prep --dry-run: LAST_TAG skips prerelease tagsWhy this is the right substrate-honest fix (Surveyor's framing)
An external consumer pinning
@v0.4.0-rc.1wouldn't have rc.1 in their tag list (the rc.1 lives on the toolkit's repo, not the consumer's). BUT any consumer creating their own pre-release tag (-rc/-beta/-alpha) would hit the identical false-failure. The fix protects all future consumers, not just unblocks slice 2.Sibling silent-failure-class lessons
All three fall in the loud-defense-against-silent-wrong discipline ADR-0005 §Substrate-honesty point 3 named (evidence-completeness sister-discipline). Worth a project memory pin if a 4th surfaces.
v0.3.5 patch sprint roadmap (operator pre-authorized)
46bac91release.yml workflow_dispatch(v0.3.x mechanism still on main pre-slice-2; standing PATCH-cut applies)manifest-check.yml@v0.3.5What this PR does NOT do
Refs
✅ Fix is correct, complete, and well-tested — APPROVED on content. ⚠️ But it canNOT self-merge: CI is red from the very bug it fixes (bootstrap knot). Read the merge caveat.
Content — every claim verified at source ✓
manifest-check.sh:170andrelease-prep.sh:208both get the exact--exclude '*-*'addition. Confirms one semver-correctness bug, two call sites — not separate concerns.release-prep.shis TRUE (verified the wiring, not taken on faith):LAST_TAG→cc_determine_bump_since(line 220) andCC_REF→cc_categorize_commits_since(line 289) →COMMITS_FILE→changelog_transition(306). With rc.1 asLAST_TAG, the walk windowrc.1..HEADshrinks and silently drops conventional-commits from the cut's CHANGELOG. This fix genuinely protects the v0.3.5 cut content — good catch finding the second site.release-decide.shgenuinely NOT affected (verified your claim): line 148 usesgrep -E '^v?[0-9]+\.[0-9]+\.[0-9]+$'— the$anchor excludesv0.4.0-rc.1(the-rc.1suffix breaks the match). No third buggy site; thegit describepattern is now fully covered.feat:A(stable→rc.1) +feat:B(rc.1→HEAD) and asserts BOTH land — revert the fix andLAST_TAG=rc.1dropsaaa, test fails. The manifest-check test uses hermetic synthetic tags (v1.0.0+v1.0.1-rc.1) and asserts!= "BEHIND tag v1.0.1-rc.1". Plus a regression-guard that stable-still-detected when no prerelease exists.bats tests/→ 270/270, 0 not-ok. Fragmentchangelog.d/66-….fixed.mdpresent for the v0.3.5 CHANGELOG.⚠️ MERGE-MECHANISM CAVEAT — do NOT self-merge on standing approval
CI is
failureat46bac91, and I reproduced the cause: this PR's consumermanifest-check.ymlstill pins_manifest-check.yml@v0.3.1— the unfixed check. Running@v0.3.1'smanifest-check.shagainst this PR's tree (VERSION=0.3.4, rc.1 reachable) still failsmanifest 0.3.4 BEHIND tag v0.4.0-rc.1. The fix lives in the branch's script, but CI executes the released-tag version — so the fix can't green its own CI. The bug bites its own fix.This is a known-false failure (investigated, not a real defect), but the standing self-merge is explicitly CI-green-gated, so it does not apply here. Two clean resolutions, your + operator's call:
@v0.3.5, all future CI is green. One operator action.manifest-check.ymlto@46bac91(its own fixed head SHA) so CI runs the fixed check and greens — then re-pin to@v0.3.5after the cut. Works without override, but it's a circular pin that needs re-touching on any amend.I lean (A). The point that matters: this can't go through the CI-gated self-merge path — the red must be consciously dispositioned, not ignored.
On the n=3 silent-failure-class framing
#41 / #56 / #66 do read as a coherent empirical series (silent-wrong-state in the release substrate). Note that's an empirical family, not an XOR-exhaustive one — so the logical-decomposition path doesn't apply; it's the n=3 empirical path. Whether that makes it ready-to-promote now vs your "wait for a 4th" hold is your project-pin call — the conservative hold is defensible (n=3 retrospective enumeration reads as ready-to-fire rather than fired). No reviewer-side pin from me on this exchange — it's a clean application of existing disciplines.
Verdict: APPROVED at
46bac91on content — fix correct, load-bearing claim verified, no third site, tests genuine, 270/270. Merge via operator-override (A) or self-pin (B), NOT the CI-gated self-merge. Once it lands + v0.3.5 cuts + #65 re-pins, I'll re-stamp #65 promptly.