|
| 1 | +# COVEN-GITHUB.md — Product Spec |
| 2 | + |
| 3 | +*coven-github: Coven-native GitHub App coding agent* |
| 4 | +*Authors: Cody 🦄 + Sage 🌿 · June 3, 2026* |
| 5 | + |
| 6 | +--- |
| 7 | + |
| 8 | +## Vision |
| 9 | + |
| 10 | +A GitHub App that turns any Coven-configured familiar into a first-class GitHub coding agent. Assign an issue to `@cody` (or any familiar bot user), and the familiar plans, edits, commits, and opens a pull request — with live oversight in CovenCave and no black-box model lock-in. |
| 11 | + |
| 12 | +--- |
| 13 | + |
| 14 | +## Problem |
| 15 | + |
| 16 | +Every existing GitHub coding agent is a closed system: |
| 17 | + |
| 18 | +- **GitHub Copilot Workspace** — GitHub's model, GitHub's context window, GitHub's behavior. No familiar identity, no persistent memory, no operator skills. Paid gate (Pro+ / Enterprise). |
| 19 | +- **Devin** — Full-VM agent, strong execution, but ~$500/month, proprietary, model-locked. |
| 20 | +- **OpenHands** — Open source, model-agnostic, GitHub integration exists — but no identity, no skills, no cross-session memory. |
| 21 | +- **Sweep AI** — Closest structural analogue (true GitHub App), but GPT-4-locked, no identity, effectively abandoned the GitHub-first path. |
| 22 | + |
| 23 | +**No competitor has:** persistent familiar identity + composable skill system + cross-session memory + BYOM + open source + self-hostable + owned oversight UI. |
| 24 | + |
| 25 | +That combination is unoccupied territory. Coven owns all five primitives already. |
| 26 | + |
| 27 | +--- |
| 28 | + |
| 29 | +## Architecture |
| 30 | + |
| 31 | +### Two-Layer Separation |
| 32 | + |
| 33 | +``` |
| 34 | +Layer 1 — GitHub ingress (coven-github) |
| 35 | + Webhooks · auth · event routing · Check Runs · PR lifecycle |
| 36 | +
|
| 37 | +Layer 2 — Execution quality (coven-code) |
| 38 | + Agent loop · model · tools · memory · skills · output |
| 39 | +``` |
| 40 | + |
| 41 | +Mixing these creates a monolith that is hard to test, deploy, and reason about. |
| 42 | +`coven-github` is a thin adapter. `coven-code` is the runtime. |
| 43 | + |
| 44 | +### Session Lifecycle |
| 45 | + |
| 46 | +``` |
| 47 | +1. Webhook arrives |
| 48 | + → validate HMAC signature (reject invalid) |
| 49 | + → parse event: repo, ref, issue body/diff, assignee/label/mention |
| 50 | +
|
| 51 | +2. Task enqueued |
| 52 | + → create GitHub Check Run (status: in_progress) |
| 53 | + → post "starting…" comment on issue |
| 54 | +
|
| 55 | +3. Worker dequeues |
| 56 | + → provision ephemeral workspace (tmp dir or container) |
| 57 | + → clone repo via installation access token |
| 58 | + → write session-brief.json: issue body, repo context, familiar config |
| 59 | +
|
| 60 | +4. coven-code session spawned |
| 61 | + → --headless --context session-brief.json --output result.json |
| 62 | + → familiar reads code, edits files, runs tests, commits |
| 63 | +
|
| 64 | +5. Progress streaming |
| 65 | + → coven-code emits structured events (file_changed, test_run, etc.) |
| 66 | + → worker updates Check Run annotations in real time |
| 67 | + → "Cody: 3/8 tests passing…" visible inline in GitHub UI |
| 68 | +
|
| 69 | +6. Completion |
| 70 | + → coven-code pushes branch via installation token |
| 71 | + → worker opens draft PR (body: familiar summary + session link) |
| 72 | + → Check Run updated: completed / success or failure |
| 73 | + → issue comment: "PR #42 opened — watch in Cave →" |
| 74 | +
|
| 75 | +7. Iteration |
| 76 | + → PR review comment "@cody fix the type error on line 42" |
| 77 | + → re-triggers step 3 with review context appended to brief |
| 78 | +``` |
| 79 | + |
| 80 | +### Infrastructure |
| 81 | + |
| 82 | +| Component | Role | |
| 83 | +|---|---| |
| 84 | +| **Webhook receiver** | HTTP server; validates HMAC; publishes to task queue | |
| 85 | +| **Task queue** | Decouples ingest from execution; Redis, SQS, or in-process (dev) | |
| 86 | +| **Worker pool** | Pulls tasks; manages coven-code processes; streams progress | |
| 87 | +| **Ephemeral workspaces** | Per-task isolated filesystems; Docker containers in production | |
| 88 | +| **GitHub API client** | Installation tokens (1hr TTL + refresh); Check Runs; PRs; comments | |
| 89 | +| **Config store** | Per-installation familiar config; model routing; secret storage | |
| 90 | + |
| 91 | +--- |
| 92 | + |
| 93 | +## coven-code Delta: Headless Mode |
| 94 | + |
| 95 | +The execution runtime needs the following additions to work as a GitHub App backend: |
| 96 | + |
| 97 | +### `--headless` flag |
| 98 | +- Disables ratatui TUI entirely |
| 99 | +- Routes all output to stdout (structured JSON events) + `--output <result.json>` |
| 100 | +- Exits 0 on success, non-0 on failure |
| 101 | + |
| 102 | +### `--context <session-brief.json>` |
| 103 | +Session brief schema: |
| 104 | +```json |
| 105 | +{ |
| 106 | + "trigger": "issue_assigned", |
| 107 | + "repo": { "owner": "OpenCoven", "name": "coven-code", "clone_url": "...", "default_branch": "main" }, |
| 108 | + "issue": { "number": 42, "title": "...", "body": "...", "labels": [] }, |
| 109 | + "familiar": { "id": "cody", "model": "anthropic/claude-sonnet-4-6", "skills": ["systematic-debugging"] }, |
| 110 | + "workspace": { "root": "/tmp/task-abc123" }, |
| 111 | + "auth": { "token": "<installation_access_token>" } |
| 112 | +} |
| 113 | +``` |
| 114 | + |
| 115 | +### `--output <result.json>` |
| 116 | +Result envelope schema: |
| 117 | +```json |
| 118 | +{ |
| 119 | + "status": "success" | "failure" | "partial", |
| 120 | + "branch": "cody/fix-issue-42", |
| 121 | + "commits": [{ "sha": "...", "message": "..." }], |
| 122 | + "files_changed": ["src/auth.rs"], |
| 123 | + "summary": "Fixed OAuth token refresh by adding a 60-second clock skew buffer.", |
| 124 | + "pr_body": "## Summary\n\n...", |
| 125 | + "events": [...], |
| 126 | + "exit_reason": null | "test_failure" | "ambiguous_spec" | "git_conflict" | "infra_error" |
| 127 | +} |
| 128 | +``` |
| 129 | + |
| 130 | +### Git auth forwarding |
| 131 | +- Accept `GIT_ASKPASS` or `GIT_TOKEN` env var for push operations |
| 132 | +- Use installation access token — not user credentials |
| 133 | + |
| 134 | +### Exit codes |
| 135 | +``` |
| 136 | +0 — success: commits made, result.json written |
| 137 | +1 — failure: agent gave up, result.json written with exit_reason |
| 138 | +2 — infra error: workspace, git, or tool failure (retry-safe) |
| 139 | +3 — ambiguous: agent needs clarification (posts comment, exits cleanly) |
| 140 | +``` |
| 141 | + |
| 142 | +--- |
| 143 | + |
| 144 | +## GitHub App Registration |
| 145 | + |
| 146 | +### Required Permissions |
| 147 | + |
| 148 | +| Permission | Level | |
| 149 | +|---|---| |
| 150 | +| Contents | Read + Write | |
| 151 | +| Issues | Read + Write | |
| 152 | +| Pull requests | Read + Write | |
| 153 | +| Checks | Write | |
| 154 | +| Metadata | Read (baseline) | |
| 155 | +| Workflows | Write (optional; needed if touching CI config) | |
| 156 | + |
| 157 | +### Webhook Events |
| 158 | + |
| 159 | +| Event | Use | |
| 160 | +|---|---| |
| 161 | +| `issues` → `assigned` | Primary task trigger | |
| 162 | +| `issue_comment` → `created` | `@mention` and iteration | |
| 163 | +| `pull_request_review_comment` → `created` | Review feedback iteration | |
| 164 | +| `check_suite` / `check_run` | CI awareness | |
| 165 | +| `push` | Branch tracking (optional) | |
| 166 | + |
| 167 | +### Bot User |
| 168 | + |
| 169 | +The GitHub App creates a bot user. Bot username configurable per installation. |
| 170 | +Default: `coven-cody[bot]`. Orgs can configure `@cody`, `@nova`, etc. via familiar mapping. |
| 171 | + |
| 172 | +--- |
| 173 | + |
| 174 | +## Familiar Identity in GitHub |
| 175 | + |
| 176 | +The PR body and issue comments are written in the familiar's voice: |
| 177 | + |
| 178 | +```markdown |
| 179 | +## Hey, I'm Cody 🦄 |
| 180 | + |
| 181 | +I looked at issue #42 and here's what I found: |
| 182 | + |
| 183 | +The OAuth token refresh path in `src/auth/refresh.rs` wasn't accounting for |
| 184 | +clock skew between the client and the auth server. I added a 60-second buffer\nto the expiry check. |
| 185 | + |
| 186 | +**Changed:** `src/auth/refresh.rs` (+12 / -3) |
| 187 | +**Tests:** 8/8 passing (added 2 regression cases) |
| 188 | + |
| 189 | +[Watch this session in CovenCave →](https://cave.opencoven.ai/sessions/abc123) |
| 190 | +``` |
| 191 | + |
| 192 | +The `pr_body` field in `result.json` is generated by the familiar — not a template. This is familiar voice, not boilerplate. |
| 193 | + |
| 194 | +--- |
| 195 | + |
| 196 | +## CovenCave Integration |
| 197 | + |
| 198 | +### Coven Board — `coven-github` Tasks |
| 199 | + |
| 200 | +A new task source in the Coven Board alongside manual sessions: |
| 201 | + |
| 202 | +``` |
| 203 | +Inbox | Running | Review | GitHub |
| 204 | +
|
| 205 | +GitHub tab shows: |
| 206 | + ● coven-code #42 — Fix OAuth refresh running 2m ago |
| 207 | + ↳ Cody · 3/8 tests passing · fix/issue-42 |
| 208 | + ● cast-codes #18 — Implement spell compiler review 18m ago |
| 209 | + ↳ Cody · PR #31 opened |
| 210 | + ● coven-cave #7 — Browser seam fix done 1h ago |
| 211 | + ↳ Cody · merged as #88 |
| 212 | +``` |
| 213 | + |
| 214 | +Click any row → open Cave session for live oversight. |
| 215 | + |
| 216 | +### Check Run Deep Link |
| 217 | + |
| 218 | +Every Check Run summary includes a `details_url` pointing to the Cave session: |
| 219 | +`https://cave.opencoven.ai/sessions/<id>` (or `localhost:3000/sessions/<id>` for self-hosted). |
| 220 | + |
| 221 | +--- |
| 222 | + |
| 223 | +## Sponsor / Premium Tier |
| 224 | + |
| 225 | +`coven-github` is open source and self-hostable. The hosted tier monetizes around managed infra and advanced orchestration. |
| 226 | + |
| 227 | +### Open Source (self-hosted) |
| 228 | +- Full GitHub App functionality |
| 229 | +- BYOM |
| 230 | +- Single familiar per installation |
| 231 | +- Local CovenCave oversight |
| 232 | +- Community support |
| 233 | + |
| 234 | +### Sponsor Tier (GitHub Sponsors) |
| 235 | +- **Small sponsor:** Early access + hosted worker credits (5 tasks/day) |
| 236 | +- **Medium sponsor:** 50 tasks/day + cloud familiar memory (cross-repo) |
| 237 | +- **Large sponsor / org:** Unlimited tasks + multi-familiar routing + dedicated worker + SLA |
| 238 | + |
| 239 | +### Hosted Premium (Enterprise) |
| 240 | +- Managed worker fleet (no infra to run) |
| 241 | +- Multi-familiar routing (Nova dispatches Cody vs security familiar vs ops familiar) |
| 242 | +- Cloud familiar memory — persistent cross-repo, cross-PR context |
| 243 | +- Organization-wide installation |
| 244 | +- Proactive PR review (familiar reviews incoming PRs unprompted) |
| 245 | +- Priority model credits / usage bundling |
| 246 | +- White-label bot username |
| 247 | + |
| 248 | +--- |
| 249 | + |
| 250 | +## Recovery Design (Sweep's Lesson) |
| 251 | + |
| 252 | +**80% of agent failures are infra, not reasoning.** Design for it from day one. |
| 253 | + |
| 254 | +| Failure class | Behavior | |
| 255 | +|---|---| |
| 256 | +| Git conflict | Agent posts comment: "I hit a conflict on `main` — can you rebase and re-trigger?" | |
| 257 | +| Test failure (fixable) | Agent iterates up to 3 times, then posts partial PR with test output | |
| 258 | +| Test failure (unknown root cause) | Posts comment with test output + what it tried; exits with `exit_reason: test_failure` | |
| 259 | +| Ambiguous spec | Posts clarifying question as issue comment; exits cleanly (code 3) | |
| 260 | +| Infra error (container, git, OOM) | Retries up to 2 times; marks Check Run `failure` with infra note | |
| 261 | +| Token expiry | Automatic refresh; transparent to agent session | |
| 262 | + |
| 263 | +All failures are visible in CovenCave with full session replay. |
| 264 | + |
| 265 | +--- |
| 266 | + |
| 267 | +## V1 Milestones |
| 268 | + |
| 269 | +### M1 — coven-code headless mode (~3 days) |
| 270 | +- `--headless`, `--context`, `--output` flags |
| 271 | +- `result.json` envelope |
| 272 | +- Git token forwarding |
| 273 | +- Exit code contract |
| 274 | +- Basic integration test: inject synthetic issue context → verify PR-shaped output |
| 275 | + |
| 276 | +### M2 — coven-github webhook service (~4 days) |
| 277 | +- GitHub App registration (manifest + private key handling) |
| 278 | +- Webhook receiver with HMAC validation |
| 279 | +- In-process task queue (Redis/SQS in production) |
| 280 | +- Worker: spawns coven-code, streams progress |
| 281 | +- Check Runs client: create / update / complete |
| 282 | +- Issue comment: start + PR link |
| 283 | + |
| 284 | +### M3 — PR lifecycle + iteration (~3 days) |
| 285 | +- Branch push via installation token |
| 286 | +- Draft PR opener with familiar-voice body |
| 287 | +- PR review comment re-trigger |
| 288 | +- `@cody` mention in issue comments |
| 289 | + |
| 290 | +### M4 — CovenCave GitHub tab (~2 days) |
| 291 | +- New task source in Coven Board |
| 292 | +- Check Run deep link → Cave session |
| 293 | +- Running/review/done states |
| 294 | + |
| 295 | +### M5 — Docs + self-hosting guide (~2 days) |
| 296 | +- `docs/self-hosting.md` |
| 297 | +- GitHub App registration walkthrough |
| 298 | +- `config/example.toml` |
| 299 | +- Sponsor tier landing copy |
| 300 | + |
| 301 | +**Total: ~2 weeks to a working V1 end-to-end.** |
| 302 | + |
| 303 | +--- |
| 304 | + |
| 305 | +## V2 Backlog |
| 306 | + |
| 307 | +- Multi-familiar routing (Nova dispatches based on issue labels / repo context) |
| 308 | +- Cross-repo familiar memory |
| 309 | +- Skill auto-detection from repo type (Rust → rust-expert skill, etc.) |
| 310 | +- Organization-wide installation |
| 311 | +- Proactive PR review (unprompted) |
| 312 | +- `coven-github` CLI: `coven-github assign --issue 42 --familiar cody` |
| 313 | +- Metrics dashboard in CovenCave (tasks completed, PR merge rate, avg time) |
| 314 | + |
| 315 | +--- |
| 316 | + |
| 317 | +## Open Questions |
| 318 | + |
| 319 | +1. **Bot username strategy** — single `coven-cody[bot]` app vs. per-org custom bot username (requires separate GitHub App per org)? |
| 320 | +2. **Container isolation** — Docker per task vs. Fly Machines vs. GitHub Actions ephemeral runners for the execution environment? |
| 321 | +3. **Memory persistence** — where does cross-PR familiar memory live in the hosted tier? Convex? Postgres? Coven's own storage? |
| 322 | +4. **Model billing** — does the operator bring their own API key, or does OpenCoven proxy model calls in the hosted tier? |
| 323 | + |
| 324 | +--- |
| 325 | + |
| 326 | +*Spec: Cody 🦄 + Sage 🌿 · June 3, 2026* |
0 commit comments