Skip to content
Git & PRs
Skill

/release

Worktrunk release workflow. Use when user asks to "do a release", "release a new version", "cut a release", or wants to publish a new version to crates.io and GitHub.

From plugin
worktrunk
9.7k5 skills3 hooks

Claude Code

$ npx -y skills add max-sixty/worktrunk --skill release --agent claude-code

SKILL.md

release.SKILL.md
name: release
description: Worktrunk release workflow. Use when user asks to "do a release", "release a new version", "cut a release", or wants to publish a new version to crates.io and GitHub.
metadata:
  internal: true

Release Workflow

Steps

1. **Sync the release branch with `main`**: The release worktree's branch lags `main` between releases — it's only reset to `main` after a release lands. Cutting from a stale branch silently drops everything merged since. Fast-forward to the tip of `main` before anything else:

   git fetch origin
   git merge --ff-only origin/main

`--ff-only` advances the branch when it's a strict ancestor of `origin/main` and **fails** (rather than creating a merge commit or discarding work) if it has diverged — reconcile manually before continuing. This is the release-branch equivalent of `wt up`, spelled out because the `up` alias rebases each branch onto its own upstream (`origin/release`), not `main`. Note the resulting commit SHA: this is the tip the changelog covers, and step 12 checks the changelog against everything that reaches `main` before the tag. 2. **Run tests**: Two gates — the local suite and the full cross-platform suite.

  • Local: `cargo run -- hook pre-merge --yes`.
  • Cross-platform: dispatch the `nightly` workflow on the cut-from tip and wait for it to go green. This is where a release gets its full linux/macos/windows validation: the PR path (`ci.yaml`) is moving to cargo-affected selection and will stop running the full `test` matrix, while `nightly` hosts `full-tests` (the full 3-OS suite) alongside feature-powerset, release-target, nix-flake, and minimal-versions. Benchmarks aren't part of `nightly` — they run in their own `benchmarks.yaml` and gate nothing.
     gh workflow run nightly.yaml --ref main
     # Registration lags the dispatch, and a prior release may have left a
     # stale completed workflow_dispatch run — filter to the in-flight one.
     sleep 5
     RUN=$(gh run list --workflow=nightly.yaml --event=workflow_dispatch --branch=main --limit 5 --json databaseId,status --jq 'map(select(.status != "completed")) | .[0].databaseId')

Launch a ci-reporter to monitor `$RUN` to completion (avoid `gh run watch` — it can hang). Fix any failure before continuing. 3. **Check current version**: Read `version` in `Cargo.toml` 4. **Review commits**: Check commits since last release to understand scope of changes. Audit the cumulative diff for the data-loss surface (see [Data-Loss Surface Review](#data-loss-surface-review)) and documentation (see [Documentation Review](#documentation-review)). 5. **Check library API compatibility (advisory)**: Run `cargo semver-checks check-release -p worktrunk` (install with `cargo install cargo-semver-checks --locked` if missing) as a bump-level input, not a compat gate — worktrunk ships breaking library changes freely. If it reports breaking changes, that's fine; under semver the bump must still be minor (pre-1.0) or major (post-1.0). See "Library API Compatibility" below. 6. **Credit contributors**: Check for external PR authors and issue reporters (see "Credit External Contributors" and "Credit Issue Reporters" below) 7. **Determine release type**: Pick the bump from the changes (including semver-checks result). Ask the user only if the choice is genuinely ambiguous (see below). 8. **Bump version** (must run on a clean tree — before editing CHANGELOG):

   cargo release X.Y.Z -p worktrunk -x --no-publish --no-push --no-tag --no-verify --no-confirm && cargo check

This bumps `Cargo.toml` and `Cargo.lock`, then auto-commits. We'll reset this commit in step 10 to fold in the CHANGELOG. 9. **Update CHANGELOG**: the top section holds this release's changes (see MANDATORY verification below). If it is `## Unreleased`, rename that heading to `## X.Y.Z` and fold the remaining entries into it — inserting a new heading above it ships a stale `## Unreleased` in the release notes. Otherwise the top section is the last shipped version: add a `## X.Y.Z` section above it, never append to it. 10. **Commit**: Reset the auto-commit from step 8, stage everything, and create the final release commit:

    git reset --soft HEAD~1 && git add -A && git commit -m "Release vX.Y.Z"

11. **Merge to main**: complete the documentation review on the final candidate, then push the release branch, open a PR, wait for CI, and merge it. Keep the worktree — the remaining steps run from it. Then move the branch onto the merged tip:

    git fetch origin && git reset --keep origin/main

The PR squash-merges, so the branch is no longer an ancestor of `main` and step 1's `--ff-only` can't advance it; `--keep` moves it across and still fails if anything is uncommitted. `main` can advance during the CI wait; step 12 catches anything that lands before the tag. 12. **Verify the changelog covers `main`, then tag and push**: the tag decides what ships — `release.yaml` builds the binaries and the GitHub release notes from the tree at the tag, so everything reachable from it is in the release. The merge squashes onto whatever `main` tip exists at merge time, so a commit that lands during the PR's CI wait is already an ancestor of the release commit and ships whether or not the changelog mentions it (the easy miss is a follow-up that reworks a feature this release already documents). List what reached `main` since the cut-from tip (step 1):

    git fetch origin
    git log --oneline <cut-from-commit>..origin/main

Clean means the changelog at `origin/main` documents every user-facing commit listed. With no drift the list is one line, the `Release vX.Y.Z (#NNNN)` squash commit. Review anything else that drifted in during the window and fold what's user-facing into the changelog with a follow-up squash PR, then re-fetch and re-run. The list only grows across passes — the drifted commits stay, joined by t

Read more
@max-sixty
Ships withworktrunk

Worktrunk is a CLI for Git worktree management, designed for parallel AI agent workflows

Stars on GitHub

Momentum

stars in total
9.7k
Star history of max-sixty/worktrunk on GitHub, a chart by star-history.com

Other skills on worktrunk.

running-tend

running-tend

Worktrunk-specific guidance for tend CI workflows. Adds codecov polling, Rust test commands, labels, and review criteria on top…

@max-sixty@max-sixtyInstall Skill
worktrunk

worktrunk

Guidance for Worktrunk (the `wt` CLI) — git worktree management, hooks, and config. Load when working out which worktree a `wt`…

@max-sixty@max-sixtyInstall Skill
wt-switch-create

wt-switch-create

Create a new worktrunk worktree (optionally in another repo) and switch this session's working directory into it. Use when…

@max-sixty@max-sixtyInstall Skill

More skills from other plugins.

gh

gh

Patterns for invoking the GitHub CLI (gh) from agents. Covers structured output, pagination, repo targeting, search vs list, gh…

cli11d47k
@cli@cliInstall Skill
gh-stack

gh-stack

Manages stacked PRs and splits multi-part work into reviewable branches with gh-stack. Use for stack creation, viewing, edits,…

gh-stack3d1.8k
@github@githubInstall Skill
field-test

field-test

Exercise git tools, resources, and prompts against a live HTTP server via MCP JSON-RPC over curl. Starts the server, surfaces the…

@cyanheads@cyanheadsInstall Skill
git-surgeon

git-surgeon

Non-interactive hunk-level git staging, unstaging, discarding, undoing, fold, amend, squash, commit splitting, and commit…

@raine@raineInstall Skill

Questions about release.

Which coding agents can use release?
release installs in Claude Code, Codex, Cursor, Gemini CLI, GitHub Copilot, OpenCode and Windsurf with the skills CLI, using each agent's flag shown on this page. Flowy's auto-invocation, which fires a skill when your prompt matches, runs in Claude Code only.