Repository navigation
S3: passive notifications — question.asked and turn-idle on followed sessions #1788
Description
Important
Problem — Attach today is active: you must be watching the panel to know a followed session needs you. The extension host already holds a live SSE connection to the hub (sseClient) — it sees every event and tells no one.
Approach — This is S3 of #1785: watch the extension host's existing event stream for question.asked and turn-idle on followed sessions (follow = a session this client has opened or pinned — no new follow UI in this slice) and raise VS Code-native notifications. The panel taps you; you stop watching the panel.
Scope — in: event watching on the existing sseClient, notification raising, follow-set definition (opened/pinned), dedupe/cooldown. · out: any new follow-management UI, panel-side rendering, engine changes.
Acceptance Criteria
- A
question.askedon a followed session raises a native notification (with the session name and question header) while the panel is unfocused; activating it focuses the panel on that session. - A turn-idle on a followed session that was busy raises a "finished" notification; a turn that ends within a short window of starting does not notify (no flash spam).
- The same question never notifies twice (dedupe by request id across reconnects — the stream replays its gap, and a replayed question.asked must not re-notify).
- Notifications only fire for followed sessions; an unfollowed session's events pass silently.
- No notification when the panel has that session open and focused (you're already there).
- The slice adds no new connections: it consumes the existing sseClient stream.
Testing Decisions
Extension suite (vitest — the package's own runner, never bun) for the watcher and notification policy; a headless extension-host assertion for the live question.asked → notification path where the probe harness allows it.
Key Decisions
- Follow = opened or pinned by this client, derived from existing state — no new follow surface.
- Dedupe must survive reconnect replay (the stream replays cursors; the notification layer keys on request id, not arrival).
Constraints & Invariants
- The sseClient connection is shared infrastructure: the watcher observes, never mutates the stream or its cursor handling.
- No engine deploys; no panel deploy required (extension-only surface).
Prior Art
- The extension host's existing SSE connection (sseClient) and its dead-man's-switch contract (fix(ops): the upstream dead-man's switch — wedged merged-group upstreams recycle, and silence becomes observable #1758).
- The question lifecycle events (asked/replied) and the session status event (the Server: session status has no ordering key + multiple emitters → stale idle while agent runs #1636 seq guard means replayed statuses are already order-safe).
- Seamless attach: live session status, a question inbox, and passive notifications — the UX layer over the fleet's existing foundations #1785's S2 inbox — the panel-side counterpart; S3's notifications and S2's inbox must agree on what counts as pending (same shared rows).
Source
Part of #1785. Composes after S2; shares no files with S1 or S2 (extension package vs app bundle).
Notes
VS Code notification APIs are mockable in the extension test harness — the watcher's policy (who, when, how often) is the tested surface; the OS-level toast is not.
Activity
Merge S3 passive notifications (#1788) into amico/issue-1785-seamless…
aarontrowbridge commentedon Oct 13, 2026
Merged into amico/issue-1785-seamless-attach (merge 0eb3957). Director-verified: extension suite 328 files / 5414 passed / 0 failed (+14 tests vs baseline), typecheck delta zero (1 known pre-existing). Dedupe keys on request id — replay-safe across reconnect gap; the watcher observes the shared sseClient stream only.