9.9 KiB
AGENTS.md
Canonical agent instructions for this repository. This file is the source of truth for how AI coding agents — Claude Code, GitHub Copilot CLI, OpenAI Codex CLI, Google Gemini CLI, Kiro CLI, Cursor, etc. — should work here. Tool-specific files like CLAUDE.md should point to this file and add only tool-specific items on top.
When this template is copied into a new project, AGENTS.md travels with it as the portable convention doc. Replace the <PLACEHOLDER> tokens below with your project's values.
Working style — read before you write
Default to more reading, less guessing. The cost of reading one more file upstream or downstream of a change is almost always paid back by the constraint you'd have missed. Fast, confident-looking code that turns out to be wrong is a net loss here.
- Read the relevant plan first. If a change lands under
dev/plans/<YYWWD>-<feature-slug>/, skim the plan's PRD / design / tasks before editing. The plan exists precisely because the obvious fix is often wrong. - Verify assumptions with tools, not memory. Before claiming "function X does Y" or "field Z exists," run Grep/Read. File paths, line numbers, and type signatures drift — check the current state. Memory entries can be stale; treat them as hints, not facts.
- Prefer a small Read over a big Edit. If a change feels obvious after 30 seconds, that's usually a sign you haven't read enough yet. One more file's context almost always surfaces a constraint you'd have missed.
- Trace lifetimes, threads, and invariants explicitly. Bugs about where data lives and which thread touches it pass code review and crash in the wild. State the ownership / threading / invariant assumption (in your head or a comment) before editing.
- Say what you don't know. If the user asks for a fix and the right approach depends on a fact you haven't verified (protocol quirk, library behavior, tool version), call it out and verify before implementing. Don't paper over uncertainty with plausible-looking code.
Thoroughness and speed aren't at odds — agents can parallelize research (see CLAUDE.md for Claude-specific sub-agent guidance) to do more reading per wall-clock second.
Layout
The following directory conventions are load-bearing. Generic names (<PROJECT_NAME>, <TEST_COMMAND>) are placeholder tokens you should replace with your project's actual values when using this template.
./— working tree of<PROJECT_NAME>. Primary language:<PRIMARY_LANGUAGE>. Test command:<TEST_COMMAND>../dev/— agentic / developer working artifacts. Tracked (not excluded). Seedev/README.md. Subdirs:dev/plans/<YYWWD>-<feature-slug>/,dev/plans/archive/,dev/notes/,dev/research/,dev/tools/../.claude/— Claude Code harness directory..claude/skills/— skill packs (codex, copilot, gemini, kiro + spec-driven workflow skills). See "Skills index" below..claude/commands/— Claude Code slash commands (e.g./repo-cleanup)..claude/settings.json— team-shared hook configuration..claude/settings.local.json— personal overrides (gitignored by default).
./AGENTS.md(this file) — canonical agent instructions../CLAUDE.md— Claude Code entrypoint; points here and adds Claude-specific items.
Skills index
Skills under .claude/skills/ are self-contained instruction packs. Claude Code loads them as /skill-name slash commands. Other tools can reference them as documentation.
Spec-driven workflow (chains through a feature's lifecycle):
/create-prd— draft a Product Requirements Document with EARS-syntax acceptance criteria, peer-reviewed by codex./create-design— optional technical blueprint translating the PRD (architecture, data flow, interfaces, security, tests)./generate-tasks— two-phase decomposition (parent tasks → sub-tasks on "Go") with traceability tags./process-task-list— execute the task list one sub-task at a time; codex review at parent-task completion and pre-PR.
All four use a fresh codex session per stage (see codex skill's "Cross-stage continuation" section for the rationale).
Peer-reviewer CLIs (driven by the spec-driven skills or invoked ad-hoc):
codex— OpenAI Codex CLI.codex exec --sandbox read-only+resume --lastfor iterative review. Session UUIDs logged indev/plans/<YYWWD>-<feature-slug>/codex-sessions.md.copilot— GitHub Copilot CLI (agentic, not the oldergh copilot suggest). Sessions incopilot-sessions.md.gemini— Google Gemini CLI. Index-based session resume (not UUID). Sessions ingemini-sessions.md.kiro— Kiro CLI (AWS, rebranded Amazon Q Developer lineage). Sessions inkiro-sessions.md.
Separate per-tool session-log files keep lineage unambiguous when mixing reviewers on one feature.
dev/ workflow
- Plan directories use a
YYWWD-chronological prefix.YY= two-digit ISO year,WW= ISO week,D= ISO day-of-week (1=Mon …7=Sun). Compute withdate +%y%V%uat creation time — don't backdate. Example:dev/plans/26167-pane-focus-sync/. - Plan directory contents (produced by the spec-driven skills):
prd.md, optionaldesign.md,tasks.md, and per-tool*-sessions.mdlogs. - Feature branches mirror the plan slug:
feature/<YYWWD>-<feature-slug>.jj bookmark liststays in the same chronological order asls dev/plans/. - Archive completed plans by moving them under
dev/plans/archive/so the active list stays scannable. - In-code traceability tags:
// spec:<feature-slug>/<ref>where<ref>isR<n.m>(PRD requirement),D§<n>(design section), orT<n.m>(task). Use the bare slug (noYYWWDprefix) — shorter forrg 'spec:<slug>'. - Lint a plan directory with
planctl lintbefore spawning a codex review or opening a PR. It catches tag-syntax errors, orphan / uncovered references, missing close-out files, and EARS-keyword deviations — all classes codex historically flagged — in single-digit milliseconds per plan. Run from inside the plan dir or pass the path explicitly; classification codes (orphan-requirement,tag-unclosed,ears-violation, etc.) are listed inplanctl --help. Install once withgo install forgejo.zerova.net/sid/template-jj/cmd/planctl@latest— spec lives atdev/plans/26172-planctl/.
See dev/README.md for the full workflow.
Version control
This template uses jj colocated with git. Prefer jj for authoring and rewriting local history; use git only for remote operations and the occasional git status sanity check.
jj new main -m "scratch" # start a change on top of main
jj describe / jj squash / etc. # normal jj workflow
jj git push # pushes to origin
Commit rules:
- Never include
Co-Authored-Bylines in commit messages. Agent-generated commits go under the user's identity unchanged. - Conventional commit prefixes:
feat:,fix:,refactor:,test:,docs:,chore:,dev:(fordev/-only changes). - Lowercase imperative subject, keep under ~70 chars. Body explains the why — the diff shows the what.
- Never skip hooks (
--no-verify) unless the user explicitly requests it. - Never push to upstream trees containing
dev/content. If<UPSTREAM_BLOCKED_PATTERN>is set in your environment, the pre-push guard atdev/tools/pre-push-guard.shwill refuse pushes ofdev/paths to a matching remote. Install via./dev/tools/install-hooks.sh.
Multi-agent coordination
When multiple agents are active on the same repository simultaneously (the default when using this template's jj-commitd session-commit daemon):
- Use
jj workspace addfor true parallel isolation. Each workspace gets its own@pointer; a branch switch in one session never flips the working tree underneath another. Setup:jj workspace add --name <role> ../<project>-<role>. Seedev/README.md→ "Primary isolation: jj workspaces". - Each session commits its own tracked files under a per-session commit message (
wip(claude:<session_id>): <files>) and bookmark (wip/claude-<session_id>set at session end). History stays attributable even when agents interleave. - Use the session inventory on start. The daemon's
session-startresponse lists every other active session and its tracked files. Log it and check for overlap with files your session plans to edit — if another session holds them, coordinate with the user before writing. Seedocs/jj-commitd.md→ "Session inventory consumption". JJ_AGENT_FEATURElabels your work (planned). ExportingJJ_AGENT_FEATURE=<feature-name>before starting will label commits aswip(<feature>:<session_id>)and set afeat/<feature>bookmark at session end — human-readable names instead of bare UUIDs. Not yet implemented; seedev/README.md→ "Planned: JJ_AGENT_FEATURE".- Cross-session file conflicts are logged. Grep
/tmp/jj-commitd-<repo_id>.logforconflictif edits seem to disappear. - Don't assume the working copy is yours. Before writing,
jj statusand confirm@is the change you expect. If a pre-flight step is relevant to your skill, run it every invocation — don't rely on session state.
Placeholder tokens (for template users)
When adopting this template, replace:
<PROJECT_NAME>— your project's short name.<PRIMARY_LANGUAGE>— Zig, Rust, Python, Go, TypeScript, etc.<TEST_COMMAND>— the canonical test command (zig build test,pytest,npm test,go test ./..., etc.).<SOURCE_ROOT>— the main source directory (src/,lib/,pkg/, etc.).<UPSTREAM_BLOCKED_PATTERN>— if you're maintaining a fork, the substring the pre-push guard matches against the upstream's remote URL (e.g.upstream-org/repo). Leave unset if your repo has no upstream to protect against.
rg -n '<[A-Z_]+>' AGENTS.md CLAUDE.md dev/ .claude/skills/ finds every placeholder token in one pass.