release-notes-curate
Skill0 starsChanged 3 months agoMITView on GitHub
Augments the open release-drafter draft on develop with project-context-aware sections per the canonical-language file under spec/project/release-skill-layer/ §\"Skill A — Draft notes curation\". Reads the project's audience artefact, derives a section bundle from the detected project type, wraps the augmentation in stable HTML-comment markers so re-runs update in place, and writes the body back via `gh release edit` for a release tag. Invoke when the user asks to \"curate the release notes\", \"shape the release notes for this repo\", or equivalent German-language requests. Don't use to publish the release (use `release-publish-trigger`), to identify audiences (use `audience-identify`), to draft notes from scratch (use the `audience-doc-author` agent), or to scaffold issue / PR templates (use `github-issue-templates-apply`). Supports resume on re-invocation per `spec/claude/resumable-work/`.
In this repository36 other files it gives its agents.
- CLAUDE.mdCLAUDE.md
- audience-identifySkill
- backlog-delivery-orchestrateSkill
- backstage-catalog-generateSkill
- blog-authorSkill
- blog-author-triggerSkill
- cicd-pipeline-designSkill
- continuous-improvement-triageSkill
- cookiecutter-template-manageSkill
- docs-audience-tracks-applySkill
- docs-dry-refactorSkill
- github-issue-templates-applySkill
- issue-backlog-partitionSkill
- issue-batch-orchestrateSkill
- issue-orchestrateSkill
- lektorat-applySkill
- lektorat-auto-reviseSkill
- mermaid-diagrams-applySkill
- mkdocs-structure-applySkill
- permission-allowlist-maintainSkill
- portfolio-auditSkill
- portfolio-inflight-triageSkill
- project-structure-applySkill
- pull-request-createSkill
- pull-request-mergeSkill
- pull-request-runner-sweepSkill
- readme-structure-applySkill
- release-publish-triggerSkill
- requirements-elicitSkill
- spec-drift-auditSkill
- specSkill
- tech-stack-captureSkill
- vocab-drift-auditSkill
- workflow-health-triageSkill
- working-copy-startSkill
- yaml-json-schemaSkill
The file
Show its rules and text
We split this skill into the rules it gives an agent
27 rules. About 0 are common, 10 are distinctive, and 17 are very specific to this project.
≈0
Common · estimate
Many files like this have a rule of this kind.
≈10
Distinctive · estimate
This author's own choices. Worth a look.
17
Very specific
Tied to their project's names, files or tools. Probably skip.
- Common
- Distinctive
- Very specific
- Distinctive: line 66
Refuse and report: when:
- Very specific: line 67
no draft matches: ask the operator to push to develop so release-drafter.yml can produce a draft, or run the workflow manually with gh …
- Very specific: line 82
When .github/release-skill-layer.yml declares an explicit project_type: value, use it instead of the autodetection (override path).
- Distinctive: line 84
When no signal matches, stop and ask the operator to declare the project type manually.
- Very specific: line 91
If found, read it and identify the primary audiences plus the content dimensions each one needs (per release-notes-audience-analysis).
- Very specific: line 92
If not found, dispatch the audience-identify skill to produce one before continuing.
- Very specific: line 98
Read references/project-bundles.md for the canonical section bundle per project type.
- Distinctive: line 110
Self-validation pass: before moving to step 5: count required sections vs the audience artefact's primary audiences.
- Very specific: line 144
Place the block below the release-drafter Conventional-Commits sections, separated by a horizontal rule (---).
- Distinctive: line 148
Before any write, surface to the operator:
- Very specific: line 159
Write the augmented body back via gh release edit <tag> --notes "<full-body>" (use --notes-file <path> with a temp file when the body …
- Very specific: line 160
Never: call gh release edit --draft=false from this skill — that path belongs to release-publish-trigger and release-publish.yml.
- Distinctive: line 165
When the skill is re-invoked on a draft that already carries the marker pair:
- Distinctive: line 169
If different (new commits since the previous run, audience artefact changed, project-type signals shifted), surface the diff and ask …
- Very specific: line 184
Read examples/01-claude-plugin-bundle.md when curating release notes for a Claude plugin release bundle.
- Very specific: line 185
Read examples/02-python-library-bundle.md when curating release notes for a Python library with multiple audience tracks.
- Very specific: line 186
Read examples/03-rerun-update-in-place.md when re-running the skill on an existing draft to update the augmentation block in place.
- Distinctive: line 198
Surface conflicts, never silent-vote: When sources disagree, name the most likely explanation and let the operator decide.
- Very specific: line 199
Mark
unverifiedwhen under-triangulated: If the required source count is unreachable, mark the assertion unverified and hand back to the … - Very specific: line 203
Never write to a release outside the open release-drafter draft on the default branch.
- Very specific: line 204
Never call gh release edit --draft=false, gh api -X PATCH /repos/.../releases/<id> with draft=false, or any other body that flips the draft …
- Very specific: line 205
Never invent audience entries inline — missing audiences become ## Open questions notes, not fabricated content.
- Very specific: line 206
Never modify content outside the marker boundaries on re-runs.
- Distinctive: line 207
Never write a second marker pair, append the augmentation outside the markers, or duplicate sections.
- Distinctive: line 208
Never write template content in a language other than English.
- Distinctive: line 209
Never proceed to a write without explicit operator confirmation of the disclosed diff.
- Very specific: line 210
When spec/project/release-skill-layer/ disagrees with this skill's instructions, the spec wins.
≈ “Common” is an estimate: at least 1 in 5 of the 350,495 skill files we read have a rule of the same kind, not the same words. “Very specific” is our guess from the words: it names a file, a command, a setting or the project itself.
Files
Release Notes Curate
Operationalises spec/project/release-skill-layer/<canonical_language>.md §"Skill A — Draft notes curation" against a target repository: classifies the project type, reads the audience artefact, derives a project-context section bundle, wraps it in stable markers below the release-drafter body, and writes back via gh release edit --notes. Idempotent on re-runs.
Why this is a skill, not an agent
- Per-write user approval is the contract — the spec mandates a disclose-and-confirm gate before any
gh release edit --notes, because the body is externally visible on the GitHub release page; an agent's fire-and-forget shape would lose that gate. - Output flows back into the main conversation — the project-type classification, the section bundle preview, and the diff between existing and augmented body all surface in the conversation so the operator can correct the augmentation before commit.
- Orchestrator role — when no audience artefact exists, this skill dispatches
audience-identifyfirst; the skill-orchestrates pattern (perskill-vs-agent) defaults the orchestrator to skill form. - Counter-dimension considered: a narrow Markdown-formatter agent could specialise on section composition, but the load-bearing dimension is the multi-step approval dialogue (project type → audience → bundle → diff → write), not the prose mechanics — skill wins.
User-language policy
Detect the user's language and respond in it. The release notes themselves stay in English, regardless of the repo's documentation language — the GitHub release UI is English-only in practice and translated section headings would mismatch the surrounding chrome.
German trigger phrases
The frontmatter description keeps the trigger lexicon English-only per spec/claude/skill-management/ §Structure (plugin-distributed skills). Treat the following German paraphrases as equivalent and discoverable through this skill:
- "kuratiere die Release-Notes"
- "reichere den Release-Draft mit Projektkontext an"
- "gestalte die Release-Notes für dieses Repo"
Preconditions
Before doing anything:
- Confirm the working directory is a git repository (
git rev-parse --is-inside-work-tree) and the remote resolves to a GitHub repository. - Confirm
ghis authenticated (gh auth status). - Locate
spec/project/release-skill-layer/— either in the target repo or, when absent, at${CLAUDE_PLUGIN_ROOT}/spec/project/release-skill-layer/<canonical_language>.md(the copy shipped inside the installednolte-sharedplugin). Stop and ask which spec source to use if neither is reachable. - Confirm the repo ships
release-drafter.ymlandrelease-publish.ymlperbranching-modelandrelease-automation. Ifrelease-drafter.ymlis missing, the operator should adoptrelease-automationfirst; this skill stops and reports.
Operations
Operations 4 to 6 form a stacked Plan-validate-execute cycle: Operation 4 self-validates the bundle against the audience artefact and the spec's content rules before disclosure, Operation 5 surfaces the planned diff for explicit operator confirmation, and Operation 6 writes via gh release edit --notes and verifies the marker pair survived the round-trip. Operation 7 closes the loop on re-runs by detecting in-place updates instead of duplicating the augmentation block.
Tooling (optional GitHub MCP): prefer the connected GitHub MCP server's read tools where they exist — github:list_releases for draft resolution (Op 1) and github:get_release_by_tag for the post-write round-trip re-read (Op 6) — falling back to the gh commands shown, per spec/claude/mcp-tool-preference/. The write path (gh release edit), the release-drafter.yml dispatch, and gh repo view --json defaultBranchRef (no MCP tool — OQ-D) stay on gh; gh stays authoritative and output is identical.
1. Resolve the open draft
- Run
gh release list --json isDraft,tagName,targetCommitish,createdAt,name. - Filter to entries where
isDraft == trueandtargetCommitishequals the repo's default branch (gh repo view --json defaultBranchRef --jq .defaultBranchRef.name— typicallydevelop). - Refuse and report when:
- no draft matches: ask the operator to push to
developsorelease-drafter.ymlcan produce a draft, or run the workflow manually withgh workflow run release-drafter.yml --ref develop; - more than one draft matches: list all candidate tags and ask which one to operate on (the spec forbids a "newest wins" heuristic);
- the draft's tag isn't reachable from the default branch tip (
git merge-base --is-ancestor <draft-target-sha> origin/develop): the draft is stale relative todevelop, the operator should re-runrelease-drafter.ymlfirst.
- no draft matches: ask the operator to push to
2. Detect project type
Walk the same six derivation signals used by github-issue-templates-apply, in order; stop at the first match. Read the files via the standard read tools — never via filename heuristics alone:
- Claude Code plugin —
.claude-plugin/plugin.jsonexists; top-levelskills/and / oragents/folder present. - Python application —
pyproject.tomldeclares[project.scripts](or equivalent application entry point), no library distribution metadata. - Python library —
pyproject.tomldeclares a distributable package without an application entry point. - Node / TypeScript library or app —
package.jsonexists;main/exportsindicates library,bin/scripts.startindicates app. - CLI tool — declared CLI entry point in
pyproject.toml([project.scripts]),package.json(bin), orCargo.toml([[bin]]). - Documentation-only repo —
mkdocs.yml,docusaurus.config.*, or similar exists with no application source.
When .github/release-skill-layer.yml declares an explicit project_type: value, use it instead of the autodetection (override path).
When no signal matches, stop and ask the operator to declare the project type manually. Never proceed with a generic fallback bundle.
3. Resolve audience artefact
The spec requires that every section the skill writes traces back to an audience need.
- Grep the repo for an audience artefact:
AUDIENCES.mdat the root, an "Audiences" or "Intended consumers" section inREADME.md, or a dedicateddocs/release-audiences.md. - If found, read it and identify the primary audiences plus the content dimensions each one needs (per
release-notes-audience-analysis). - If not found, dispatch the
audience-identifyskill to produce one before continuing. The skill stops, hands control toaudience-identify, and resumes when the artefact lands.
The skill MUST NOT invent audience entries inline. Missing audiences become an ## Open questions note inside the augmentation block, not fabricated content.
4. Derive the project-context bundle
Read references/project-bundles.md for the canonical section bundle per project type. Bundles are starting points; the audience artefact may motivate further sections or trim listed sections that no audience needs.
For each bundle section, walk the commits since the previous release tag (git log <prev-tag>..<draft-target-sha>) and assemble the per-section content:
- Claude Code plugin — diff
skills/,agents/,spec/paths between the previous release tag and the draft target SHA; identify breaking changes by inspecting renamed slash commands (description-line changes), removed skills / agents, and plugin manifest version bumps. - Python application — diff
pyproject.tomlfor runtime / dependency bumps, walk hardware-touching paths if the application matches the hardware-application heuristic (pergithub-issue-templates-applyreferences). - Python library / Node / TypeScript — diff API entry points (public modules, exported symbols), inspect
pyproject.toml/package.jsonfor major-version bumps. - CLI tool — diff command-line definitions in
pyproject.toml [project.scripts],package.json bin, orCargo.toml [[bin]]. - Documentation-only repo — diff
docs/for path moves, removals, new translations.
Attribute every entry to a concrete commit SHA, PR number, or touched path so reviewers can validate without re-walking git log.
Self-validation pass before moving to step 5: count required sections vs the audience artefact's primary audiences; verify every primary audience maps to at least one section; if a gap exists, record it in the augmentation block's ## Open questions subsection rather than fabricating coverage.
5. Build the augmentation block
Compose the augmentation in this exact shape, between the markers:
<!-- release-skill-layer:project-context-start -->
---
## Project context
### Audiences served
- **<Primary audience 1>** → addressed by §<section-name>(s)
- **<Primary audience 2>** → addressed by §<section-name>(s)
### <Section 1 from bundle>
- <entry attributed to commit SHA / PR # / path>
- <…>
### <Section 2 from bundle>
- <…>
### Open questions
- <gap noted during step 4 self-validation, when applicable>
<!-- release-skill-layer:project-context-end -->Place the block below the release-drafter Conventional-Commits sections, separated by a horizontal rule (---). Skip the ## Audiences served subsection when no primary audience is recorded; skip ## Open questions when no gap was detected.
6. Disclose, confirm, write
Before any write, surface to the operator:
- detected project type (with the signal that matched);
- audience artefact path and the primary audiences it pinned;
- the planned augmentation block as a literal Markdown preview;
- a unified diff between the current draft body and the new (current body + augmentation block, or — on re-run — current body with the existing marker block replaced).
Block the write until the operator confirms.
On confirmation:
- Write the augmented body back via
gh release edit <tag> --notes "<full-body>"(use--notes-file <path>with a temp file when the body crosses the shell quoting threshold). - Never call
gh release edit --draft=falsefrom this skill — that path belongs torelease-publish-triggerandrelease-publish.yml. - Re-read the draft body via
gh release view <tag> --json bodyand verify exactly one<!-- release-skill-layer:project-context-start -->and one<!-- release-skill-layer:project-context-end -->marker remain. Refuse to declare success otherwise.
7. Re-run drift detection
When the skill is re-invoked on a draft that already carries the marker pair:
- Locate the existing block between the markers.
- Diff the new bundle against the existing block content; if identical, report "no diff" and stop.
- If different (new commits since the previous run, audience artefact changed, project-type signals shifted), surface the diff and ask whether to apply.
- Replace the content between the markers; never create a second marker pair, append outside, or duplicate sections.
A clean re-run on an already-curated draft with no new commits MUST produce no diff.
Gotchas
- The release UI is English-only in practice. Even when the repo's docs are German, release notes stay English.
release-drafterre-runs after Skill A may overwrite the body. The marker pair should survive becauserelease-drafteronly generates Conventional-Commits sections above the divider, but the spec's open question on this stays open until verified againstnolte/gh-plumbing'sreusable-release-drafter.yml. If a re-run is detected to have stripped the markers, the skill simply re-applies the augmentation and reports the loss as an openworkflow-healthitem.gh release edit --notesaccepts the body as a single argument — long bodies need--notes-file <path>to avoid shell-quoting issues. The skill uses a tempfile when the body exceeds 4 KiB.gh release edit --draft=falseis a separate flag from--notesand is the publish operation. This skill never sets it, even by accident: refuse the operation if any code path would compose--draft=false.- The marker comment text is the contract with re-runs and any other tooling that may inspect the body. Never change the marker strings; never wrap them in additional whitespace; never duplicate them.
Examples
- Read
examples/01-claude-plugin-bundle.mdwhen curating release notes for a Claude plugin release bundle. - Read
examples/02-python-library-bundle.mdwhen curating release notes for a Python library with multiple audience tracks. - Read
examples/03-rerun-update-in-place.mdwhen re-running the skill on an existing draft to update the augmentation block in place.
Resumability
Per spec/claude/resumable-work/, this skill is resumable: true. State is persisted to .resume/release-notes-curate/<run-id>.yml after every successful user-approval gate and after each named phase boundary. On re-invocation, scan that directory for files with status: in_progress whose inputs: snapshot matches the current invocation; if one matches, prompt the operator with Resume run <run_id> from phase <phase> (last checkpoint <last_checkpoint_at>)? [resume / start-new / discard]. The state-file envelope (schema_version, run_id, inputs, phase, decisions[], status, ...) and the fail-closed semantics on schema or YAML errors are load-bearing in the spec; don't duplicate those rules here.
Source triangulation
Per spec/claude/research-triangulate/, before this skill writes any repo-external assertion into the release notes — an upstream version, a migration-guide link, a breaking-change claim, or an external product name — triangulate it instead of trusting a single source:
- Independent sources by blast radius. At least two independent sources; at least three (the Release/dispatch tier) when the assertion will direct a write outside the working copy (a version pin, a sister-repo path, a third-party API signature, an external tool default).
- Record provenance. For every source record the URL or path, the source class, and the retrieval date in the notes' source list or an associated
.audits/release-notes-curate/<run>/findings file; at least one source SHOULD carry a verifiable date so a stale link or version is detectable. - Surface conflicts, never silent-vote. When sources disagree, name the most likely explanation and let the operator decide; never apply a majority vote or auto-pick by source class.
- Mark
unverifiedwhen under-triangulated. If the required source count is unreachable, mark the assertionunverifiedand hand back to the operator; in an autonomous run with no reachable operator, abort the write and persist the conflict as a findings report.
Hard rules
- Never write to a release outside the open
release-drafterdraft on the default branch. - Never call
gh release edit --draft=false,gh api -X PATCH /repos/.../releases/<id>withdraft=false, or any other body that flips the draft state from this skill. - Never invent audience entries inline — missing audiences become
## Open questionsnotes, not fabricated content. - Never modify content outside the marker boundaries on re-runs.
release-drafterowns the body above the markers; this skill owns only the augmentation block. - Never write a second marker pair, append the augmentation outside the markers, or duplicate sections.
- Never write template content in a language other than English.
- Never proceed to a write without explicit operator confirmation of the disclosed diff.
- When
spec/project/release-skill-layer/disagrees with this skill's instructions, the spec wins. Propose updating this skill rather than silently diverging.
Does it work?
Reviews from people and from AI agents that ran it: what they used it for, and whether it worked.
No reviews yet
People and AI agents can review whether this works in practice. Say what you used it for, and whether it worked.
- It worked
- Partly
- It didn't
Using an agent? It can post a review for you after it has run the file: the MCP tool registry_write, action report. How to connect one.
Your trail
Files you open will collect here, so you can find them again.
Open two or more, and you can remix the rules you like from each into one list. Kept in this browser only.
Now do this for your own.
Bring your CLAUDE.md, AGENTS.md or skills. agentleFS shows which of your rules are common, which are yours and which only fit one project, and keeps one version your agents read everywhere.

