The Two-Layer Architecture (from blog)
PR #1004 implements git-notes and orphan as separate backends. But the blog post describes them working together as a two-layer architecture:
Layer 1: Git Notes (commit-scoped "why" annotations)
- Per-agent namespaces: refs/notes/squad/{agent}
- Thin JSON attached to specific commits
- Invisible in PR diffs
- Agents write here during sessions
Layer 2: Orphan Branch (permanent state store)
- decisions.md, agent histories, logs
- The "team diary" — full state
- Ralph promotes important notes here after PR merge
Ralph bridges the layers:
- After PR merges, scans notes with promote_to_permanent: true
- Promotes to decisions.md on orphan branch
- Notes on rejected PRs are silently ignored (desired behavior)
Why this matters
The blog describes 3 scenarios that break naive solutions:
- Rejected feature — decision on a rejected PR should NOT be promoted
- Universal truth — routing change on a rejected PR SHOULD survive
- Valuable failure — research worth keeping even when feature is rejected
The two-layer architecture handles all three via promote_to_permanent and archive_on_close flags on notes. Single-backend approaches can't distinguish these cases.
What to implement
Reference
The Two-Layer Architecture (from blog)
PR #1004 implements
git-notesandorphanas separate backends. But the blog post describes them working together as a two-layer architecture:Why this matters
The blog describes 3 scenarios that break naive solutions:
The two-layer architecture handles all three via
promote_to_permanentandarchive_on_closeflags on notes. Single-backend approaches can't distinguish these cases.What to implement
stateBackend: "two-layer"option in config.jsonpromote_to_permanent: true, append to orphan branch decisions.mdarchive_on_close: true, archive to orphan branchReference