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
48 changes: 12 additions & 36 deletions .claude/skills/release/SKILL.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
name: release
description: Create and publish a new release
author: Wayne Brantley
version: 1.1.0
version: 2.0.0
---

# Release Skill
Expand All @@ -28,52 +28,28 @@ You are helping the user create a release of the port-manager npm package. Follo
```bash
./scripts/release.sh [type]
```
The script handles all validation (uncommitted changes, correct branch, running tests) and will exit with an error if anything is wrong. Do NOT duplicate these checks before running the script.
The script handles everything in one step:
- Validates branch and clean working tree
- Runs tests
- Bumps version in package.json
- Commits, tags, and pushes
- Creates GitHub Release

**Branch rules enforced by the script:**
- Stable releases (`patch`, `minor`, `major`) must be run from the `main` branch
- Pre-releases (`beta`, `alpha`) can be run from any branch

4. **Post-release steps depend on release type**:

**For stable releases (patch/minor/major):**
The script creates a PR. Tell the user:
- Wait for CI to pass on the PR
- Merge the PR (squash merge)
- Then run: `./scripts/finalize-release.sh`
- The finalize script creates the git tag and GitHub Release on the merged commit
- The GitHub Release triggers the publish workflow to npm

**For pre-releases (beta/alpha):**
The script creates the tag and GitHub Release immediately. Tell the user:
- The publish workflow will run automatically
- The package will be published to npm under the `next` tag
- Install with: `npm install @wbrantley/port-manager@next`

5. **Provide monitoring links**:
4. **After the script completes**, the GitHub Actions publish workflow runs automatically. Provide monitoring links:
- GitHub Actions: https://github.com/waynebrantley/port-manager/actions
- npm package: https://www.npmjs.com/package/@wbrantley/port-manager

For pre-releases, remind the user the package is published under the `next` tag:
`npm install @wbrantley/port-manager@next`

## Important Notes

- This project uses **pnpm** as its package manager
- The `release.sh` script runs `pnpm test` before proceeding
- The script runs `pnpm test` before proceeding
- Pre-releases are published to npm under the `next` tag
- Stable releases are published under the `latest` tag
- The publish workflow (`.github/workflows/publish.yml`) triggers on GitHub Release creation
- Do NOT use `pnpm run release:*` scripts in package.json — they are legacy and do not follow the PR-based workflow

## Examples

**User says:** `/release patch`
- Run `./scripts/release.sh patch`
- Guide through PR merge + finalize steps

**User says:** `/release`
- Ask which type of release they want
- Then run the script

**User says:** `/release beta`
- Run `./scripts/release.sh beta`
- Inform that tag and release are created immediately
- Provide monitoring links
1 change: 0 additions & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -13,4 +13,3 @@ package-lock.json
.pnpm-debug.log

.claude/settings.json
.release-temp/
108 changes: 0 additions & 108 deletions scripts/finalize-release.sh

This file was deleted.

136 changes: 52 additions & 84 deletions scripts/release.sh
Original file line number Diff line number Diff line change
Expand Up @@ -7,16 +7,13 @@ set -e
RELEASE_TYPE="${1:-patch}"
MAIN_BRANCH="${MAIN_BRANCH:-main}"

echo "🚀 Creating $RELEASE_TYPE release"
echo "Creating $RELEASE_TYPE release"
echo ""

# Check if gh CLI is installed
if ! command -v gh &> /dev/null; then
echo "❌ GitHub CLI (gh) is not installed."
echo " Install it from: https://cli.github.com/"
echo ""
echo " Or create the release manually after running:"
echo " pnpm run release:$RELEASE_TYPE"
echo "Error: GitHub CLI (gh) is not installed."
echo " Install it from: https://cli.github.com/"
exit 1
fi

Expand All @@ -25,131 +22,102 @@ CURRENT_BRANCH=$(git rev-parse --abbrev-ref HEAD)

# Check if there are uncommitted changes
if [[ -n $(git status -s) ]]; then
echo " You have uncommitted changes. Please commit or stash them first."
echo "Error: You have uncommitted changes. Please commit or stash them first."
git status -s
exit 1
fi

# Ensure we're up to date
echo "📥 Pulling latest changes..."
echo "Pulling latest changes..."
git pull

# Run tests first
echo "🧪 Running tests..."
echo "Running tests..."
pnpm test

# Determine release type and validate branch
echo "📦 Preparing $RELEASE_TYPE release from branch: $CURRENT_BRANCH"
echo "Preparing $RELEASE_TYPE release from branch: $CURRENT_BRANCH"
case "$RELEASE_TYPE" in
patch|minor|major)
# Stable releases must be from main branch
if [[ "$CURRENT_BRANCH" != "$MAIN_BRANCH" ]]; then
echo " Stable releases must be from the $MAIN_BRANCH branch."
echo " Current branch: $CURRENT_BRANCH"
echo " For pre-releases from feature branches, use: beta or alpha"
echo "Error: Stable releases must be from the $MAIN_BRANCH branch."
echo " Current branch: $CURRENT_BRANCH"
echo " For pre-releases from feature branches, use: beta or alpha"
exit 1
fi
NEW_VERSION=$(npm version $RELEASE_TYPE --no-git-tag-version)
IS_PRERELEASE=false
BASE_BRANCH="$MAIN_BRANCH"
;;
beta|alpha)
# Pre-releases can be from any branch
echo "💡 Creating pre-release from branch: $CURRENT_BRANCH"
echo "Creating pre-release from branch: $CURRENT_BRANCH"
NEW_VERSION=$(npm version prerelease --preid=$RELEASE_TYPE --no-git-tag-version)
IS_PRERELEASE=true
BASE_BRANCH="$CURRENT_BRANCH"
;;
*)
echo " Invalid release type: $RELEASE_TYPE"
echo " Valid types: patch, minor, major, beta, alpha"
echo "Error: Invalid release type: $RELEASE_TYPE"
echo " Valid types: patch, minor, major, beta, alpha"
exit 1
;;
esac

