Create a Trellis migration manifest and matching docs-site changelogs for a target release by analyzing commits since the previous release. Use when preparing a patch, beta, rc, or minor release manifest.
Installs into .claude/skills of the current project.
Are you the author of Create Manifest?
Add the live security badge to your README. It updates with every re-scan.
[](https://www.skillsdirectory.com/skills/mindfold-ai-create-manifest)
---
name: create-manifest
description: "Create a Trellis migration manifest and matching docs-site changelogs for a target release by analyzing commits since the previous release. Use when preparing a patch, beta, rc, or minor release manifest."
---
# Create Migration Manifest
Create a migration manifest for a new patch, beta, rc, or minor release based on commits since the previous release.
## Arguments
- `$ARGUMENTS` - Target version, for example `0.5.15` or `0.6.0-beta.14`. If omitted, ask the user.
## Package release model
Trellis currently publishes two npm packages from the same git tag:
- `@mindfoldhq/trellis`
- `@mindfoldhq/trellis-core`
Both packages must always share the exact same version and npm dist-tag. Source uses `workspace:*`; the packed CLI must depend on the exact published core version.
Official npm publishing is CI-only. Never use local `npm publish` or `pnpm publish` to compensate for a failed or partial release. Local verification may use `pnpm pack`, `release-preflight`, tests, lint, typecheck, and `npm view`.
## Step 1: Identify Last Release
```bash
git tag --sort=-v:refname | head -5
```
Pick the most recent release tag on the current release line, for example `v0.5.14` or `v0.6.0-beta.13`.
## Step 2: Gather Changes
```bash
git log <last-release-tag>..HEAD --oneline
git log <last-release-tag>..HEAD --oneline -- packages/cli/src/ packages/core/src/
git log <last-release-tag>..HEAD --oneline -- packages/cli/scripts/ .github/workflows/ package.json packages/*/package.json pnpm-lock.yaml
```
User-facing changelog coverage should focus on source behavior under `packages/cli/src/` and `packages/core/src/`. Release wiring, workflow, or package dependency changes belong in `Internal` only when users can observe the behavior, for example install/update reliability or multi-package availability.
## Step 3: Analyze Each Relevant Commit
For each commit that touches relevant source or release behavior:
1. Read the diff:
```bash
git diff <parent>...<commit> -- packages/cli/src/ packages/core/src/ --stat
git diff <parent>...<commit> -- packages/cli/scripts/ .github/workflows/ package.json packages/*/package.json pnpm-lock.yaml --stat
```
2. Classify as `feat`, `fix`, `refactor`, or `chore`.
3. Write a one-line changelog entry in conventional commit style.
Drop pure spec edits, mechanical refactors, and internal-only cleanup unless they materially change what users observe.
## Step 4: Draft Changelog
Voice: technical reference doc. Short, clear, plain. Not a story, not a sales pitch. Follow `.trellis/spec/docs-site/docs/style-guide.md` -> "Changelog / Release Notes Voice".
Do:
- Lead each `###` section with one sentence stating what changed. Then table, code, or bullets. Done.
- Use feature names as headings, for example `### Joiner onboarding task`.
- Include grep-able identifiers: file paths, function names, flag names, migration entries.
- Mirror English and Chinese 1:1 in docs-site changelogs: same sections, same tables, same code blocks; only prose translated.
Do not:
- Add "Why", "Background", or "Rationale" paragraphs.
- Add a Tests section or test counts.
- Add Internal entries unless users can observe the behavior.
- Use rhetorical questions, emotional framing, filler adverbs, or marketing voice.
- Use outcome-phrased headings that age badly or are not grep-able.
Length cap: each `###` section should stay under about 120 words.
Allowed top-level sections, ordered:
1. `Enhancements`
2. `Bug Fixes`
3. `Internal` only if user-observable
4. `Upgrade`
Skip empty sections.
Manifest `changelog` field:
- Use one string with real `\n` separators.
- Group with bold prefixes: `**Enhancements:**`, `**Bug Fixes:**`, `**Internal:**`.
- Keep it shorter than the MDX changelog because it prints in terminal during `trellis update`.
## Step 5: Determine Manifest Fields
| Field | How to decide |
|---|---|
| `breaking` | Any breaking API or behavior change. Default `false` for patch/prerelease fixes. |
| `recommendMigrate` | Any rename/delete migration the user should run. Default `false` for patch fixes. When `breaking=true` and `recommendMigrate=true`, `trellis update` exits 1 without `--migrate`. |
| `migrations` | List of `rename`, `rename-dir`, `delete`, or `safe-file-delete` actions. Usually `[]` for patch fixes. |
| `migrationGuide` | Mandatory when `breaking=true` and `recommendMigrate=true`. Human migration guide inserted into the generated migration task PRD. |
| `aiInstructions` | Strongly recommended with `migrationGuide`. Instructions for AI migration assistance. |
| `notes` | Brief terminal guidance shown during update. |
Breaking releases without `migrationGuide` produce a broken upgrade experience. `packages/cli/scripts/create-manifest.js` validates this.
## Step 5a: Per-Migration Entry Fields
| Field | Purpose | Required |
|---|---|---|
| `type` | `rename`, `rename-dir`, `delete`, or `safe-file-delete` | yes |
| `from` | Source path relative to project root | yes |
| `to` | Target path | yes for renames |
| `description` | What the migration does, shown in the confirm prompt | recommended |
| `reason` | Version-specific context for modified-file prompts | optional |
| `allowed_hashes` | Known-pristine SHA256 hashes for safe deletion | required for `safe-file-delete` |
`rename` uses the project-local `.trellis/.template-hashes.json`; it does not use manifest `allowed_hashes`.
Use:
- `rename` when a file moved and has a replacement path.
- `safe-file-delete` when a file was removed and has no replacement.
- `safe-file-delete` plus `notes` when a removed file was folded into another command.
## Step 6: Create Manifest
Pipe JSON through stdin:
```bash
cat <<'EOF' | node packages/cli/scripts/create-manifest.js
{
"version": "<version>",
"description": "<short description>",
"breaking": false,
"recommendMigrate": false,
"changelog": "<changelog text with real newlines>",
"notes": "<notes>",
"migrations": []
}
EOF
```
For breaking releases with many rename entries, generate the entries with a small temporary Node script and pipe the final JSON into `create-manifest.js`.
## Step 7: Create Docs-Site Changelogs
This step is mandatory for every release.
Create both files:
1. `docs-site/changelog/v<version>.mdx`
2. `docs-site/zh/changelog/v<version>.mdx`
Use the format from recent changelog files. English and Chinese structure must match 1:1.
Update `docs-site/docs.json`:
- Add `"changelog/v<version>"` to the English changelog pages list at the top.
- Add `"zh/changelog/v<version>"` to the Chinese changelog pages list at the top.
- Update navbar changelog links to the new version.
When a `<Note>` or `<Warning>` block contains a markdown list, the closing tag must start at column 0:
```mdx
<Note>
- bullet
</Note>
```
## Step 8: Docs Lifecycle
The docs-site root path is stable. Development cycles live under `beta/` or `rc/`.
| Transition | Script | When |
|---|---|---|
| Start a new beta | `docs-site/scripts/docs-beta-start.sh` | Before the first beta of a new minor/major, for example `0.6.0-beta.0`. |
| Beta to RC | `docs-site/scripts/docs-beta-to-rc.sh` | Before the first rc, for example `0.6.0-rc.0`. |
| RC to GA | `docs-site/scripts/docs-promote.sh` | Before `pnpm release:promote`. |
Per-patch releases (`-beta.1`, `-rc.1`, `0.5.1`) do not run lifecycle scripts. Write changelog MDX, update `docs.json`, commit/push docs-site, then bump the main repo submodule pointer.
Full reference: `.trellis/spec/docs-site/docs/release-lifecycle.md`.
## Step 9: Preflight Before Release
Run local verification only; do not publish locally.
```bash
node packages/cli/scripts/check-docs-changelog.js --type <beta|rc|promote>
node packages/cli/scripts/release-preflight.js check-versions
node packages/cli/scripts/release-preflight.js verify-packed-cli
node packages/cli/scripts/release-preflight.js publish-plan
pnpm lint
pnpm typecheck
pnpm test
```
Skip `check-docs-changelog` only for stable patch releases where that command is not required by the release type.
## Step 10: Review and Confirm
Verify:
1. `packages/cli/src/migrations/manifests/<version>.json` exists and has valid JSON.
2. Manifest `changelog` renders as real newlines.
3. Both docs-site changelog MDX files exist and match 1:1.
4. **All** submodule commits are pushed before the main repo pointer commit (currently `docs-site/` + `marketplace/`). Verify with: `git submodule foreach 'sha=$(git rev-parse HEAD); git ls-remote origin $sha | grep -q $sha && echo "ok $name" || echo "FAIL $name $sha"'`. Tag-triggered CI does `git submodule update --init --recursive` and fails on the first unpushed pointer with `fatal: remote error: upload-pack: not our ref <SHA>`.
5. `@mindfoldhq/trellis` and `@mindfoldhq/trellis-core` versions still match.
## Step 11: Publish Through CI
Use the project release script so the tag starts CI:
```bash
pnpm release
pnpm release:beta
pnpm release:rc
pnpm release:promote
```
After CI succeeds, verify public npm:
```bash
npm view @mindfoldhq/trellis@<version> version dist-tags --json --registry=https://registry.npmjs.org/
npm view @mindfoldhq/trellis-core@<version> version dist-tags --json --registry=https://registry.npmjs.org/
```
If CI fails or npm visibility is wrong, fix the workflow/scripts and re-run the CI path. Do not use local publish to fill the gap.
## Dogfooding
Breaking releases must run end-to-end migration in a throwaway directory:
```bash
mkdir /tmp/migrate-test && cd /tmp/migrate-test && git init -q .
npx -y @mindfoldhq/trellis@<last-ga> init -y -u test --claude --cursor --<platforms>
node <repo>/packages/cli/dist/cli/index.js update --migrate --dry-run
yes | node <repo>/packages/cli/dist/cli/index.js update --migrate --force
yes | node <repo>/packages/cli/dist/cli/index.js update
```
Watch for orphan files, idempotency churn, and backup bloat.