Bootstraps the toolkit's `index.md` system in a target project. Scans for markdown-heavy folders, drafts `title` and `description` frontmatter, scaffolds `index.md` per chosen folder, and runs `canon indexes regen` to validate. Use when asked to "set up indexes", "bootstrap indexes", "add index.md to this project", or "install indexes". Assumes the `canon` CLI is on PATH.
Scanned 9/2/2026
Install to Claude Code
npx -y skills add erclx/canon --skill setup-indexes --agent claude-codeInstalls into .claude/skills of the current project.
Are you the author of Setup Indexes?
Add the live security badge to your README — it updates automatically with every re-scan.
[](https://www.skillsdirectory.com/skills/erclx-setup-indexes)More formats (shields.io, HTML) on the badges page.
---
name: setup-indexes
description: Bootstraps the toolkit's `index.md` system in a target project. Scans for markdown-heavy folders, drafts `title` and `description` frontmatter, scaffolds `index.md` per chosen folder, and runs `canon indexes regen` to validate. Use when asked to "set up indexes", "bootstrap indexes", "add index.md to this project", or "install indexes". Assumes the `canon` CLI is on PATH.
---
# Indexes install
Adds the index.md system to a project that does not have it. Operates in the active Claude session: Claude reads files, drafts frontmatter, confirms with the user, and writes. The CLI handles validation and regeneration only.
Read `.claude/context/indexes.md` from the toolkit if context on the system is needed before scanning.
## Scope
- Bootstrap un-indexed folders only. Skip folders that already contain an `index.md`.
- All-or-nothing per chosen folder. Every `*.md` sibling in a chosen folder gets `title` and `description` injected, or none does. Partial migration creates folders that hard-error on regen.
- This is where `setup-init` sends an install that wants the Claude layer without the tooling chain, once `canon claude init` has seeded the docs. The work is the same either way, since the scan below prunes `.claude` and reads the project's own documentation folders whichever route reached it.
## Scan
Walk the project root for folders containing three or more sibling `*.md` files. Prune `.git`, `node_modules`, `.claude`, `snippets`, anything matched by `.gitignore`, and any folder that already contains an `index.md`.
Skip `.claude/snippets/`. Snippets are invoked by reference (`@snippet-name`) rather than browsed, so they need neither `index.md` nor per-file frontmatter. Adding them creates noise that targets keep reporting.
For each candidate, capture:
- Folder path relative to project root
- Sibling count
- Existing frontmatter coverage (how many siblings already carry `title` and `description`)
## Present candidates
Output one line per candidate:
```plaintext
- docs/ (8 files, 0/8 with frontmatter)
- guides/ (5 files, 2/5 with frontmatter)
- references/ (3 files, 0/3 with frontmatter)
```
Ask the user which to bootstrap. Accept folder paths, `all`, or `none`. The user can also force a folder with fewer than three siblings by naming it explicitly.
## Draft frontmatter
For each chosen folder, read every `*.md` sibling and draft frontmatter:
- `title`: derived from the first H1. If absent, derive from the filename in sentence case.
- `description`: one line summarizing the file's purpose, drawn from the first paragraph after the H1. Follow `${CLAUDE_SKILL_DIR}/../../standards/markdown.md` § Frontmatter descriptions for length and style.
Surface every drafted entry to the user grouped by file:
```plaintext
docs/architecture.md
title: Architecture
description: System boundaries, data flow, and module responsibilities
```
The user accepts, edits, or rejects per file. Offer "accept all remaining" once the user confirms two in a row to keep the loop short.
Never write drafts before the user confirms. Drafted text is a proposal, not a commit.
## Scaffold the folder index
Compose `index.md` for each chosen folder with:
```markdown
---
title: <folder name in sentence case, user-editable>
subtitle: <one-line folder purpose, user-editable>
---
```
Surface the proposed `title` and `subtitle` and let the user edit before writing.
## Inject
After all confirmations, write frontmatter into each sibling and `index.md` into each folder. Use a single batched write per file.
Preserve existing content below the frontmatter block. If a sibling already has frontmatter without `title` or `description`, merge in the missing fields. Do not touch files the user rejected.
## Validate
Run from the project root:
```bash
canon indexes regen --dry-run --json
```
Parse the JSON. On any `error` action, surface the file and reason and stop. On `would-write` for the bootstrapped folders, the dry-run is healthy. Run for real:
```bash
canon indexes regen --json
```
Count the `written` actions in that record and report the number. Read the real run the same way the dry run is read, since the exit carries nothing reliable back to a session. An operator's shell profile may wrap `canon` in a function that runs the binary and then a second command and takes the second status, so a regen that errored on a sibling missing `title` arrives here as a clean pass.
## Offer the convention seed
First check whether `CLAUDE.md` exists in the project root. If absent, do not scaffold one. Skip the seed install with this exact message:
```plaintext
No CLAUDE.md in the project. Skipping convention seed.
To add the convention later, run `canon tooling sync` or `canon init`,
then re-invoke this skill.
```
If `CLAUDE.md` exists, check it for an existing `## Indexes` section:
```bash
grep -l '^## Indexes' CLAUDE.md 2>/dev/null
```
If the section is present, skip the seed silently.
If `CLAUDE.md` exists but has no `## Indexes` section, offer to install the canonical convention block. The text below is the source of truth and is mirrored in the toolkit's `tooling/claude/seeds/CLAUDE.md`. Paste it verbatim. Do not rewrite, paraphrase, condense, or add punctuation.
```markdown
- When a folder has an `index.md`, check it before reading individual files in that folder.
- For folders where an agent browses to pick a document, `index.md` is regenerated from each file's frontmatter. Do not hand-edit `index.md`. Code folders and scratch folders do not need one.
- Every `index.md` carries its own frontmatter (`title`, `subtitle`) that the walker preserves. To keep a folder's `index.md` hand-edited, add `auto: false` to its frontmatter.
```
Append a new `## Indexes` section at the end of the file containing the three lines. Do not touch any other section.
## Closeout
Always emit this block as the final message of the skill run. Do not skip it regardless of how the seed step concluded (installed, already present, declined, or skipped because no `CLAUDE.md` exists). Output exactly one closeout, even if the seed step paused for user input. Resume the flow after the user responds and emit the closeout next.
Format:
```plaintext
Bootstrap complete.
Folders bootstrapped:
- <path> (<n> files)
Drafts: <n> accepted, <n> edited, <n> rejected
Convention seed: <installed | already present | declined | skipped (no CLAUDE.md)>
Optional maintenance (opt in, the skill does not configure these):
- lint-staged entry in .lintstagedrc.json:
"**/*.md": "canon indexes regen"
- Claude Code PostToolUse hook on Edit and Write matching **/*.md running:
canon indexes regen
```
Replace bracketed values with the values from this run. Drop the "Folders bootstrapped" line if zero folders were chosen.
## Reference
Both pages sit in the toolkit and install nowhere, so a target reads them there rather than in its own tree.
- The toolkit's `.claude/context/indexes.md`: system rationale, frontmatter contract, when to adopt
- The toolkit's `docs/agents/indexes.md`: `canon indexes regen` flags, exit codes, JSON shape
Is this your skill, or is something wrong with this listing? Request removal or report an issue. Author removals are honored within 72 hours.
No comments yet. Be the first to comment!