caliber-testing
Writes Vitest tests following project patterns: __tests__/ directories, vi.mock() for module…
Creates a new CLI command following the Commander.js pattern in src/commands/. Handles command registration in src/cli.ts, telemetry tracking via tracked() wrapper, and option parsing. Use when user says add command, new CLI command, create subcommand, or adds files to
$ npx -y skills add caliber-ai-org/ai-setup --skill adding-a-command --agent claude-codeHow it fires
How this skill gets triggered: by you, by Claude, or both.
/adding-a-commandContext preview
The summary Claude sees to decide when to auto-load this skill.
Creates a new CLI command following the Commander.js pattern in src/commands/. Handles command registration in src/cli.ts, telemetry tracking via tracked() wrapper, and option parsing. Use when user says add command, new CLI command, create subcommand, or adds files to
name: adding-a-command description: Creates a new CLI command following the Commander.js pattern in src/commands/. Handles command registration in src/cli.ts, telemetry tracking via tracked() wrapper, and option parsing. Use when user says add command, new CLI command, create subcommand, or adds files to src/commands/. Do NOT use for modifying existing commands or fixing bugs in existing commands. paths: - src/commands/**/*.ts - src/cli.ts
1. **Create the command file** at `src/commands/{commandName}.ts` with named async export.
2. **Handle errors consistently**: Wrap error-prone operations in try/catch. Distinguish between user errors and system errors:
3. **Import and register in src/cli.ts** in the correct location:
4. **Define options (if needed)**:
5. **Verify before proceeding**:
User says: "Add a command to show config status"
**Actions taken**: 1. Create src/commands/status.ts with statusCommand() export 2. Import and register in src/cli.ts with tracked() wrapper
**Result**: `caliber status` displays config status; `caliber status --json` outputs JSON.
Code example:
import chalk from 'chalk';
import { loadConfig } from '../llm/config.js';
export async function statusCommand(options?: { json?: boolean }) {
const config = loadConfig();
if (options?.json) {
console.log(JSON.stringify({ configured: !!config }, null, 2));
return;
}
console.log(chalk.bold('Status'));
console.log(` LLM: ${chalk.green(config?.provider || 'Not configured')}`);
}Registration in src/cli.ts:
import { statusCommand } from './commands/status.js';
program
.command('status')
.description('Show config status')
.option('--json', 'Output as JSON')
.action(tracked('status', statusCommand));---
User says: "Add a sources add subcommand"
**Actions taken**: 1. Create src/commands/sources.ts with sourcesAddCommand() export 2. Register under sources group with tracked('sources:add', ...)
**Result**: `caliber sources add ../lib` adds a source.
Code example:
export async function sourcesAddCommand(sourcePath: string) {
if (!fs.existsSync(sourcePath)) {
console.log(chalk.red(`Path not found: ${sourcePath}`));
throw new Error('__exit__');
}
const existing = loadSourcesConfig(process.cwd());
existing.push({ type: 'repo', path: sourcePath });
writeSourcesConfig(process.cwd(), existing);
console.log(chalk.green(`Added ${sourcePath}`));
}Registration:
const sources = program.command('sources');
sources
.command('add')
.argument('<path>', 'Path to add')
.action(tracked('sources:add', sourcesAddCommand));---
User says: "Add init with --agent flag supporting comma-separated values"
**Actions taken**: 1. Create parseAgentOption() parser in src/cli.ts 2. Create src/commands/init.ts with initCommand(options) 3. Register with custom parser
**Result**: `caliber init --agent claude,cursor` passes parsed array to handler.
Parser code:
function parseAgentOption(value: string) {
const agents = value.split(',').map(s => s.trim().toLowerCase(Continuously sync your AI setups with one command. Codebase tailor suited agent skills, MCPs and config files for Claude Code, Cursor, and Codex.
Repo: caliber-ai-org/ai-setup
Writes Vitest tests following project patterns: __tests__/ directories, vi.mock() for module…
Discovers and installs community skills from the public registry. Use when the user mentions…
Adds a new LLM provider implementing LLMProvider interface with call() and stream() methods.…
Saves user instructions as persistent learnings for future sessions. Use when the user says…
Add a new deterministic scoring check in src/scoring/checks/ that evaluates config quality.…
Sets up Caliber for automatic AI agent context sync. Installs pre-commit hooks so CLAUDE.md,…