Problem
A drive-by contributor opening anvil.go (760+ lines, all public API + lifecycle + builder) has no map of how the pieces fit. CLAUDE.md captures conventions but doesn't explain what's where.
Proposal
Add docs/architecture.md — one page, no fluff. Sections:
- One-paragraph mental model — anvil is a subprocess; we own its lifecycle and expose a Go-typed RPC client.
- Lifecycle diagram (ASCII):
Build() → Start() → [ready] → Stop()/Close(). Where the cancel context lives. Where sync.Once kicks in.
- File map — what each
.go file is responsible for (mirror the table in CLAUDE.md but with one-sentence summaries).
- RPC method anatomy — annotated copy of the canonical wrapper showing
rpcCalls.Add, CallContext, error wrap, log.
- Test strategy — shared-anvil pattern, when to use
setupTestAnvil instead, the unit-test httptest pattern.
- Where to add new things — RPC wrapper →
anvil.go + tests; new builder option → builder section + validate(); new helper → helpers.go.
Acceptance criteria
- One page, scannable in 60 seconds.
- Linked from CONTRIBUTING.md and CLAUDE.md.
- No diagrams that need rendering — ASCII or none.
Problem
A drive-by contributor opening
anvil.go(760+ lines, all public API + lifecycle + builder) has no map of how the pieces fit. CLAUDE.md captures conventions but doesn't explain what's where.Proposal
Add
docs/architecture.md— one page, no fluff. Sections:Build()→Start()→[ready]→Stop()/Close(). Where the cancel context lives. Wheresync.Oncekicks in..gofile is responsible for (mirror the table in CLAUDE.md but with one-sentence summaries).rpcCalls.Add,CallContext, error wrap, log.setupTestAnvilinstead, the unit-test httptest pattern.anvil.go+ tests; new builder option → builder section +validate(); new helper →helpers.go.Acceptance criteria