Skip to content

chore(ci): tag-driven release workflow#5

Merged
faculopezscala merged 1 commit into
mainfrom
chore/tag-driven-release
Apr 6, 2026
Merged

chore(ci): tag-driven release workflow#5
faculopezscala merged 1 commit into
mainfrom
chore/tag-driven-release

Conversation

@faculopezscala
Copy link
Copy Markdown
Contributor

Summary

  • Replaces the fragile push-to-main auto-bump release with a tag-driven publish workflow plus a manual version-bump workflow.
  • release.yml now triggers only on v* tags, validates the tag matches semver, verifies all three publishable package.jsons match the tag, and publishes idempotently in dependency order (core -> cli -> mcp).
  • version-bump.yml is the new manual entrypoint: pick patch/minor/major/prerelease, it commits the bump and pushes the tag, which triggers release.yml.
  • workspace:* -> concrete-version substitution is preserved as a publish-time-only transformation (never committed).
  • Adds .github/workflows/README.md documenting how to cut a release, emergency manual path, rollback story, and what not to do.

Before / after

Before: every push to main -> auto-bump patch -> publish -> commit release: vX.Y.Z back to main -> tag. Typo fix in README cut a release. No way to do minor/major. Race conditions on commit-back.

Before: manual flow only. From the Actions tab run Version Bump, choose level. The workflow bumps all three packages, commits chore: bump version to vX.Y.Z, pushes tag vX.Y.Z. Tag push triggers release.yml which runs build/test, asserts tag matches package versions, rewrites workspace:* -> ^X.Y.Z in memory, publishes idempotently (npm view skip for already-published versions), and creates a GitHub Release with --generate-notes (which then triggers binaries.yml).

Safety properties

  • Tag format guard: rejects anything not matching v\d+\.\d+\.\d+(-.*)?.
  • Version match guard: refuses to publish if any of core/cli/mcp package.json disagrees with the tag.
  • workspace:* post-rewrite assertion: greps the three manifests for workspace:* and fails the run if any remain.
  • Idempotent publish: npm view <pkg>@<ver> per package; re-running on the same tag is safe.
  • GitHub Release creation also no-ops if release already exists.
  • version-bump.yml aborts if the computed tag already exists.

How to cut v1.0.0 (recommendation)

  1. From the Actions tab, run Version Bump with level=major. That will move 0.1.14 -> 1.0.0, commit, tag, and trigger publish.
  2. Watch release.yml finish (it will publish @sowdb/core@1.0.0, then @sowdb/cli@1.0.0, then @sowdb/mcp@1.0.0, then create the GitHub Release).
  3. binaries.yml will then build and attach the standalone CLI binaries.
  4. If you want a release candidate first, run Version Bump with level=prerelease (default tag rc) to ship 0.1.15-rc.0, smoke test from npm, then run level=major for the real 1.0.0.

Test plan

  • Merge PR.
  • Trigger Version Bump with level=prerelease to validate end-to-end on a throwaway RC.
  • Confirm the RC publishes to npm with @sowdb/core listed as ^X.Y.Z (not workspace:*) in the published cli/mcp manifests.
  • Confirm binaries.yml ran on the resulting GitHub Release.
  • Re-run release.yml on the same tag and confirm it skips everything (idempotent).

🤖 Generated with Claude Code

Replace push-to-main auto-bump release with a two-workflow setup:
version-bump.yml (manual, computes + commits + tags) and release.yml
(tag-driven publish, idempotent, validates tag matches package.json,
preserves workspace:* substitution at publish time only).

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@faculopezscala faculopezscala merged commit 2a46040 into main Apr 6, 2026
1 check passed
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.

1 participant