Slice 4: graceful project handoff (pending switch + ack)
Add pending-switch coordination to internal/activity (RequestSwitch/PendingSwitch/AckSwitch/CancelSwitch); AckSwitch atomically sets the active project and records switch-completed with Claude's summary. New MCP tools get_pending_switch and ack_switch (request is user-only via HTTP). HTTP GET/POST/DELETE /api/switch. New <handoff-bar> component (ask/waiting/cancel/completed) over SSE; activity-feed reflects switch-completed. Test covers request->ack->clear. Verified live: request/waiting/cancel over SSE. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
@@ -395,18 +395,20 @@ obeys the safety rules (§1.4).
|
||||
When the user switches project/task in the app, it is a **request**, not an
|
||||
instant yank. The cooperative protocol:
|
||||
|
||||
1. **User** picks a new project/task in the app → the app records a
|
||||
**pending‑switch request** (target + optional note) and the UI shows
|
||||
"waiting for Claude to reach a good stopping point."
|
||||
1. **User** asks (in the app) for Claude to switch to a project →
|
||||
`POST /api/switch` records a **pending‑switch request** (target + optional
|
||||
note) and `<handoff-bar>` shows "waiting for Claude to reach a good stopping
|
||||
point." (The request is a **user‑only** action — there is no MCP tool to raise
|
||||
it; Claude fulfils requests, it doesn't create them.)
|
||||
2. **Claude** sees the pending request (it checks at its natural turn‑boundary
|
||||
checkpoints via `get_pending_switch`). It **finishes to a safe stopping
|
||||
point and preserves work** — never abandons uncommitted changes to switch;
|
||||
it completes the in‑flight step and commits/stashes as appropriate — then
|
||||
performs the switch (`set_active_project`, moving its working context to the
|
||||
new repo) and calls **`ack_switch`** with a short summary of where it left
|
||||
the previous project.
|
||||
3. **App** marks the request fulfilled and **notifies the user** over SSE
|
||||
("Claude switched to *ProjectB*; *ProjectA* left at: …"). The user proceeds.
|
||||
calls **`ack_switch`** with a short summary of where it left the previous
|
||||
project. `ack_switch` **atomically** makes the requested target the active
|
||||
project and clears the request.
|
||||
3. **App** records `switch-completed` and **notifies the user** over SSE
|
||||
("Claude switched to *ProjectB* — *left at: …*"). The user proceeds.
|
||||
|
||||
**Rule:** the switch is Claude‑completed at a checkpoint, not app‑forced. Losing
|
||||
or interrupting uncommitted work to satisfy a switch is a §1.4‑class violation.
|
||||
|
||||
Reference in New Issue
Block a user