Files
pbakaus_impeccable/DEVELOP.md
T
GlacierPhonk 8d4f65f351 docs: update DEVELOP.md to reflect current architecture
The contributor guide had fallen behind the codebase in several ways:

- Documented source/commands/ which no longer exists (skills-only now)
- Only described 4 providers (Cursor, Claude Code, Gemini, Codex) —
  added Agents, Kiro, OpenCode, Pi
- Cursor described as "no frontmatter support" but it now uses Agent
  Skills with YAML frontmatter
- "What Gets Generated" diagram showed old command-based output paths
- Build system described as "single ~170-line script" but is now modular
  (scripts/lib/transformers/*.js)
- Referenced dist/ as committed but it's now gitignored
- Key Functions list missing 4 transformer functions
- Source Format missing user-invokable and args fields
- Referenced npm instead of bun in troubleshooting
2026-03-14 22:04:52 +01:00

266 lines
9.7 KiB
Markdown

# Developer Guide
Documentation for contributors to Impeccable.
## Architecture
This repository uses a **feature-rich source format** that transforms into provider-specific formats. We chose "Option A" architecture: maintain full metadata in source files and downgrade for providers with limited support (like Cursor), rather than limiting everyone to the lowest common denominator.
### Why This Approach?
Different providers have different capabilities:
- **Claude Code, OpenCode**: Full metadata — args, user-invokable, allowed-tools, license, compatibility
- **Codex, Agents**: Args converted to `argument-hint` format
- **Gemini**: Minimal frontmatter, `{{arg}}` placeholders become `{{args}}`
- **Cursor, Kiro, Pi**: Basic frontmatter (name, description, license/compatibility)
By maintaining rich source files, we preserve maximum functionality where supported while still providing working (if simpler) versions for all providers.
## Source Format
### Skills (`source/skills/{name}/SKILL.md`)
```yaml
---
name: skill-name
description: What this skill provides
license: License info (optional)
compatibility: Environment requirements (optional)
---
Your skill instructions here...
```
**Frontmatter fields** (based on [Agent Skills spec](https://agentskills.io/specification)):
- `name` (required): Skill identifier (1-64 chars, lowercase/numbers/hyphens)
- `description` (required): What the skill provides (1-1024 chars)
- `user-invokable` (optional): Boolean — if `true`, the skill can be invoked as a slash command
- `args` (optional): Array of argument objects (for user-invokable skills)
- `name`: Argument identifier
- `description`: What it's for
- `required`: Boolean (defaults to false)
- `license` (optional): License/attribution info
- `compatibility` (optional): Environment requirements (1-500 chars)
- `metadata` (optional): Arbitrary key-value pairs
- `allowed-tools` (optional, experimental): Pre-approved tools list
**Body**: The skill instructions for the LLM.
## Building
### Prerequisites
- Bun (fast JavaScript runtime and package manager)
- No external dependencies required
### Commands
```bash
# Build all provider formats
bun run build
# Clean dist folder
bun run clean
# Rebuild from scratch
bun run rebuild
```
### What Gets Generated
```
source/ → dist/
skills/{name}/SKILL.md cursor/.cursor/skills/{name}/SKILL.md
claude-code/.claude/skills/{name}/SKILL.md
gemini/.gemini/skills/{name}/SKILL.md
codex/.codex/skills/{name}/SKILL.md
agents/.agents/skills/{name}/SKILL.md
kiro/.kiro/skills/{name}/SKILL.md
opencode/.opencode/skills/{name}/SKILL.md
pi/.pi/skills/{name}/SKILL.md
```
## Provider Transformations
All providers output skills to `dist/{provider}/.{config}/skills/{name}/SKILL.md` with reference files in subdirectories. They differ in frontmatter fields and argument handling.
### Cursor
- Output: `dist/cursor/.cursor/skills/{name}/SKILL.md`
- Frontmatter: name, description, license
- **Note**: Agent Skills require Cursor nightly channel
### Claude Code (Full Featured)
- Output: `dist/claude-code/.claude/skills/{name}/SKILL.md`
- Frontmatter: name, description, user-invokable, args, license, compatibility, metadata, allowed-tools
- Preserves `{{arg}}` placeholders in body
### OpenCode (Full Featured)
- Output: `dist/opencode/.opencode/skills/{name}/SKILL.md`
- Frontmatter: name, description, user-invokable, args, license, compatibility, metadata, allowed-tools
- Same format as Claude Code
### Gemini CLI
- Output: `dist/gemini/.gemini/skills/{name}/SKILL.md`
- Frontmatter: name, description
- For user-invokable skills: remaining `{{arg}}` placeholders become `{{args}}`
### Codex CLI
- Output: `dist/codex/.codex/skills/{name}/SKILL.md`
- Frontmatter: name, description, argument-hint, license
- For user-invokable skills: `{{argname}}``$ARGNAME` (uppercase)
### Agents (VS Code Copilot, Antigravity)
- Output: `dist/agents/.agents/skills/{name}/SKILL.md`
- Frontmatter: name, description, user-invokable, argument-hint
- Args converted to `argument-hint` format (e.g., `<target> [FORMAT=<value>]`)
### Kiro
- Output: `dist/kiro/.kiro/skills/{name}/SKILL.md`
- Frontmatter: name, description, license, compatibility, metadata
### Pi
- Output: `dist/pi/.pi/skills/{name}/SKILL.md`
- Frontmatter: name, description, license, compatibility, metadata
## Adding New Content
### 1. Create Source File
```bash
mkdir source/skills/myskill
touch source/skills/myskill/SKILL.md
```
Add frontmatter and content following the format above.
### 2. Build
```bash
bun run build
```
This generates all 8 provider formats automatically.
### 3. Test
Test with your provider of choice to ensure it works correctly. Remember that Cursor will have limited functionality.
### 4. Commit
Commit source files:
```bash
git add source/
git commit -m "Add [skill name]"
```
## Build System Details
The build system uses a modular architecture under `scripts/`:
- `build.js` — Main orchestrator
- `lib/utils.js` — Shared utilities (frontmatter parsing, file I/O, placeholder replacement)
- `lib/zip.js` — ZIP bundle generation
- `lib/transformers/*.js` — One file per provider (cursor, claude-code, gemini, codex, agents, kiro, opencode, pi)
### Key Functions
- `parseFrontmatter()`: Extracts YAML frontmatter and body
- `readSourceFiles()`: Reads all skill directories from `source/skills/`
- `replacePlaceholders()`: Substitutes `{{model}}`, `{{config_file}}`, etc. per provider
- `transformCursor()`: Basic frontmatter (name, description, license)
- `transformClaudeCode()`: Full metadata with args and allowed-tools
- `transformGemini()`: Minimal frontmatter, `{{arg}}``{{args}}`
- `transformCodex()`: Args → argument-hint, `{{arg}}``$ARGNAME`
- `transformAgents()`: Args → argument-hint, user-invokable flag
- `transformKiro()`: Basic frontmatter with license/compatibility/metadata
- `transformOpenCode()`: Full metadata (same as Claude Code)
- `transformPi()`: Basic frontmatter with license/compatibility/metadata
## Best Practices
### Skill Writing
1. **Focused scope**: One clear domain per skill
2. **Clear descriptions**: Make purpose obvious
3. **Clear instructions**: LLM should understand exactly what to do
4. **Include examples**: Where they clarify intent
5. **State constraints**: What NOT to do as clearly as what to do
6. **Test across providers**: Verify it works in multiple contexts
## Reference Documentation
- [Agent Skills Specification](https://agentskills.io/specification) - Open standard
- [Cursor Commands](https://cursor.com/docs/agent/chat/commands)
- [Cursor Rules](https://cursor.com/docs/context/rules)
- [Cursor Skills](https://cursor.com/docs/context/skills)
- [Claude Code Slash Commands](https://code.claude.com/docs/en/slash-commands)
- [Anthropic Skills (Claude Code)](https://github.com/anthropics/skills)
- [Gemini CLI Custom Commands](https://cloud.google.com/blog/topics/developers-practitioners/gemini-cli-custom-slash-commands)
- [Gemini CLI Skills](https://github.com/google-gemini/gemini-cli/blob/main/docs/cli/gemini-md.md)
- [Codex CLI Slash Commands](https://developers.openai.com/codex/guides/slash-commands#create-your-own-slash-commands-with-custom-prompts)
- [Codex CLI Skills](https://developers.openai.com/codex/skills/)
- [Pi Skills](https://github.com/badlogic/pi-mono/blob/main/packages/coding-agent/docs/skills.md)
## Repository Structure
```
impeccable/
├── source/ # Edit these! Source of truth
│ └── skills/ # Skill definitions
│ ├── frontend-design/
│ │ ├── SKILL.md
│ │ └── reference/*.md # Domain-specific references
│ ├── audit/SKILL.md
│ ├── polish/SKILL.md
│ └── ...
├── dist/ # Generated output (gitignored)
│ ├── cursor/
│ ├── claude-code/
│ ├── gemini/
│ ├── codex/
│ ├── agents/
│ ├── kiro/
│ ├── opencode/
│ └── pi/
├── scripts/
│ ├── build.js # Main orchestrator
│ └── lib/
│ ├── utils.js # Shared utilities
│ ├── zip.js # ZIP generation
│ └── transformers/ # One file per provider
│ ├── cursor.js
│ ├── claude-code.js
│ ├── gemini.js
│ ├── codex.js
│ ├── agents.js
│ ├── kiro.js
│ ├── opencode.js
│ └── pi.js
├── tests/ # Bun test suite
├── package.json # ESM project config
├── README.md # User documentation
├── DEVELOP.md # This file
└── .gitignore
```
## Troubleshooting
### Build fails with YAML parsing errors
- Check frontmatter indentation (YAML is indent-sensitive)
- Ensure `---` delimiters are on their own lines
- Verify colons have spaces after them (`key: value`)
### Output doesn't match expectations
- Check the transformer function for your provider in `scripts/lib/transformers/`
- Verify source file has correct frontmatter structure
- Run `bun run rebuild` to ensure clean build
### Provider doesn't recognize the files
- Check installation path for your provider
- Verify file naming matches provider requirements
- Consult provider's documentation (links above)
## Questions?
Open an issue or submit a PR!