Skip to content

AX-1734: Add tag/release mechanism - #22

Merged
YoniMelki merged 8 commits into
mainfrom
ax-1734-release-mechanism
Aug 4, 2026
Merged

AX-1734: Add tag/release mechanism#22
YoniMelki merged 8 commits into
mainfrom
ax-1734-release-mechanism

Conversation

@YoniMelki

@YoniMelki YoniMelki commented Jun 23, 2026

Copy link
Copy Markdown
Collaborator

Summary

Adds a tag/release mechanism. The version lives in exactly one place: .version in .claude-plugin/plugin.json — the manifest Claude Code already reads, and the file CONTRIBUTING.md already told contributors to bump.

  • release.yml — on push to main, if the commit subject carries [major], [minor] or [patch], reads the version from the manifest, tags vX.Y.Z, and publishes a GitHub Release with a repo zip attached.
  • No VERSION file, and so no validate-version check either. A duplicate copy of the version is the only thing such a check would have policed.
  • CONTRIBUTING.md gains a Releasing section.

Notes for reviewers

The version comes from the manifest, not from the marker. The marker only decides whether to release; it does not compute a bump. The version change stays reviewable in the PR that makes it, and no bot ever pushes to main.

The marker is matched on the subject line only. This repo squash-merges, and GitHub pre-fills the squash body from the branch's commit messages — which quote [minor] while merely documenting the flow. Matching the whole message would have meant merging this very PR cut a release nobody asked for.

Merging a marker without bumping the manifest fails the release rather than re-tagging a version that already shipped.

The commit message is read through env, not interpolated into the script, so a crafted commit subject cannot inject shell.

History worth knowing

An earlier revision of this branch added a VERSION file pinned at 0.2.12 and a drift check comparing it to the manifest. Main has since moved to 0.2.17, so that check would have failed on the first PR after merge. Dropping the duplicate removes the failure mode instead of resyncing it.

The first revision also auto-bumped the version and pushed the result to main. That was dropped in favour of the developer-driven bump the other plugin repos settled on.

Test plan

  • validate passes on this PR
  • After merge, release.yml shows up in Actions and no release fires — the squash subject defaults to this PR's title, which carries no marker
  • A follow-up PR bumping the manifest, merged with [patch] in the subject, produces the matching tag and GitHub Release

Closes AX-1734 / part of AX-1733

YoniMelki and others added 2 commits July 15, 2026 13:38
@YoniMelki
YoniMelki force-pushed the ax-1734-release-mechanism branch from 20d6376 to 3eda24c Compare July 15, 2026 10:40
Comment thread .github/workflows/release.yml Outdated
Comment thread .github/workflows/release.yml
Comment thread .github/workflows/release.yml Outdated
Comment thread .github/workflows/validate-version.yml Outdated
Comment thread .github/workflows/validate-version.yml Outdated
Comment thread .github/workflows/validate-version.yml Outdated
Comment thread .github/workflows/release.yml
…tep comments

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
yanivt-jfrog
yanivt-jfrog previously approved these changes Jul 16, 2026
…ION file

.claude-plugin/plugin.json already carries the version Claude Code reads, and
CONTRIBUTING already told contributors to bump it. Adding a VERSION file made a
second copy and then needed validate-version.yml to police the two against each
other, so both are gone.

The merge with main also exposed why that mattered: VERSION was pinned at 0.2.12
while the manifest had moved to 0.2.17, so the drift check this branch added
would have failed on the first PR after merge.

release.yml now reads the version from the manifest instead of bumping and
pushing to main, matching the flow the other plugin repos settled on. It also
refuses to re-tag a version that already shipped (the one mistake a
marker-triggered release allows) and reads the commit message from env rather
than interpolating it into the script.
These repos squash-merge, and GitHub pre-fills the squash message body from the
branch's commit messages (or the PR description). Both of those quote
[major]/[minor]/[patch] while only documenting the flow, so matching the whole
message meant merging this very PR would have cut a release nobody asked for.

Matching the subject line alone keeps the trigger deliberate: a release happens
when someone writes the marker in the subject they are merging, not when a marker
happens to appear in generated body text.
Comment thread .github/workflows/release.yml Outdated
Comment thread .github/workflows/release.yml
Comment thread .github/workflows/release.yml Outdated
… release

Three fixes from review, all in release.yml.

An orphan tag was possible: the tag was pushed in its own step before
`gh release create`, so a failure in between left a tag with no release behind
it. The re-run then hit the "already exists" check with nothing actually wrong
but the tag, and it needed deleting by hand. The tag is now created by
`gh release create --target "$GITHUB_SHA"` in the same API call as the release,
so there is no window between the two. Nothing pushes over git anymore, so the
write token is gone from the checkout step.

Releases were not gated on validation. The validate workflow triggers on the same
push, but as a separate workflow with no relationship to this one, so it could
still be red while a release went out. The same check now runs here, before the
release is created.

`zip -r release.zip .` packed the working tree, so anything an earlier step left
on the runner would ship inside the artifact. Replaced with `git archive`, which
exports tracked files at HEAD, still excluding .github.
Comment thread .github/workflows/release.yml Outdated
…TRIBUTING

Review feedback: the per-step comments in release.yml had grown into several
paragraphs of rationale, which is documentation rather than a code comment.

Each step now carries at most two lines - what it does, or the one constraint a
reader could otherwise undo by "simplifying" it: subject-line matching, env
rather than interpolation, git archive rather than the working tree, --target
creating the tag. A pointer at the top of the file sends readers to
CONTRIBUTING.md for the full flow.

CONTRIBUTING.md gains the parts the comments had that it did not already say:
what the workflow does in order, what ends up in the release zip, why validation
runs inside the release job instead of relying on the separate validate
workflow, and why the tag is created by the release rather than pushed before it.

No behaviour change - the release.yml diff is comments only.
@YoniMelki
YoniMelki merged commit 5525279 into main Aug 4, 2026
2 checks passed
@YoniMelki
YoniMelki deleted the ax-1734-release-mechanism branch August 4, 2026 14:50
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