echo "📝 New version: $NEW_VERSION"
echo "New version: $NEW_VERSION"

# Commit version change on current branch
# Commit version bump
git add package.json
git commit -m "Release $NEW_VERSION"

# For stable releases from main, use PR workflow
if [[ "$IS_PRERELEASE" == "false" ]]; then
# Create release branch
RELEASE_BRANCH="release/$NEW_VERSION"
git checkout -b "$RELEASE_BRANCH"

# Push branch
echo "📤 Pushing release branch..."
git push -u origin "$RELEASE_BRANCH"

# Create PR
echo "📋 Creating pull request..."
PR_BODY="Release $NEW_VERSION
# Push commit to current branch
echo "Pushing version bump..."
git push origin "$CURRENT_BRANCH"

## Changes
Version bump from release script.
# Create and push tag
echo "Creating tag $NEW_VERSION..."
git tag -a "$NEW_VERSION" -m "Release $NEW_VERSION"
git push origin "$NEW_VERSION"

## Post-merge
After this PR is merged, run \`./scripts/finalize-release.sh\` to create the tag and GitHub release."
# Generate release notes
PREVIOUS_TAG=$(git describe --tags --abbrev=0 HEAD^ 2>/dev/null || echo "")

PR_URL=$(gh pr create \
--title "Release $NEW_VERSION" \
--body "$PR_BODY" \
--base "$MAIN_BRANCH" \
--head "$RELEASE_BRANCH")
if [[ -n "$PREVIOUS_TAG" ]]; then
COMPARE_LINK="https://github.com/waynebrantley/port-manager/compare/${PREVIOUS_TAG}...${NEW_VERSION}"
RELEASE_NOTES="## What's Changed

echo ""
echo "✅ Release PR created: $PR_URL"
echo ""
echo "📋 Next steps:"
echo " 1. Wait for tests to pass"
echo " 2. Merge the PR (squash merge)"
echo " 3. Run: ./scripts/finalize-release.sh $NEW_VERSION"
echo ""

# Save release info for finalize script
mkdir -p .release-temp
echo "$NEW_VERSION" > .release-temp/pending-version
echo "$IS_PRERELEASE" > .release-temp/is-prerelease
echo "$PR_URL" > .release-temp/pr-url

echo "💡 Tip: The finalize script will create the tag and GitHub release after merge."
echo ""
Full changelog: $COMPARE_LINK"
else
# For pre-releases, create tag and release immediately
echo "📤 Pushing changes and creating release..."
git push origin "$CURRENT_BRANCH"

# Create and push tag
echo "🏷️ Creating tag $NEW_VERSION..."
git tag -a "$NEW_VERSION" -m "Release $NEW_VERSION"
git push origin "$NEW_VERSION"

# Create GitHub Release
echo "🎉 Creating GitHub pre-release..."

RELEASE_NOTES="Pre-release $NEW_VERSION from branch \`$CURRENT_BRANCH\`
RELEASE_NOTES="Release $NEW_VERSION"
fi

## Installation
\`\`\`bash
npm install @wbrantley/port-manager@next
\`\`\`"
# Create GitHub Release
echo "Creating GitHub Release..."

if [[ "$IS_PRERELEASE" == "true" ]]; then
gh release create "$NEW_VERSION" \
--title "$NEW_VERSION" \
--notes "$RELEASE_NOTES" \
--prerelease \
--target "$CURRENT_BRANCH"

echo ""
echo "✅ Pre-release $NEW_VERSION created successfully!"
echo " 🏷️ Tag: $NEW_VERSION"
echo " 🌿 Branch: $CURRENT_BRANCH"
echo " 📦 npm package will be published automatically via GitHub Actions"
echo " 🔗 View release: https://github.com/waynebrantley/port-manager/releases/tag/$NEW_VERSION"
echo ""
echo "🔍 Monitor publish workflow:"
echo " https://github.com/waynebrantley/port-manager/actions"
echo "Pre-release $NEW_VERSION created successfully!"
echo " Tag: $NEW_VERSION"
echo " Branch: $CURRENT_BRANCH"
echo " npm tag: next"
echo " Install: npm install @wbrantley/port-manager@next"
else
gh release create "$NEW_VERSION" \
--title "$NEW_VERSION" \
--notes "$RELEASE_NOTES"

echo ""
echo "Release $NEW_VERSION created successfully!"
echo " Tag: $NEW_VERSION"
fi

echo " npm publish will run automatically via GitHub Actions"
echo ""
echo "Monitor:"
echo " Actions: https://github.com/waynebrantley/port-manager/actions"
echo " npm: https://www.npmjs.com/package/@wbrantley/port-manager"
echo ""