book-binding
Use when creating a new grimoire plugin (a book-of-* book), adding a skill or hook to an existing book, or preparing a book release. Covers the scaffold tool, the layout and frontmatter rules both har
SKILL.mdplugins/archmage/skills/book-binding/SKILL.md
GitHubBinding a book
A book is one plugin directory under plugins/ in the grimoire repository. This skill applies inside a checkout of that repository. If you are not in one, tell the user and stop.
1. Scaffold
From the repository root:
node tools/grimoire.mjs new-book book-of-<domain> --description "<one sentence>" [--category "<Codex category>"] [--skill <skill-name>]
The tool creates VERSION (0.1.0), CHANGELOG.md, both manifests, a README.md, and, with --skill, a first skill with its agents/openai.yaml sidecar. It then regenerates both marketplace files. Only archmage may omit the book-of- prefix.
2. Write skills
Each skill lives in skills/<name>/SKILL.md plus skills/<name>/agents/openai.yaml.
- Name the skill after its topic with the shortest name that identifies it (
tdd,adr,code-review). A domain term beats a description of it; a gerund (reviewing-pull-requests) is fine when a verb is needed. Names are kebab-case, at most 4 words, contain no article (a,an,the), and must be unique across every book;checkenforces all four. - Frontmatter may use only
name,description,metadata,license,allowed-tools. Put anything else undermetadata.namemust equal the directory name. - Write the
descriptionas a trigger: "Use when ..." followed by what the skill does. Both harnesses pick skills by this text. - Reference helper scripts through the interpreter (
node scripts/x.mjs), never by bare path. - Do not link to files in other books or outside the plugin root.
- The sidecar needs
interface.display_name,interface.short_description, andpolicy.allow_implicit_invocation(false for skills the user must invoke explicitly).
3. Add a hook (optional)
Put hooks/hooks.json at the plugin root and set "hooks": "./hooks/hooks.json" in .codex-plugin/plugin.json. Use only events both harnesses support (SessionStart, UserPromptSubmit, PreToolUse, PostToolUse, Stop, SubagentStart, SubagentStop, PreCompact, SessionEnd). Write matchers with Claude's tool names (Bash, Edit|Write, Agent); Codex aliases them. Commands look like node "${CLAUDE_PLUGIN_ROOT}/scripts/x.mjs". Scripts are dependency-free Node 20+, read the JSON payload from stdin, and must exit 0 with no output on any internal failure.
Never add commands/, bin/, a root plugin.json, a symlink, or a CLAUDE.md inside the plugin. The checker rejects all of them, each for a harness-compatibility reason listed in AGENTS.md.
4. Validate
node tools/grimoire.mjs check
node tools/run-tests.mjs
claude plugin validate . --strict
Fix everything check reports before committing. It also regenerates nothing; if it says a marketplace is stale, run node tools/grimoire.mjs stamp.
To try the book in a real session, install this checkout into both harnesses from the repository root:
node tools/grimoire.mjs dev-install # first time: swaps marketplace "grimoire" from GitHub to this checkout (asks before deleting Claude plugin data)
node tools/grimoire.mjs dev-refresh # after every edit: both harnesses copy plugins into a cache, so re-copy
node tools/grimoire.mjs dev-uninstall # when done: swap back to GitHub
Never register a second marketplace name or use --plugin-dir beside an installed copy; skills would appear twice and hooks would run twice. In Codex, a changed hooks/hooks.json must be trusted again in /hooks.
5. Release
- Edit
plugins/<book>/VERSIONto the new semver. - Move the
[Unreleased]notes inplugins/<book>/CHANGELOG.mdunder a## [<version>] - <date>heading. - Run
node tools/grimoire.mjs stamp <book>to write the version into both manifests and the marketplaces. - Commit and tag
<book>/v<version>.