Skip to content

feat: custom prefix + SKILL_NAME templating — /g-ship, /g-qa in one command (v0.12.12.0)#586

Open
lucaslim wants to merge 6 commits intogarrytan:mainfrom
lucaslim:lucaslim/skill-prefix-frontmatter-sync
Open

feat: custom prefix + SKILL_NAME templating — /g-ship, /g-qa in one command (v0.12.12.0)#586
lucaslim wants to merge 6 commits intogarrytan:mainfrom
lucaslim:lucaslim/skill-prefix-frontmatter-sync

Conversation

@lucaslim
Copy link
Copy Markdown

@lucaslim lucaslim commented Mar 27, 2026

Summary

  • Custom prefix word. Setup now offers 3 choices: short names (`/qa`), namespaced (`/gstack-qa`), or a custom word you type (`g`, `gs`, `mytools`). The dash separator is automatic.
  • `{{SKILL_NAME}}` template variable. SKILL.md templates now use `name: {{SKILL_NAME}}` in frontmatter. The generator resolves this to the prefixed name at build time (e.g. `name: g-ship` when prefix is `g`). Claude Code uses the `name:` field as the slash command trigger — this is what makes `/g-ship` actually work, not just a renamed directory.
  • Live reload. `gstack-config set skill_prefix g` regenerates all installed SKILL.md files immediately — no setup re-run needed.
  • `--prefix ` flag. Takes a word argument now (`--prefix g`) instead of being a toggle. `--no-prefix` unchanged.
  • Universal cleanup. Any prefix → any prefix cleans up old generated dirs first, using `AUTO-GENERATED from SKILL.md.tmpl` as the detection signal.

What changed

File Change
`bin/gstack-config` Validation, empty string handling, backward compat (`true`→`gstack`), live regen trigger, `readlink -f` path resolution, `
`setup` `SKILL_PREFIX` is now a string word; 3-option interactive prompt; `validate_prefix()`; `cleanup_generated_skill_dirs()` replaces 2 old cleanup functions; `GSTACK_SKIP_REGEN=1` prevents double regen
`scripts/gen-skill-docs.ts` `{{SKILL_NAME}}` resolution from dir name + prefix; `--output-root ` for installing to target dir without modifying source
`scripts/resolvers/preamble.ts` Updated prefix instruction — handles arbitrary word, not just legacy `"true"`
29 SKILL.md + templates `name: {{SKILL_NAME}}` in all templates; regenerated with updated preamble text
`test/gen-skill-docs.test.ts` 8 updated tests for string-based prefix, universal cleanup, 3-option prompt

How the name templating works

Every SKILL.md template has `name: {{SKILL_NAME}}` in its frontmatter. When `gen-skill-docs.ts` runs:

  1. It derives the base name from the directory (`ship`, `qa`, etc.)
  2. If a prefix is set (e.g. `g-`), it prepends it: `g-ship`
  3. The generated `SKILL.md` gets `name: g-ship`
  4. Claude Code reads that `name:` field and registers `/g-ship` as the trigger

Without this, renaming the directory to `g-ship/` would create the file path but Claude Code would still look for a different name. The `name:` field is the actual hook.

Test plan

  • `bun test` — 591 pass, 0 fail
  • `{{SKILL_NAME}}` resolves correctly with and without prefix (gen-skill-docs tests)
  • `gstack-config get skill_prefix` returns `gstack` when stored value is `true` (backward compat)
  • `gstack-config set skill_prefix g` validates format and triggers regen
  • Setup 3-option prompt tested (choice 1/2/3, custom word input, validation)
  • Universal cleanup detects by `AUTO-GENERATED` header, not prefix string
  • `GSTACK_SKIP_REGEN=1` suppresses double regen when called from setup
  • PATH-invoked `gstack-config` resolves gstack dir via `readlink -f`

Design doc

APPROVED by autoplan (CEO + Eng reviews): `~/.gstack/projects/lucaslim-gstack/lucaslim-lucaslim-skill-prefix-frontmatter-sync-design-20260327-131400.md`

9 MUST-FIX items from eng review — all addressed before coding began.

lucaslim and others added 6 commits March 27, 2026 13:17
…-root on install

When a user opts into gstack- prefixed skills, Claude Code reads the name:
field in SKILL.md frontmatter to register slash commands. Previously that
field was hardcoded (e.g. name: ship) even when installed as gstack-ship/,
so /gstack-ship never triggered.

Fix: replace hardcoded name: fields in all 29 SKILL.md.tmpl files with
{{SKILL_NAME}}, resolved by a new SKILL_NAME resolver in gen-skill-docs.ts.
The resolver derives the name from the skill directory + the --prefix flag
(e.g. --prefix gstack- turns ship → gstack-ship, preserves gstack-upgrade).

setup now calls gen-skill-docs.ts with --output-root ~/.claude/skills/ and
--prefix gstack- (when configured), generating SKILL.md files directly into
real directories instead of symlinking. The installed SKILL.md reflects the
correct name: field so /gstack-ship, /gstack-qa, etc. all register properly.

Cleanup helpers updated to remove both old symlinks and generated directories
(identified by AUTO-GENERATED header) when switching prefix modes.
…put-root integration tests

Two review-driven improvements:

1. generate_claude_skill_docs() now checks PIPESTATUS[0] after piping bun's
   output through grep. If bun exits non-zero (not in PATH, syntax error,
   module not found), the install previously appeared to succeed with no
   skills written. Now it prints a clear ERROR to stderr and returns 1.

2. New describe block in gen-skill-docs.test.ts: three integration tests
   that actually invoke gen-skill-docs.ts with --prefix gstack- --output-root
   /tmp/... and read the output SKILL.md files to assert correct name: values:
   - name: gstack-ship with prefix (happy path)
   - name: gstack-upgrade with prefix (already-prefixed, no double-prefix)
   - name: ship without prefix (unprefixed mode)

These close the gap the eng review found: prior tests only checked that setup
referenced the right function names, but nobody verified the actual output.
…tes skills instantly

Users can now choose a custom prefix word instead of just gstack- or none.
- setup interactive prompt: 3 options (flat / gstack- / custom word)
- --prefix <word> CLI flag accepts a word (dash appended automatically)
- gstack-config set skill_prefix g triggers immediate Claude skill regen
- gstack-config get skill_prefix migrates stored true→gstack, false→false
- Validation: [a-z0-9]{1,10} in both setup and gstack-config
- Universal cleanup_generated_skill_dirs replaces prefix-specific cleanup functions
- SKILL_PREFIX changes from int (0/1) to string (word or empty)
- Dash guard: empty prefix never produces --prefix - (dash-only)
- GSTACK_SKIP_REGEN=1 prevents double regen when setup calls gstack-config set
- Preamble text updated: handles any prefix word, not just "true"

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
Preamble SKILL_PREFIX guidance now handles arbitrary prefix words (g, gs, etc.)
instead of only the legacy "true" boolean value.

Co-Authored-By: Claude Sonnet 4.6 <noreply@anthropic.com>
@lucaslim lucaslim changed the title feat: custom skill prefix — /g-ship, /g-qa in one command (v0.12.12.0) feat: custom prefix + SKILL_NAME templating — /g-ship, /g-qa in one command (v0.12.12.0) Mar 27, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant