# CLAUDE.md This file provides guidance to Claude Code (claude.ai/code) when working with code in this repository. Read this first, then follow the pointers below — do not start writing code before reading `docs/development-plan.md` and the current Unit's coverage references in `docs/sdd/`. ## What this is **graphlemon** is a Level 5 autonomous "lights-out software factory": a two-layer Organizer Agent architecture (Org Graph = fixed Planner→Coder→Validator; Work Graph = dynamic per-task execution graph) that drives real software development end-to-end, backed entirely by Claude Code ACP (`claude -p` non-interactive calls) — there is no Hermes CLI execution backend in this project (decision, 2026-07-29, see `docs/sdd/05-实施约束与依赖.md` §5.3). The authoritative spec is `docs/sdd/` (00-06 + `docs/sdd/sdd-mvcp-contract.json`), generated via the MVCP (Model/View/Controller/Process) methodology from `docs/graphlemon_architecture.md`. **Do not treat `graphlemon_architecture.md` as the spec to implement against** — it's the PRD- equivalent input that produced the SDD. When they conflict, the SDD wins (it's newer and more detailed); if a conflict looks unresolved, stop and ask rather than picking one silently. ## Status: all 43 planned Units (U-001~U-043, PH0~PH5) are implemented and committed `docs/development-plan.md` and `docs/sdd/unit_matrix.json` describe the plan as it read at inception (2026-07-29) — they were **not** kept updated with "done" checkmarks as work landed, so don't treat their prose as a live status board. `git log --oneline` is the actual record: every Unit from U-001 through U-043 has a matching commit, plus many `U-0XX fix:`/`U-0XX follow-up:` commits for bugs found during real (not mocked) runs, plus a long tail of `graphlemon: for task ` / `graphlemon: auto-commit uncommitted changes for ` / `graphlemon: merge ` commits — those are graphlemon **actually self-hosting**: running its own Planner→Coder→Validator loop against its own repo (`target_folder_path` == this checkout, `src/paths.is_self_target()`), with the Deploy Supervisor (`supervisor/`) staging, health-checking, and cutting over its own code changes. PH5 (self-modification / auto-rollback) is real and running, not future work — see "Two things named Supervisor" below and `supervisor/self_hosting_e2e.py`. When a `development-plan.md` line and the actual code disagree about what's done, trust the code and `git log`, and — if it matters to the task at hand — flag the doc as stale rather than silently trusting either source. `development-plan.md`'s per-Unit "实现补充"/"真实 bug" notes (inline, added after-the-fact) are still valuable: they're a real incident log of bugs found during self-hosting runs and how they were fixed (e.g. worktree commits being silently dropped, `memory: project` writes landing on the wrong checkout) — read them before touching `supervisor/isolation/`, `src/work_node_run.py`, or anything worktree-related. ## Where to start 1. Read `docs/development-plan.md` for the Phase → Sub-phase → Unit breakdown and the *design* rationale behind each piece — but see Status above before trusting any "done"/"depends_on" framing as current. `docs/sdd/unit_matrix.json` is its machine-readable mirror (also static). 2. `docs/sdd/06-验收与测试锚点.md` has REQ-01 through REQ-15, the acceptance anchors every Unit's Done criterion cites. REQ-15 (PH5, Deploy Supervisor blue-green + auto-rollback) was added 2026-07-30 after the original REQ-01~14 set. 3. For any specific behavior, prefer reading the actual module in `src/`/`supervisor/`/`agents/` over the plan doc — the plan doc records intent at write-time and known deviations, the code is truth. ## Commands Two independent `unittest discover` roots — there is no single top-level `discover` that covers both (deliberately: `supervisor/` was added later as PH5 landed, see `development-plan.md`'s U-036 note): ```bash # graphlemon's own backend/schema/agent-orchestration code (560+ tests as of PH5) python3 -m unittest discover -s src # Deploy Supervisor + the isolate/diff/apply library it depends on # (this also picks up supervisor/isolation/test_*.py — no separate invocation needed) python3 -m unittest discover -s supervisor -p "test_*.py" # single test python3 -m unittest src.test_work_graph_execute.SomeTestClass.test_method ``` Both suites skip real-`claude`-subprocess tests by default (`skip_unless_env`, `src/test_support.py`) — those need `RUN_REAL_AGENT_E2E=1` and real API spend, e.g.: ```bash RUN_REAL_AGENT_E2E=1 python3 -m unittest src.test_agent_e2e ``` `supervisor/self_hosting_e2e.py`'s own real end-to-end scenario (`run_self_hosting_closed_loop`, the literal 9-step self-development-feasibility.md walkthrough) is gated the same way in `supervisor/test_self_hosting_e2e.py` — do not invoke it casually; it does a real self-targeted Planner→Coder→Validator→stage→cutover→monitor run against **this repo**. No build step, no lint config, no package manager — pure stdlib Python, nothing to install. ```bash # A-1 spike (already validated 2026-07-29, kept for reference/re-running) ./spikes/a1-dynamic-workflows/run-spike.sh /path/to/some/git/repo # local console (U-007/U-008): backend serves the API, frontend is static no-build HTML/JS python3 -m src.backend_server --port 8000 # default --port 0 means OS-assigned (fine for tests, not for browsing) ``` ## Hard constraints (do not relitigate these — they're settled decisions) - **Execution backend**: Claude Code ACP only (`claude -p ... --output-format json --json-schema --permission-mode auto`, no `--bare`, no `--dangerously-skip-permissions`). See 05 §5.3, §5.3.1, §5.4. One documented gotcha: `--agent` + `--json-schema` together silently drop `structured_output` — see 05 §5.4.1.1 and `src/work_graph_plan.py`'s ```` ```json ```` fence parsing workaround. - **Implementation language**: graphlemon's own backend/frontend/Deploy Supervisor are **pure stdlib Python** — no Flask/FastAPI/Express/Node.js, no npm build step. This mirrors the predecessor project graphloop's convention. See 05 §5.7. (This constraint is on graphlemon's own implementation only — it does NOT apply to the code graphlemon generates for target projects, which follows whatever stack that target project uses.) - **Testing**: stdlib `unittest` only, no pytest/fixtures. Mock the `subprocess`/`claude -p` boundary in normal tests; real end-to-end tests that actually shell out to `claude` are gated behind `RUN_REAL_AGENT_E2E=1` (`src/test_support.py:skip_unless_env`, mirrors graphloop's precedent) — reuse that helper, don't invent a per-file variant. - **Isolation**: parallel coding nodes must use `git_worktree_ref` (`src/work_node_run.py`). If `target_folder_path` is graphlemon's own repo (self-hosting/self-modification), worktree is **unconditionally mandatory** even for serial single-node changes — see 05 §5.8, `src/paths.is_self_target()`. Worktree checkouts live at `.graphlemon-worktrees//` **inside** the main repo's working tree while a node runs (gitignored — never let `git add -A` on `repo_path` pick one up mid-run). Before touching this code, read the three `U-013` incident notes in `development-plan.md` (uncommitted worktree changes silently dropped on merge, `memory: project` writes landing on the main checkout instead of the worktree, and the pathspec-vs-gitignore conflict that fixing the second one introduced) — `work_node_run.ensure_worktree_committed()` is the fix for all three; don't re-solve the same problem a fourth way. ## Two things named "Supervisor" — do not confuse them 1. **"Supervisor(调度子 Agent)"** — an in-process monitoring node inside the Coder Work Graph (architecture doc, existing concept). Watches Work Node execution, triggers reflection/ rescheduling. Part of the Graph Engine itself. 2. **"Deploy Supervisor"** (`supervisor/`) — an independent OS process (`python3 -m supervisor.deploy_supervisor`), entirely outside the Graph Engine, that handles blue-green deployment and automatic rollback when graphlemon modifies its own code. Fully implemented (U-034~U-043): `deploy_stage.py` (stage a candidate), `deploy_health_check.py` (poll for startup readiness, not one-shot — see U-038 fix), `deploy_cutover.py`, `deploy_monitor.py`, `deploy_rollback.py`. Fail-closed, never-auto-restart philosophy adapted (not imported) from graphloop's `hermes_watchdog.py`. See `docs/done/supervisor-auto-rollback-design.md` for the full design and the disambiguation note at the top of that file. These are unrelated components that happen to share a root word in casual English. Identifiers for #2 are always prefixed `c_deploy_supervisor_*` / `deploy_health_signal` — never abbreviate to just "supervisor" in code or docs. ## Prior art worth reading, not worth copying wholesale `/Users/yibo/Documents/lemonAI/graphloop` is an earlier, unmaintained attempt at this same architecture — substantially implemented (two-layer graph, isolated workspace, change manifest, selective apply, fan-in/fan-out, real Claude-based Planner/Worker/Reviewer agents) but its own Phase 10 self-evolution attempt stalled with concrete documented failures (a worker writing files outside its isolated workspace, a 300s timeout, a stale-PID recovery incident). Its `CLAUDE.md` is worth reading for architecture patterns; its `hermes_watchdog.py`/`phase10_controller.py` are worth reading for the "fail-closed, deterministic, never-auto-restart" supervision philosophy (graphlemon's Deploy Supervisor deliberately extends this into auto-rollback rather than just auto-halt — see `docs/done/supervisor-design-comparison.md` for why). Do not import graphloop code directly; anything worth reusing has already been copied and adapted into this repo (`supervisor/isolation/`, adapted verbatim per the U-036 note in `development-plan.md`). ## Repo layout - `docs/` — architecture doc (`graphlemon_architecture.md`), SDD (`docs/sdd/`, authoritative), development plan, and gap-analysis all live at the top level as living/actively-read documents (see Status above for how stale the plan/unit-matrix "done" framing is relative to the real code). Point-in-time material is split into three subdirectories by role, not chronology: `docs/done/` (design/decision docs whose conclusions have been fully absorbed into the SDD — e.g. the Deploy Supervisor design chain — kept for the reasoning trail, not because they're still authoritative), `docs/todo/` (requirements/design docs for work not yet implemented — BRD/PRD-level requirements docs and, once confirmed, SDD-level design docs, same two-stage split the Planner itself uses), `docs/reference/` (external source material — articles, course notes — plus graphlemon's own "how does this compare to our architecture" notes on each one). When adding a new doc, pick by role (has its conclusion shipped into the SDD? → done; still pending confirmation/implementation? → todo; is it someone else's writing you're archiving? → reference), not by putting everything loose in `docs/`. - `docs/wireframes/` — static no-build HTML prototypes for the PH3 console views (`v_*.html`), referenced per-page from `docs/sdd/02-V-界面与交互.md` §2.1-2.13; DOM/class names map 1:1 to that doc's field lists. - `skills/` — the Skill library (architecture doc §7.3): one directory per skill (`skills//SKILL.md` + optional `references/`), migrated/adapted from the Hermes profiles (§9's role mapping) and referenced by name from each Org Agent's `.claude/agents/*.md` `skills:` frontmatter list (`src/agent_profile.py::FRONTMATTER`, the canonical source of that list — edit it there, not by hand-editing the deployed `.claude/agents/*.md`). - `.claude/workflows/` — auto-generated, not hand-authored: real Dynamic Workflow scripts written by `src/work_graph_execute.py::write_workflow_script()`/`src/work_graph_orchestrate.py` (one script per Work Node execution) and by `e2e_pipeline.py`'s PRD-consistency check. Version- controlled because it's inside the target repo (self-target case: this repo), but treat the contents as execution artifacts, not source you maintain by hand. - `src/` — graphlemon's own backend: `schema.py` (17-table SQLite schema — the original 01-M 15 entities plus PH5's `deployment`/`deploy_health_signal`), `backend_server.py` (stdlib `http.server` HTTP API + WebSocket-ish log/event streaming, no third-party deps), the Org Graph layer (`org_node_trigger.py`, `org_node_lifecycle.py`, `org_loop_route.py`, `org_level_loop.py`), the Work Graph layer (`work_graph_plan.py`, `work_graph_execute.py`, `work_graph_orchestrate.py`, `work_node_run.py`), root-cause tracing (`root_cause_trace.py`), skills (`skill_update.py`, `skill_query.py`), budget/scheduling (`budget_guardrail.py`, `scheduler.py`), and `paths.py` (graphlemon's own runtime home — `~/.graphlemon` by default, override via `GRAPHLEMON_HOME`, deliberately outside this repo checkout so logs/db never enter this repo's own git history). **This is not the same kind of `src/` a target project has in its own repo** — a target project's own `src/` is its pre-existing source tree; graphlemon doesn't create or restructure it (05 §5.7, architecture doc §13.2). Each `src/x.py` has a same-directory `src/test_x.py` (and sometimes `src/test_x_e2e.py` for the gated real-agent variant) — that pairing is the repo convention, keep it when adding modules. - `supervisor/` — Deploy Supervisor process + its isolation library (`supervisor/isolation/`: `isolated_workspace.py`, `change_manifest.py`, `selective_apply.py`, `workspace_security.py`, adapted from graphloop). `supervisor/self_hosting_e2e.py` is the acceptance-scenario glue that wires Graph Engine scheduling + Deploy Supervisor into one real self-targeted run. - `agents/{coder,planner,validator}/SOUL.md` — original Hermes-profile identity docs, migrated 2026-07-31 (A-2 assumption, "部分成立" — Coder's needed real rewriting to drop a hardcoded Feishu API token and a `--dangerously-skip-permissions` self-invocation; Planner/Validator were near-verbatim). These are the source-of-truth prose; `.claude/agents/*.md` is the actual Claude-Code-discoverable wrapper (frontmatter: `skills:`/`memory: project`/`tools:`/`model:`) that Claude Code loads — if you change agent behavior, both need to move together, and the `.claude/agents/*.md` frontmatter comment block records exactly what changed between them. - `frontend/` — the PH3 console: static `index.html`/`app.js`/`style.css`, no build step, no npm. - `spikes/` — one-off validation spikes (`a1-dynamic-workflows/`, confirmed 2026-07-29). - `.claude/agent-memory/{coder,planner,validator}/` — per-agent `memory: project` files, tracked in git on purpose (architecture doc §8 decision: memory must leave a git trail, not be silently mutable local state). - `.graphlemon/runs//` — real Artifacts (brd/prd/sdd/benchmark/code_diff/test_report) from actual self-hosting runs against this repo. `.graphlemon-worktrees/` (gitignored, see Isolation above) is the transient per-node worktree checkout directory, not persistent state.