Guidance for AI coding agents working on this repository. This is the single
source of truth — CLAUDE.md imports it.
The product is spec'd; changes that contradict a spec need a founder-visible issue first, not code. Canonical set:
docs/architecture.md— how squads works under the hood (files, context cascade, roles, feedback loop)docs/philosophy.md— what this product is and refuses to bedocs/agent-contract.md— the typed contract every agent runs underdocs/governance.md— permission and approval modeltemplates/seed/skills/squads-cli/SKILL.md— the operating loop as taught to every scaffolded project
squads-cli is a CLI orchestrator for autonomous AI agent teams. It organizes agents into squads (domain-aligned teams), manages their context and memory, and dispatches them via native AI CLIs (claude, gemini, etc.).
The CLI is open source. Agents are the primary consumers — after squads run dispatches an agent, it calls CLI commands to read context, persist memory, and coordinate with other agents.
src/
├── cli.ts # All command registrations (Commander.js, lazy imports)
├── commands/ # One file per command — start here for any command change
├── lib/ # Shared logic (parsing, context, memory, git, providers)
templates/ # Files generated by `squads init`
test/ # Unit + E2E tests (vitest)
Key files by concern:
| Concern | File |
|---|---|
| Squad/agent discovery | src/lib/squad-parser.ts |
| Context injection | src/lib/run-context.ts |
| Agent execution | src/commands/run.ts, src/lib/execution-engine.ts |
| Multi-agent conversation | src/lib/conversation.ts, src/lib/workflow.ts |
| Provider CLIs | src/lib/llm-clis.ts (integration), src/lib/providers.ts (registry + pricing) |
| Memory read/write | src/lib/memory.ts |
| Git / GitHub | src/lib/git.ts, src/lib/github.ts (gh CLI + bot identity) |
| Observability | src/lib/observability.ts, src/lib/telemetry.ts |
| Terminal output | src/lib/terminal.ts |
| Command registration | src/cli.ts |
npm install
npm run build # tsup → dist/ — required before committing, must pass
npm run typecheck # tsc — build does NOT typecheck; run this for behavior/type changes
npm test # vitest, 1900+ tests, all must pass
npm run lint # ESLint
npm link # test globally as `squads`npx vitest run test/commands/run.test.ts # Single fileE2E tests in test/e2e/ run actual CLI commands against temp directories.
- Create
src/commands/<name>.tsexporting an async function - Register in
src/cli.tswith a lazy dynamic import — commands load only when invoked:.action(async (name, options) => { const { createCommand } = await import('./commands/create.js'); return createCommand(name, options); });
- Add
--jsonflag for machine output - Add tests in
test/commands/<name>.test.ts
Use the removedCommand() pattern in cli.ts — never silently delete:
program.command('old-name', { hidden: true })
.description('[removed]')
.action(removedCommand('old-name', 'Use: squads replacement'));All filesystem discovery goes through squad-parser.ts. Never hardcode paths to .agents/ — use findSquadsDir(), findProjectRoot(), loadSquad(), listSquads().
- TypeScript strict mode. No
anytypes. - Lazy imports in cli.ts. Commands are loaded only when invoked.
- Terminal output via
terminal.ts. UsewriteLine(),colors,bold— not rawconsole.log. --jsonon every command. Agents parse CLI output programmatically.- No new dependencies without explicit approval.
- No hardcoded repos, orgs, or file paths. Everything discovered at runtime.
- Graceful degradation. Missing files, unavailable APIs — show local data, never crash on missing optional data.
- Conventional Commits.
feat:,fix:,docs:,chore:. - Feature branches for non-trivial changes. PRs target
develop. SeeRELEASING.mdfor the release flow.
- Don't add dependencies (especially heavy ones) without discussion
- Don't use
console.login command implementations - Don't hardcode GitHub as the only git provider
- Don't break
--jsonoutput formats (agents depend on them) - Don't skip the build step —
npm run buildis the quality gate (andtypecheckfor type changes)