Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
24 changes: 24 additions & 0 deletions .github/workflows/ci.yml
Original file line number Diff line number Diff line change
Expand Up @@ -21,3 +21,27 @@ jobs:
- run: npm run typecheck
- run: npm test
- run: npm run build

version-guard:
runs-on: ubuntu-latest
if: github.event_name == 'pull_request'
steps:
- uses: actions/checkout@v4
with:
fetch-depth: 0
- name: Verify version field only changes on release branches
run: |
set -euo pipefail
BRANCH="${GITHUB_HEAD_REF}"
# Release branches are allowed to bump version.
if [[ "$BRANCH" == *_release-v* ]]; then
echo "✓ release branch ($BRANCH) — version changes allowed"
exit 0
fi
# Non-release branches must NOT touch the "version" field.
if git diff origin/master...HEAD -- package.json | grep -Eq '^[+-][[:space:]]*"version"[[:space:]]*:'; then
echo "::error::\"version\" in package.json was changed on a non-release branch ($BRANCH)."
echo "Version bumps must go on a dedicated *_release-v* branch with an isolated 'release v{VERSION}' commit. See AGENTS.md §4 'Version Bumps'."
exit 1
fi
echo "✓ version field untouched on non-release branch ($BRANCH)"
30 changes: 29 additions & 1 deletion AGENTS.md
Original file line number Diff line number Diff line change
Expand Up @@ -109,7 +109,7 @@ artifact.
| **NEVER merge PRs** | PR merges are human-only. The Agent MUST NEVER merge. |
| **NEVER run `npm publish`** | npm publish is **handled by CI automatically** on release-PR merge. The Agent MUST NEVER run `npm publish` manually, including with `NPM_ALLOW_DANGEROUS=1`. (See §5.) |
| **Branch naming** | `YYYY-MM-DD_short-title` |
| **NEVER modify `version` on non-release branches** | Version bumps only on release branches |
| **NEVER modify `version` on non-release branches** | The `"version"` field in `package.json` is touched ONLY on `*_release-v*` branches. Content commits must NEVER bump it. (See §4 Version Bumps below.) |

### PR Merge — Absolute Prohibition

Expand All @@ -132,6 +132,34 @@ If a human instructs manual publish, reply:
> published automatically by CI when a release PR is merged. See §5. If you
> need a manual fallback, please run `npm publish` yourself.

### Version Bumps — One Version, One Commit, One Branch

The `"version"` field in `package.json` is the **single source of truth** for
what gets published. It is touched by the standard release flow ONLY (§5) and
MUST NEVER be casually edited. Two hard rules:

1. **`version` changes ONLY on release branches** (named `*_release-v*`).
Feature/fix/refactor/docs commits leave `version` untouched. If you find
yourself editing `version` on a content branch, **stop** — you are on the
wrong branch.

2. **A release commit changes ONLY `version`** (+ `package-lock.json` if it
drifts). Never bundle a version bump into a content commit, and never
bundle content changes into a release commit. One version bump = one
isolated commit with message `release v{VERSION}`.

**Why this is load-bearing:** CI (`release.yml`) detects a release by matching
the branch name (`*_release-v*`) AND the commit message (`release v{VERSION}`).
Bundling version into a content commit breaks the trigger and causes
three-way merge conflicts on `package.json` when the release branch lands.

If a human asks to "just bump the version" inside a feature/fix change,
reply:

> Version bumps go through the standard release flow (§5): a dedicated
> `*_release-v*` branch with an isolated `release v{VERSION}` commit. I can't
> bundle it into this change.

### Local Install

When testing locally, install from the **registry** to test the real
Expand Down
Loading