Problem
When Codev is initialized in a project that already had a Claude Code session running (claude binary already alive somewhere on the machine), the main architect launched by codev adopt (or by Tower's launchInstance on first workspace touch) does not spawn a fresh session — it appears to hijack / attach to an existing, unrelated Claude Code session as its starting point.
Reproduction:
- Open a project directory in VS Code (or any terminal). Do NOT initialize Codev in it.
- In some other context (a different terminal, a different project's session), Claude Code has an active session (persisted state on disk, potentially a running process).
- In the target project, run
codev adopt (or trigger auto-adopt via VS Code opening the folder with codev.autoStartTower).
- Tower's
launchInstance fires, creates the main architect terminal.
- Observe: the main architect's opening state is not a fresh session. It picks up prior conversation context / role state from an unrelated Claude Code session, effectively hijacking it.
Impact
- Architect boots in a context inherited from a different project — protocols, mental model, and any prior "you are the main architect for X" instructions bleed in.
- New workspaces don't start clean. The workspace's
codev/state/main.md (per-architect notebook) and porch project state are correctly scoped, but the conversation state inside the Claude terminal is contaminated.
- Undermines the trust that "add-architect / adopt → fresh, purpose-scoped architect."
Root cause hypothesis
Two candidate sites in the launch path:
packages/codev/src/agent-farm/servers/tower-instances.ts:392 — launchInstance. Spawns the main architect PTY. Investigate whether the launch options passed to shellper / Claude include a --resume, --continue, or session-id argument that reaches for the most-recent Claude session on the machine.
packages/codev/src/agent-farm/utils/harness.ts — the Claude harness config. Look for buildResume / sessionId behavior that defaults to "most recent" when no explicit id is provided.
Specifically: Claude Code CLI has a --resume flag that reattaches to the most-recent conversation on the machine by default. If the launch command builds a --resume argument without validating that the session is scoped to this workspace, it'll grab whichever conversation Claude last touched globally.
Note the pattern documented at packages/codev/src/agent-farm/utils/harness.ts:87: "no stored session id yet (codex/gemini omit it → no stale-jsonl crash-loop)." Something equivalent for Claude on fresh workspaces would prevent the hijack.
Fix sketch
Two surgical changes:
-
Detect fresh vs resume-worthy state at launch time. For a workspace that has never registered an architect terminal before, launch Claude WITHOUT --resume (or with an explicit "new session" invocation). Only resume when there's a scoped architect row in global.db.architects with a persisted session id owned by this workspace.
-
Verify session ownership before attach. If a session id is passed, cross-check that the session file's project-scope tag matches this workspace path. Refuse to attach to a session that references a different project directory.
Scope
packages/codev/src/agent-farm/servers/tower-instances.ts (launchInstance, main architect spawn)
packages/codev/src/agent-farm/utils/harness.ts (Claude harness resume logic)
- Coverage: fresh
codev adopt in a new workspace + concurrent Claude session elsewhere → main architect boots clean
Related
Problem
When Codev is initialized in a project that already had a Claude Code session running (
claudebinary already alive somewhere on the machine), the main architect launched bycodev adopt(or by Tower'slaunchInstanceon first workspace touch) does not spawn a fresh session — it appears to hijack / attach to an existing, unrelated Claude Code session as its starting point.Reproduction:
codev adopt(or trigger auto-adopt via VS Code opening the folder withcodev.autoStartTower).launchInstancefires, creates the main architect terminal.Impact
codev/state/main.md(per-architect notebook) and porch project state are correctly scoped, but the conversation state inside the Claude terminal is contaminated.Root cause hypothesis
Two candidate sites in the launch path:
packages/codev/src/agent-farm/servers/tower-instances.ts:392—launchInstance. Spawns the main architect PTY. Investigate whether the launch options passed to shellper / Claude include a--resume,--continue, or session-id argument that reaches for the most-recent Claude session on the machine.packages/codev/src/agent-farm/utils/harness.ts— the Claude harness config. Look forbuildResume/sessionIdbehavior that defaults to "most recent" when no explicit id is provided.Specifically: Claude Code CLI has a
--resumeflag that reattaches to the most-recent conversation on the machine by default. If the launch command builds a--resumeargument without validating that the session is scoped to this workspace, it'll grab whichever conversation Claude last touched globally.Note the pattern documented at
packages/codev/src/agent-farm/utils/harness.ts:87: "no stored session id yet (codex/gemini omit it → no stale-jsonl crash-loop)." Something equivalent for Claude on fresh workspaces would prevent the hijack.Fix sketch
Two surgical changes:
Detect fresh vs resume-worthy state at launch time. For a workspace that has never registered an architect terminal before, launch Claude WITHOUT
--resume(or with an explicit "new session" invocation). Only resume when there's a scoped architect row inglobal.db.architectswith a persisted session id owned by this workspace.Verify session ownership before attach. If a session id is passed, cross-check that the session file's project-scope tag matches this workspace path. Refuse to attach to a session that references a different project directory.
Scope
packages/codev/src/agent-farm/servers/tower-instances.ts(launchInstance, main architect spawn)packages/codev/src/agent-farm/utils/harness.ts(Claude harness resume logic)codev adoptin a new workspace + concurrent Claude session elsewhere → main architect boots cleanRelated
packages/codev/src/agent-farm/utils/harness.ts:87— existing comment about codex/gemini omitting session id "to avoid stale-jsonl crash-loop." Same concern class; different remediation for Claude.~/.agent-farm/global.db. Any per-workspace hydration check must key onworkspace_path.