diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-1-dependency-baseline.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-1-dependency-baseline.md new file mode 100644 index 0000000..4ee7046 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-1-dependency-baseline.md @@ -0,0 +1,66 @@ +# Phase 1: Pi Dependency Baseline Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Move the project to the tested Pi/TUI `0.84.3` baseline without changing product behavior or UI. + +**Architecture:** Update only the three Pi development packages and the generated lockfile. Keep wildcard peer dependencies so the published extension remains compatible with its host. Make compiler-driven compatibility edits only if `0.84.3` requires them. + +**Tech Stack:** TypeScript, pnpm, Vitest, Biome, `@earendil-works/pi-ai@0.84.3`, `@earendil-works/pi-coding-agent@0.84.3`, `@earendil-works/pi-tui@0.84.3`. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** None. + +**Usable result:** The unchanged extension builds, tests, and packages against Pi `0.84.3`; README states Pi `0.84.3+`. + +## Constraints + +- Do not change commands, schemas, settings, rendering, or interaction behavior. +- Leave `peerDependencies` as `"*"`; update only the three Pi `devDependencies`. +- Do not add pi-status or any other dependency. +- Limit source edits to errors proven by the `0.84.3` typecheck or tests. + +### Task 1: Update and verify the dependency baseline + +**Files:** + +- Modify: `package.json` +- Modify: `pnpm-lock.yaml` +- Modify: `README.md` +- Modify only if compilation requires it: the exact source/test call site reported by `pnpm typecheck` + +- [ ] **Step 1: Record the baseline.** + + Run `pnpm check` before editing. Expected: the current suite passes; if it does not, record the pre-existing failure and stop rather than folding an unrelated fix into this phase. + +- [ ] **Step 2: Update only the Pi development packages.** + + Set these exact values in `package.json`: + + ```json + "@earendil-works/pi-ai": "^0.84.3", + "@earendil-works/pi-coding-agent": "^0.84.3", + "@earendil-works/pi-tui": "^0.84.3" + ``` + + Leave TypeScript, Vitest, Biome, TypeBox, engines, and all peer dependencies unchanged. Run `pnpm install --lockfile-only` to regenerate `pnpm-lock.yaml`. + +- [ ] **Step 3: Document the minimum tested host.** + + In `README.md`, update the Pi prerequisite/compatibility text to say `0.84.3+`. Do not document dashboard behavior yet. + +- [ ] **Step 4: Prove compatibility.** + + Run `pnpm check`. Expected: lint, `tsc --noEmit`, and all Vitest tests pass. If the compiler identifies a Pi API change, make the smallest call-site adaptation, add or update the nearest focused test, and rerun the failing command before the full check. + +- [ ] **Step 5: Verify package and scope.** + + Run `pnpm run pack:dry-run`, `git diff --check`, and `git diff -- package.json pnpm-lock.yaml README.md`. Expected: the package dry-run succeeds; only the three versions, their lockfile graph, and minimum-version documentation change unless Step 4 proved a required compatibility edit. + +- [ ] **Step 6: Commit the atomic result.** + + ```bash + git add package.json pnpm-lock.yaml README.md + git commit -m "chore: update pi dependencies to 0.84.3" + ``` diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-2-chain-input-repair.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-2-chain-input-repair.md new file mode 100644 index 0000000..24a69db --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-2-chain-input-repair.md @@ -0,0 +1,49 @@ +# Phase 2: Chain Input Repair Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Make `/run-chain` and `/chain` previews respond to modern CSI-u/Kitty keyboard input and prevent failed or cancelled previews from launching a chain. + +**Architecture:** Replace raw byte comparisons in `ChainClarifyComponent` with Pi/TUI `matchesKey()` and native `Input`, forward focus through `Focusable`, and gate preview execution to interactive TUI mode. Preserve the current preview appearance; dashboard styling starts in Phase 3. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 1 dependency baseline. + +**Usable result:** `/run-chain` works in modern terminals, remains scriptable outside TUI mode, and never launches after preview rejection, cancellation, or UI failure. + +## Constraints + +- Preserve `/run-chain`, `/chain`, `--yes`, `--bg`, schemas, and `ChainClarifyResult`. +- Show preview only when `ctx.mode === "tui" && !bg && !yes`. +- Do not introduce dashboard primitives or visual changes in this phase. +- Every new input and failure branch needs a focused regression. + +### Task 1: Reproduce modern input failures + +**Files:** `tests/chain-clarify.test.ts` + +- [ ] Add failing tests that send `"\x1b[13u"` for Enter, `"\x1b[106u"` for `j`, and `"\x1b[98u"` for `b`. Assert Enter confirms, `j` moves selection, and `b` returns the background action. Run `pnpm vitest run tests/chain-clarify.test.ts`; expected: the new cases fail against raw string comparisons. + +### Task 2: Repair input and focus at the boundary + +**Files:** `src/tui/chain-clarify.ts`, `tests/chain-clarify.test.ts` + +- [ ] Make `ChainClarifyComponent` implement `Component, Focusable`; replace the hand-rolled text buffer with Pi/TUI `Input`; expose `focused` and forward it to the input. +- [ ] Use `matchesKey(data, Key.*)` for navigation, Enter, Escape, and editing shortcuts; ignore `isKeyRelease(data)`. Retain printable-key behavior through native `Input` and preserve the existing `ChainClarifyResult` variants. +- [ ] Run `pnpm vitest run tests/chain-clarify.test.ts`. Expected: legacy and CSI-u cases pass, focus reaches the native input, and key-release events do not act twice. + +### Task 3: Gate previews and fail closed + +**Files:** `src/core/slash-chain.ts`, `tests/slash-chain.test.ts`, `tests/core/chain-clarify-integration.test.ts` + +- [ ] Add failing tests for non-TUI invocation, `--yes`, `--bg`, cancelled previews, and rejected `ctx.ui.custom` promises for both `/chain` and `/run-chain`. +- [ ] Centralize the preview condition as `ctx.mode === "tui" && !bg && !yes`. On cancellation or rejection, emit a visible `pi-subagent-result` error and return before spawning any agent. Non-TUI, `--yes`, and `--bg` paths bypass the preview according to existing semantics. +- [ ] Run `pnpm vitest run tests/slash-chain.test.ts tests/core/chain-clarify-integration.test.ts`. Expected: every bypass and failure path has an explicit no-spawn assertion. + +### Task 4: Verify and commit + +- [ ] Run `pnpm check` and `git diff --check`. Manually run `/run-chain` in a CSI-u/Kitty-capable terminal and confirm arrows/`j`/`k`, editing, Escape, reopen, Enter, and `b` work. +- [ ] Commit with `git add src/tui/chain-clarify.ts src/core/slash-chain.ts tests/chain-clarify.test.ts tests/slash-chain.test.ts tests/core/chain-clarify-integration.test.ts && git commit -m "fix: support modern chain preview input"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-3-dashboard-foundation.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-3-dashboard-foundation.md new file mode 100644 index 0000000..5c06919 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-3-dashboard-foundation.md @@ -0,0 +1,59 @@ +# Phase 3: Dashboard Foundation Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Introduce one local dashboard renderer and use it for the chain preview, establishing the visual system without changing other surfaces. + +**Architecture:** A dependency-free `dashboard-style.ts` owns overlay sizing, ANSI-safe frame width, selected-row viewport fitting, and the small-terminal fallback. The chain preview is the first consumer. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 2 chain input repair. + +**Usable result:** The chain preview has a responsive pi-status-inspired frame and viewport while retaining all repaired interactions. + +## Constraints + +- Use only Pi's active theme; add no palettes, settings, config, pi-status dependency, or shared package. +- Overlay options are centered, `width: "92%"`, `maxHeight: "85%"`. +- Preserve chain behavior and readonly parallel steps. +- ANSI-aware width/truncation must use the TUI utilities already available in Pi/TUI. + +### Task 1: Specify the renderer with failing tests + +**Files:** Create `tests/dashboard-style.test.ts` + +- [ ] Add exact tests for: a frame rendered at width `24`; `dashboardContentWidth(24) === 18`; a selected row scrolled into view with a stable offset; and `renderDashboardTooSmall(30, 3, theme)` containing `Esc`. Run `pnpm vitest run tests/dashboard-style.test.ts`; expected: module-not-found failure. + +### Task 2: Add the minimal shared renderer + +**Files:** Create `src/tui/dashboard-style.ts` + +- [ ] Export exactly: + + ```ts + export const DASHBOARD_MAX_HEIGHT_RATIO = 0.85; + export const DASHBOARD_OVERLAY_OPTIONS: OverlayOptions; + export const MIN_DASHBOARD_FRAME_WIDTH = 7; + export function dashboardContentWidth(width: number): number; + export function renderDashboardFrame(lines: readonly string[], width: number, theme: Theme): string[]; + export function fitDashboardViewport(lines: readonly string[], selectedLine: number | undefined, height: number, offset: number): { lines: string[]; offset: number }; + export function renderDashboardTooSmall(width: number, height: number, theme: Theme): string[]; + ``` + +- [ ] Use horizontal padding `2`, heavy frame glyphs `┏ ┓ ┗ ┛ ━ ┃`, and `{ anchor: "center", width: "92%", maxHeight: "85%" }`. Clamp every width/height calculation; keep the selected line visible without unnecessary offset jumps. +- [ ] Run `pnpm vitest run tests/dashboard-style.test.ts`; expected: all exact-width, viewport, and narrow-terminal tests pass. + +### Task 3: Apply it only to chain preview + +**Files:** `src/tui/chain-clarify.ts`, `tests/chain-clarify.test.ts`, `tests/core/chain-clarify-integration.test.ts` + +- [ ] Add failing render tests for the heavy frame, visible `▸` selection marker, footer hints, narrow fallback, and selected-row scrolling. +- [ ] Render the preview through the shared frame and viewport. Keep parallel steps readonly and retain native input/focus behavior from Phase 2. +- [ ] Run the three focused test files, then `pnpm check` and `git diff --check`. + +### Task 4: Commit the atomic result + +- [ ] Commit with `git add src/tui/dashboard-style.ts src/tui/chain-clarify.ts tests/dashboard-style.test.ts tests/chain-clarify.test.ts tests/core/chain-clarify-integration.test.ts && git commit -m "feat: add dashboard chain preview"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-4-live-widgets.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-4-live-widgets.md new file mode 100644 index 0000000..fc2a083 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-4-live-widgets.md @@ -0,0 +1,48 @@ +# Phase 4: Live Widgets Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Restyle the persistent AgentWidget and ChainWidget with the dashboard hierarchy while preserving placement and lifecycle. + +**Architecture:** Keep each widget's existing state and update hooks. Change only rendering to compact themed headings, status rows, activity continuations, and summaries; reuse existing truncation and active-theme roles. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 3 dashboard foundation. + +**Usable result:** Running agents and chains display a consistent compact dashboard treatment above the editor. + +## Constraints + +- AgentWidget and ChainWidget remain above the editor. +- Do not change manager state, timers, task ordering, completion behavior, or settings. +- Use the active Pi theme and existing helpers; do not wrap persistent widgets in overlay frames. + +### Task 1: Lock the intended output + +**Files:** `tests/agent-widget.test.ts`, `tests/chain-widget.test.ts` + +- [ ] Replace/add focused snapshots or line assertions for this hierarchy: + + ```text + ╭─ ✦ AGENTS + │ ● worker description · metadata + │ ⎿ activity + ╰─ running/queued summary + ``` + + Apply the analogous `CHAINS` heading and chain metadata. Cover narrow truncation and empty/terminal states already supported. Run both test files; expected: visual assertions fail before implementation. + +### Task 2: Restyle without changing lifecycle + +**Files:** `src/tui/agent-widget.ts`, `src/tui/chain-widget.ts` + +- [ ] Replace only render composition: themed `✦` headings, semantic status dot/icon, one primary row, indented `⎿` activity, and compact summary. Preserve existing constructors, subscriptions, invalidation, data selection, and placement calls. +- [ ] Use ANSI-safe truncation already present in the repository/Pi/TUI. Do not import pi-status or create another rendering abstraction. + +### Task 3: Verify and commit + +- [ ] Run `pnpm vitest run tests/agent-widget.test.ts tests/chain-widget.test.ts`, then `pnpm check` and `git diff --check`. Expected: behavior tests and new render assertions pass. +- [ ] Commit with `git add src/tui/agent-widget.ts src/tui/chain-widget.ts tests/agent-widget.test.ts tests/chain-widget.test.ts && git commit -m "feat: restyle live agent and chain widgets"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-5-agents-menu.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-5-agents-menu.md new file mode 100644 index 0000000..f3a4473 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-5-agents-menu.md @@ -0,0 +1,41 @@ +# Phase 5: Agents Menu Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Migrate `/agents` list and detail menus to responsive framed dashboard overlays while preserving native editing dialogs. + +**Architecture:** Reuse the shared overlay options, frame, and viewport around existing menu state. Keep multi-step creation and full markdown editing on Pi's native input/editor components. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 4 live widgets. + +**Usable result:** `/agents` is readable and scrollable on normal and small terminals, with all create/edit/delete actions unchanged. + +## Constraints + +- Preserve `/agents`, agent definitions, validation, settings formats, and action semantics. +- Native input/editor dialogs remain native and receive focus. +- Center overlays at `92%` width and `85%` maximum height. + +### Task 1: Add failing menu regressions + +**Files:** `tests/agents-menu.test.ts` + +- [ ] Add assertions for heavy framed list/detail views, visible selected row, footer key hints, selected-row-aware scrolling, `30x3` fallback, and `DASHBOARD_OVERLAY_OPTIONS` passed to the custom UI. +- [ ] Retain/add interaction tests for navigation, create, edit, delete confirmation, Escape, and focus transfer into native input/editor dialogs. Run `pnpm vitest run tests/agents-menu.test.ts`; expected: only new layout assertions fail. + +### Task 2: Apply shared layout + +**Files:** `src/tui/agents-menu.ts` + +- [ ] Render list and detail contents with `renderDashboardFrame`; calculate inner height and use `fitDashboardViewport` so selection stays visible. +- [ ] Use `renderDashboardTooSmall` below the minimum dimensions and a clear `▸` selection marker plus compact footer hints. +- [ ] Pass `DASHBOARD_OVERLAY_OPTIONS` to the `/agents` custom UI. Leave the creation wizard and full markdown editor implementations intact; explicitly forward focus whenever the active child is focusable. + +### Task 3: Verify and commit + +- [ ] Run `pnpm vitest run tests/agents-menu.test.ts`, then `pnpm check` and `git diff --check`. Manually open `/agents`, scroll, create/cancel an agent, and open/cancel markdown editing. +- [ ] Commit with `git add src/tui/agents-menu.ts tests/agents-menu.test.ts && git commit -m "feat: migrate agents menu to dashboard layout"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-6-inline-renderers.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-6-inline-renderers.md new file mode 100644 index 0000000..e2a16fa --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-6-inline-renderers.md @@ -0,0 +1,46 @@ +# Phase 6: Inline Renderers Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Give subagent calls/results, completion notifications, watchdog warnings, and intercom messages one compact status-and-metadata hierarchy. + +**Architecture:** Add two private formatting helpers in the existing render module and reuse them from existing inline render entry points. Preserve the native message shell, custom message types, payloads, and detail toggles. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 5 agents menu. + +**Usable result:** Every inline pi-subagents message is visually consistent without changing its contract or interaction. + +## Constraints + +- Preserve tool call/result data, custom message types, expanded details, watchdog logic, and intercom delivery. +- Use active-theme semantic roles; no palettes or new public abstraction. +- Keep helpers private and local because there is only one renderer implementation. + +### Task 1: Specify consistent inline output + +**Files:** `tests/render.test.ts`, `tests/watchdog-render.test.ts` + +- [ ] Add focused assertions for running/success/error subagent calls and results, collapsed/expanded metadata, completion notification, watchdog warning, and intercom message. Assert subject/status hierarchy and stable metadata separators, not terminal color escape values. +- [ ] Run `pnpm vitest run tests/render.test.ts tests/watchdog-render.test.ts`; expected: new presentation assertions fail. + +### Task 2: Add the smallest shared formatting + +**Files:** `src/tui/render.ts`, `src/index.ts` + +- [ ] Add private helpers with these signatures: + + ```ts + function statusHeader(icon: string, subject: string, status: string): string; + function metadataLine(parts: readonly string[]): string; + ``` + +- [ ] Use them for subagent tool call/result rendering, completion messages, watchdog warnings, and intercom messages. Filter absent metadata parts before joining; retain existing native shells, payload parsing, detail expansion, and theme application. + +### Task 3: Verify and commit + +- [ ] Run `pnpm vitest run tests/render.test.ts tests/watchdog-render.test.ts`, then `pnpm check` and `git diff --check`. +- [ ] Commit with `git add src/tui/render.ts src/index.ts tests/render.test.ts tests/watchdog-render.test.ts && git commit -m "feat: unify inline subagent status rendering"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-7-fleet-list.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-7-fleet-list.md new file mode 100644 index 0000000..d57acd9 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-7-fleet-list.md @@ -0,0 +1,40 @@ +# Phase 7: Fleet List Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Restyle FleetList and align its viewer overlay sizing without changing keyboard capture or agent activation. + +**Architecture:** Keep the below-editor fleet as an unboxed compact list; use shared overlay sizing only when it opens the conversation viewer. Preserve the current roster and activation state machine. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 6 inline renderers. + +**Usable result:** Background-agent navigation matches the dashboard language and still opens the correct conversation reliably. + +## Constraints + +- FleetList remains below the editor and displays five rows. +- Preserve input capture, key-release handling, right-aligned metadata, roster filtering, activation, and cleanup. +- Do not put the persistent fleet inside a box. + +### Task 1: Add failing fleet regressions + +**Files:** `tests/fleet-list.test.ts` + +- [ ] Assert an unboxed `✦ Agents` heading, `▸` selected row, dim `•` unselected rows, dashboard footer hints, five-row viewport, right-aligned metadata, and shared `92%`/`85%` viewer overlay options. +- [ ] Retain/add behavior assertions for CSI-u and legacy navigation, key-release suppression, correct agent activation, roster changes, and cleanup. Run the file; expected: new visual/overlay assertions fail. + +### Task 2: Restyle the existing component + +**Files:** `src/tui/fleet-list.ts` + +- [ ] Change render composition only: add the heading, markers, compact metadata, and footer; keep existing five-row viewport and ANSI-safe width calculations. +- [ ] When activating a row, open the conversation viewer with `DASHBOARD_OVERLAY_OPTIONS`. Do not move focus or input handling into a new controller. + +### Task 3: Verify and commit + +- [ ] Run `pnpm vitest run tests/fleet-list.test.ts`, then `pnpm check` and `git diff --check`. Manually start a background agent, navigate the fleet, open it, close it, and confirm editor input is restored. +- [ ] Commit with `git add src/tui/fleet-list.ts tests/fleet-list.test.ts && git commit -m "feat: restyle background agent fleet"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-8-conversation-viewer.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-8-conversation-viewer.md new file mode 100644 index 0000000..57ed8ad --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-8-conversation-viewer.md @@ -0,0 +1,41 @@ +# Phase 8: Conversation Viewer Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Migrate the conversation viewer and composer to the shared framed dashboard layout while preserving live control of background agents. + +**Architecture:** Frame the existing viewer, raise its viewport allocation from `70%` to `85%`, and forward focus to the native composer. Keep subscriptions, steering, stop actions, and scrolling in the existing component. + +**Tech Stack:** TypeScript, Pi/TUI `0.84.3`, Vitest. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phase 7 fleet list. + +**Usable result:** A responsive, focus-correct conversation overlay can inspect, steer, and stop background agents. + +## Constraints + +- Preserve message rendering, live subscription updates, scrolling, steer submission, stop, Escape, and cleanup. +- Use shared centered `92%` width/`85%` max-height options. +- Reuse Pi's native input for the composer; do not build a custom editor. + +### Task 1: Add failing viewer regressions + +**Files:** `tests/conversation-viewer.test.ts` + +- [ ] Add assertions for heavy frame, header/status hierarchy, `85%` viewport constant, footer hints, narrow-terminal fallback, scroll bounds, and composer visibility. +- [ ] Add/retain behavior tests for focus forwarding, CSI-u and legacy keys, key releases, live subscription updates, steering submit, stop action, Escape, and disposal. Run the file; expected: new layout/focus assertions fail. + +### Task 2: Apply the frame and focus contract + +**Files:** `src/tui/conversation-viewer.ts` + +- [ ] Change `VIEWPORT_HEIGHT_PCT` from `0.7` to `DASHBOARD_MAX_HEIGHT_RATIO` (`0.85`). Render header, messages, composer, and footer through the shared frame and small-terminal fallback. +- [ ] Implement/retain `Focusable`; forward `focused` to the native composer when it is active. Fit the message viewport without changing chronological ordering or subscription behavior. +- [ ] Keep steer and stop routing exactly as-is; visual buttons/hints must call the existing actions. + +### Task 3: Verify and commit + +- [ ] Run `pnpm vitest run tests/conversation-viewer.test.ts tests/fleet-list.test.ts`, then `pnpm check` and `git diff --check`. Manually inspect a live background agent, scroll, steer, stop, and close at small and normal sizes. +- [ ] Commit with `git add src/tui/conversation-viewer.ts tests/conversation-viewer.test.ts && git commit -m "feat: migrate conversation viewer to dashboard layout"`. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-9-release-verification.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-9-release-verification.md new file mode 100644 index 0000000..8fb46c2 --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui-phase-9-release-verification.md @@ -0,0 +1,53 @@ +# Phase 9: Release Verification Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Document the completed migration and prove the cumulative result is releasable. + +**Architecture:** No product architecture changes. Update user-facing docs, run the full automated pipeline, audit scope/contracts, and execute the end-to-end terminal checklist against the integrated phases. + +**Tech Stack:** TypeScript, pnpm, Biome, Vitest, Pi/TUI `0.84.3`. + +**Parent plan:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md` + +**Prerequisite:** Phases 1–8 complete. + +**Usable result:** The repaired and migrated extension is documented, packaged, and verified across automated and manual interaction paths. + +## Constraints + +- This phase fixes only defects introduced or exposed by the migration; unrelated cleanup remains out of scope. +- Preserve commands, flags, schemas, tool contracts, agent definitions, settings, and surface placements. +- Confirm there is no pi-status runtime dependency, copied palette/config system, or cross-extension read. + +### Task 1: Finish user-facing documentation + +**Files:** `README.md`, `CHANGELOG.md` + +- [ ] In `README.md`, retain the Phase 1 `0.84.3+` prerequisite and document modern `/run-chain` preview keys, `--yes`, `--bg`, dashboard overlays, `/agents`, FleetList, and conversation steering at the level users need. +- [ ] In `CHANGELOG.md`, add one entry covering the CSI-u input repair, safe preview cancellation/failure, Pi `0.84.3` baseline, and dashboard UI migration. Do not claim unrelated changes. + +### Task 2: Run the complete automated gate + +- [ ] Run `pnpm check`. Expected: Biome lint, `tsc --noEmit`, and the complete Vitest suite pass. +- [ ] Run `pnpm run pack:dry-run`. Expected: the package is produced as a dry run and contains the required `src`, `agents`, `chains`, license, changelog, and README files. +- [ ] Run `git diff --check`. Expected: no whitespace errors. + +### Task 3: Audit contracts and scope + +- [ ] Review `git diff --stat` and `git diff`. Confirm changes are limited to the parent plan's named source/tests/docs/dependency files. +- [ ] Search the diff for changes to `/run-chain`, `/chain`, `/agents`, `--yes`, `--bg`, schemas, tool contracts, agent definition formats, settings, and widget placement. Expected: public contracts and placements are unchanged. +- [ ] Search dependencies/imports for `pi-status`. Expected: no runtime dependency or cross-extension import/read exists. + +### Task 4: Run the terminal acceptance checklist + +- [ ] In a modern CSI-u/Kitty-capable terminal, run `/run-chain implement -- inspect this repository`; verify arrows and `j`/`k`, editing, cancel/reopen, Enter confirmation, and first-agent launch. +- [ ] Press `b` in preview; verify the chain backgrounds, an ID is shown, and ChainWidget updates. +- [ ] Run with `--yes`; verify preview is skipped. Run non-TUI invocation; verify it does not attempt custom UI. +- [ ] Open `/agents`; verify list/detail scrolling, settings, native create input, and markdown editor focus. +- [ ] Start a background agent; verify FleetList navigation, viewer scrolling, steering, stop, and Escape focus restoration. +- [ ] Resize to the narrow fallback and back; verify recovery. Switch between available Pi themes; verify all surfaces remain legible. + +### Task 5: Commit the release-ready result + +- [ ] If every gate passes, commit documentation with `git add README.md CHANGELOG.md && git commit -m "docs: document dashboard ui migration"`. Record any unavailable manual environment check explicitly rather than marking it passed. diff --git a/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md new file mode 100644 index 0000000..7c8d6ad --- /dev/null +++ b/docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md @@ -0,0 +1,670 @@ +# Run-Chain Input Repair and Dashboard UI Migration Implementation Plan + +> **For agentic workers:** REQUIRED SUB-SKILL: Use superpowers:subagent-driven-development (recommended) or superpowers:executing-plans to implement this plan task-by-task. Steps use checkbox (`- [ ]`) syntax for tracking. + +**Goal:** Make `/run-chain` usable with modern CSI-u/Kitty terminal input and give every pi-subagents-owned UI surface the compact visual language of the pi-status dashboard. + +**Architecture:** Add one small local dashboard-style renderer for framed overlays, ANSI-safe sizing, and viewport fitting. Keep current managers, commands, schemas, settings, and surface placements; repair chain input with Pi/TUI primitives and migrate each existing UI onto the shared visual conventions without importing pi-status or its state machine. + +**Tech Stack:** TypeScript, `@earendil-works/pi-ai@0.84.3`, `@earendil-works/pi-coding-agent@0.84.3`, `@earendil-works/pi-tui@0.84.3`, Vitest, pnpm, Biome. + +**Spec:** `docs/superpowers/plans/2026-08-26-run-chain-dashboard-ui.md#approved-design` + +## Global Constraints + +- The tested Pi/TUI baseline is exactly `0.84.3`; retain wildcard Pi peer dependencies and document Pi `0.84.3+` for users. +- Use Pi's active theme only. Do not add pi-status palette presets, color settings, config files, or cross-extension reads. +- Do not add a runtime dependency on pi-status or extract a shared package. +- Preserve `/run-chain`, `/chain`, `/agents`, `--yes`, `--bg`, chain schemas, tool contracts, agent definitions, and settings formats. +- Preserve AgentWidget above-editor placement, ChainWidget above-editor placement, and FleetList below-editor placement. +- Keep Pi's native input/editor dialogs for multi-step agent creation and full markdown editing. +- Interactive overlays use a centered `92%` width and `85%` maximum height. +- A failed or cancelled chain preview must never launch an unconfirmed chain. +- Every new branch, viewport calculation, or input path leaves a focused runnable Vitest regression. + +--- + +## Approved Design + +The defect is in `ChainClarifyComponent`: its raw string comparisons recognize legacy bytes such as `"\r"` and `"j"`, while modern terminals may send CSI-u values such as `"\x1b[13u"` and `"\x1b[106u"`. Pi/TUI's `matchesKey()` already recognizes both encodings. Existing tests pass because they feed only the legacy strings, so they do not exercise the failing boundary. + +The migration ports only pi-status' general presentation ideas: heavy framed overlays, visible selection, semantic theme roles, restrained spacing, footer key hints, ANSI-safe truncation, and a selected-row-aware viewport. pi-status' dashboard reducer, statusbar domain, sidebar, palettes, and configuration remain outside this repository. + +Owned surfaces included in the migration: + +1. Interactive overlays: `/agents` menus, chain preview/editor, and conversation viewer/composer. +2. Persistent surfaces: AgentWidget, ChainWidget, and FleetList. +3. Inline surfaces: subagent tool calls/results, completion notifications, watchdog warnings, and intercom messages. + +## File Structure + +- Create `src/tui/dashboard-style.ts`: shared overlay constants, frame rendering, ANSI-safe padding, viewport fitting, and small-terminal rendering. +- Create `tests/dashboard-style.test.ts`: exact width, viewport, and narrow-terminal regressions. +- Modify `src/tui/chain-clarify.ts`: modern key matching, native `Input`, focus forwarding, and dashboard rendering. +- Modify `src/core/slash-chain.ts`: TUI-only preview gating and safe preview failure behavior. +- Modify `src/tui/agents-menu.ts` and `src/tui/conversation-viewer.ts`: shared framed overlays and viewport behavior. +- Modify `src/tui/agent-widget.ts`, `src/tui/chain-widget.ts`, and `src/tui/fleet-list.ts`: compact dashboard-style headings and rows without changing placement or lifecycle. +- Modify `src/tui/render.ts` and `src/index.ts`: consistent inline status and metadata hierarchy. +- Modify corresponding existing `tests/*.test.ts` files, `package.json`, `pnpm-lock.yaml`, `README.md`, and `CHANGELOG.md`. + +--- + +### Task 1: Align the Pi Baseline and Add Dashboard Primitives + +**Files:** + +- Create: `src/tui/dashboard-style.ts` +- Create: `tests/dashboard-style.test.ts` +- Modify: `package.json` +- Modify: `pnpm-lock.yaml` + +**Interfaces:** + +```ts +import type { OverlayOptions } from "@earendil-works/pi-tui"; +import type { Theme } from "./agent-widget.js"; + +export const DASHBOARD_MAX_HEIGHT_RATIO = 0.85; +export const DASHBOARD_OVERLAY_OPTIONS: OverlayOptions; +export const MIN_DASHBOARD_FRAME_WIDTH = 7; + +export function dashboardContentWidth(width: number): number; +export function renderDashboardFrame( + lines: readonly string[], + width: number, + theme: Theme, +): string[]; +export function fitDashboardViewport( + lines: readonly string[], + selectedLine: number | undefined, + height: number, + offset: number, +): { lines: string[]; offset: number }; +export function renderDashboardTooSmall( + width: number, + height: number, + theme: Theme, +): string[]; +``` + +- [ ] **Step 1: Update only the three Pi development packages.** + + In `package.json`, change these versions and leave TypeScript, Vitest, Biome, TypeBox, engines, and peer dependencies unchanged: + + ```json + { + "devDependencies": { + "@earendil-works/pi-ai": "^0.84.3", + "@earendil-works/pi-coding-agent": "^0.84.3", + "@earendil-works/pi-tui": "^0.84.3" + } + } + ``` + + Run: + + ```bash + pnpm install --lockfile-only + pnpm typecheck + ``` + + Expected: the lockfile resolves the three Pi packages at `0.84.3` and the existing source typechecks without compatibility shims. If typecheck exposes a real upstream API change, record the exact compiler error in this task and make only the smallest call-site adjustment required by that error. + +- [ ] **Step 2: Write failing frame and viewport tests.** + + Create `tests/dashboard-style.test.ts` with a no-ANSI theme and these assertions: + + ```ts + import { describe, expect, test } from "vitest"; + import { + dashboardContentWidth, + fitDashboardViewport, + renderDashboardFrame, + renderDashboardTooSmall, + } from "../src/tui/dashboard-style.js"; + + const theme = { + fg: (_color: string, text: string) => text, + bold: (text: string) => text, + }; + + describe("dashboard style", () => { + test("renders every frame row at the requested visible width", () => { + const lines = renderDashboardFrame(["Header", "Body"], 24, theme); + expect(lines).toHaveLength(6); + expect(lines.every((line) => line.length === 24)).toBe(true); + expect(lines[0]).toBe(`┏${"━".repeat(22)}┓`); + expect(lines.at(-1)).toBe(`┗${"━".repeat(22)}┛`); + expect(dashboardContentWidth(24)).toBe(18); + }); + + test("moves the viewport until the selected row is visible", () => { + const result = fitDashboardViewport(["0", "1", "2", "3", "4"], 4, 3, 0); + expect(result).toEqual({ lines: ["2", "3", "4"], offset: 2 }); + }); + + test("renders a bounded small-terminal escape message", () => { + const lines = renderDashboardTooSmall(30, 3, theme); + expect(lines).toHaveLength(3); + expect(lines.every((line) => line.length === 30)).toBe(true); + expect(lines.join("\n")).toContain("Esc"); + }); + }); + ``` + +- [ ] **Step 3: Run the new tests and confirm the missing module failure.** + + ```bash + pnpm vitest run tests/dashboard-style.test.ts + ``` + + Expected: FAIL because `src/tui/dashboard-style.ts` does not exist. + +- [ ] **Step 4: Implement the exact shared primitives.** + + Adapt pi-status' frame and viewport algorithms into `src/tui/dashboard-style.ts` with these fixed values: + + ```ts + import { + truncateToWidth, + visibleWidth, + type OverlayOptions, + } from "@earendil-works/pi-tui"; + import type { Theme } from "./agent-widget.js"; + + const PADDING_X = 2; + const FRAME = { tl: "┏", tr: "┓", bl: "┗", br: "┛", h: "━", v: "┃" } as const; + + export const DASHBOARD_MAX_HEIGHT_RATIO = 0.85; + export const MIN_DASHBOARD_FRAME_WIDTH = 7; + export const DASHBOARD_OVERLAY_OPTIONS: OverlayOptions = { + anchor: "center", + width: "92%", + maxHeight: "85%", + }; + + function pad(text: string, width: number): string { + if (width <= 0) return ""; + const value = truncateToWidth(text, width, ""); + return `${value}${" ".repeat(Math.max(0, width - visibleWidth(value)))}`; + } + + export function dashboardContentWidth(width: number): number { + return Math.max(1, Math.floor(width) - 2 - PADDING_X * 2); + } + ``` + + Implement `renderDashboardFrame()` with top border, one blank row, padded content, one blank row, and bottom border. Implement `fitDashboardViewport()` with clamped height/offset and selected-row visibility. Implement `renderDashboardTooSmall()` as fixed-width rows with `Terminal too small · Esc` centered vertically. + +- [ ] **Step 5: Run the focused tests and typecheck.** + + ```bash + pnpm vitest run tests/dashboard-style.test.ts + pnpm typecheck + git diff --check + ``` + + Expected: all dashboard primitive tests pass, every rendered line stays within its requested visible width, and no unrelated dependency changes appear. + +- [ ] **Step 6: Commit the foundation.** + + ```bash + git add package.json pnpm-lock.yaml src/tui/dashboard-style.ts tests/dashboard-style.test.ts + git commit -m "feat: add dashboard ui primitives" + ``` + +### Task 2: Repair `/run-chain` Input and Restyle the Preview + +**Files:** + +- Modify: `src/tui/chain-clarify.ts` +- Modify: `src/core/slash-chain.ts` +- Modify: `tests/chain-clarify.test.ts` +- Modify: `tests/slash-chain.test.ts` +- Modify: `tests/core/chain-clarify-integration.test.ts` + +**Interfaces:** + +- Consumes `DASHBOARD_OVERLAY_OPTIONS`, `dashboardContentWidth()`, `fitDashboardViewport()`, `renderDashboardFrame()`, and `renderDashboardTooSmall()` from Task 1. +- Preserves `ChainClarifyResult = { action: "run" | "cancel" | "bg"; steps: ChainStep[] }`. +- `ChainClarifyComponent` implements both `Component` and `Focusable`; its `focused` setter forwards focus to the active `Input`. + +- [ ] **Step 1: Add failing CSI-u component regressions.** + + Extend `tests/chain-clarify.test.ts` with encoded keys that Pi/TUI recognizes but the raw switch currently ignores: + + ```ts + test("CSI-u Enter returns the run action", () => { + const { component, result } = makeComponent([ + { agent: "scout", task: "analyze" }, + ]); + component.handleInput("\x1b[13u"); + expect(result.value?.action).toBe("run"); + }); + + test("CSI-u printable shortcuts navigate and background the chain", () => { + const { component, result } = makeComponent([ + { agent: "scout", task: "analyze" }, + { agent: "worker", task: "change" }, + ]); + component.handleInput("\x1b[106u"); + expect( + component + .render(80) + .some((line) => line.includes("▸") && line.includes("worker")), + ).toBe(true); + component.handleInput("\x1b[98u"); + expect(result.value?.action).toBe("bg"); + }); + ``` + + Update legacy cursor assertions from `>` to the dashboard marker `▸` in the same test file. + +- [ ] **Step 2: Add a failing command-to-component integration regression.** + + In `tests/slash-chain.test.ts`, construct a TUI command context whose `ui.custom` calls the provided factory, feeds `"\x1b[13u"` into the returned component, and resolves from `done`. Invoke `executeSlashChain()` with one valid Scout step and assert `manager.spawnAndWait` is called exactly once. + + Add a second case where `ui.custom` rejects with `new Error("preview failed")`; assert `spawnAndWait` is not called and `pi.sendMessage` receives a visible `pi-subagent-result` containing `preview failed`. + + The context must include: + + ```ts + const ctx = { + mode: "tui", + cwd: "/tmp", + model: parentModel, + modelRegistry, + ui: { + custom: async (factory: Function) => + await new Promise((resolve) => { + const component = factory( + mockTui, + mockTheme, + mockKeybindings, + resolve, + ); + component.handleInput("\x1b[13u"); + }), + }, + } as unknown as ExtensionCommandContext; + ``` + +- [ ] **Step 3: Run both regressions and confirm the root-cause failure.** + + ```bash + pnpm vitest run tests/chain-clarify.test.ts tests/slash-chain.test.ts + ``` + + Expected: the legacy tests pass, while CSI-u Enter/printable input does not resolve the current component and the integration path does not reach `spawnAndWait`. + +- [ ] **Step 4: Replace raw keys and manual editing with Pi/TUI primitives.** + + In `chain-clarify.ts`: + - Import `Input`, `Key`, `matchesKey`, `type Focusable`, and `isKeyRelease` from `@earendil-works/pi-tui`. + - Ignore key-release events before dispatching actions. + - Use `matchesKey(data, Key.enter)`, `matchesKey(data, Key.escape)`, `matchesKey(data, Key.up)`, and `matchesKey(data, Key.down)` for primary actions. + - Preserve `j`/`k`, `q`, `b`, `e`, and `m` by matching each printable key through `matchesKey()`. + - Replace `editBuffer` and `handleEditInput()` with one `Input | undefined`. Prefill through `input.handleInput(currentValue)`, save through `input.onSubmit`, and return to list mode through `input.onEscape`. + - Implement `focused` getter/setter and forward the value to the current `Input`. + - Clear input focus in `dispose()`. + + Render the overlay as: + + ```text + Chain Preview · N steps + + ▸ [1/N] agent + Task task text + Model inherited-or-override + + ↑/↓ Select • e Edit task • m Edit model • Enter Run • b Background • q/Esc Cancel + ``` + + Use `fitDashboardViewport()` so the selected step remains visible and `renderDashboardTooSmall()` when the frame or body cannot fit. Parallel groups remain read-only and show their child agent names; do not add parallel-item editing. + +- [ ] **Step 5: Gate the preview to TUI and use shared overlay options.** + + In `executeSlashChain()` keep the existing `!bg && !yes` condition and add `ctx.mode === "tui"`. Pass: + + ```ts + { overlay: true, overlayOptions: DASHBOARD_OVERLAY_OPTIONS } + ``` + + to `ctx.ui.custom()`. Keep cancellation as an immediate return. Wrap the custom call inside `executeSlashChain()` so a rejected preview sends a visible `pi-subagent-result` containing the error and returns before preflight or dispatch. This shared error path must cover both `/chain` and `/run-chain`. + + Update test contexts that intentionally exercise the preview to include `mode: "tui"`. Add one `mode: "rpc"` case and assert the chain executes without calling `ui.custom`. + +- [ ] **Step 6: Run chain input, execution, and preflight regressions.** + + ```bash + pnpm vitest run \ + tests/chain-clarify.test.ts \ + tests/core/chain-clarify-integration.test.ts \ + tests/slash-chain.test.ts \ + tests/chain-preflight.test.ts \ + tests/chain-execution.test.ts + pnpm typecheck + git diff --check + ``` + + Expected: legacy and CSI-u input both work, confirmation reaches the first child spawn, cancellation does not spawn, `--yes`/`--bg` still bypass the preview, and preflight behavior is unchanged. + +- [ ] **Step 7: Commit the root fix and preview migration.** + + ```bash + git add src/core/slash-chain.ts src/tui/chain-clarify.ts \ + tests/chain-clarify.test.ts tests/core/chain-clarify-integration.test.ts tests/slash-chain.test.ts + git commit -m "fix: handle modern input in chain preview" + ``` + +### Task 3: Migrate `/agents` Menus to Framed Overlays + +**Files:** + +- Modify: `src/tui/agents-menu.ts` +- Modify: `tests/agents-menu.test.ts` + +**Interfaces:** + +- Consumes the Task 1 dashboard frame, viewport, small-terminal renderer, and overlay options. +- Preserves `showAgentsMenu()`, `runAgentsMenuAction()`, `runAgentsMenuSettingsFlow()`, `SETTINGS_MENU_ITEMS`, and every persisted setting parser. + +- [ ] **Step 1: Add failing dashboard-menu render and navigation tests.** + + Extend the menu test harness so `ctx.ui.custom` captures the returned component. Assert: + + ```ts + expect(component.render(80)[0]).toMatch(/^┏━/); + expect(component.render(80).at(-1)).toMatch(/━┛$/); + expect(component.render(80).join("\n")).toContain("↑/↓ Select"); + ``` + + Add a 12-row terminal fixture with more rows than fit, move down to the last row using `matchesKey`-compatible input, and assert the selected row remains rendered. Keep existing action, scope, parsing, create, edit, disable, export, and delete assertions. + +- [ ] **Step 2: Run the menu tests and confirm the unframed failure.** + + ```bash + pnpm vitest run tests/agents-menu.test.ts + ``` + + Expected: current behavioral tests pass and the new frame/viewport assertions fail. + +- [ ] **Step 3: Refactor only `showRowsMenu()` presentation.** + + Keep all agent and settings workflows unchanged. Inside `showRowsMenu()`: + - Track `selectedIndex` and `offset`. + - Render the title, a blank row, aligned menu rows, a blank row, and the supplied footer through `renderDashboardFrame()`. + - Use `▸` in accent for the selected row and dim text for unselected rows. + - Use `fitDashboardViewport()` with terminal rows capped at `85%`; selection must remain visible. + - Use the shared small-terminal output and keep Escape operational. + - Invoke `ctx.ui.custom()` with the shared centered overlay options. + - Keep `ctx.ui.select()` as the non-custom fallback. + + Do not replace `ctx.ui.input()` or `ctx.ui.editor()` in create, edit, or settings flows. + +- [ ] **Step 4: Run all agent-menu tests and typecheck.** + + ```bash + pnpm vitest run tests/agents-menu.test.ts tests/agents.test.ts + pnpm typecheck + git diff --check + ``` + + Expected: the dashboard frame and scrolling work while all existing agent actions and setting writes retain their current arguments and results. + +- [ ] **Step 5: Commit the menu migration.** + + ```bash + git add src/tui/agents-menu.ts tests/agents-menu.test.ts + git commit -m "refactor: frame agents menus as dashboard overlays" + ``` + +### Task 4: Migrate the Conversation Viewer and Composer + +**Files:** + +- Modify: `src/tui/conversation-viewer.ts` +- Modify: `src/tui/fleet-list.ts` +- Modify: `tests/conversation-viewer.test.ts` +- Modify: `tests/fleet-list.test.ts` + +**Interfaces:** + +- Consumes Task 1 dashboard primitives and overlay options. +- Preserves `ConversationViewer`, `ViewerKeybindings`, Fleet activation, live session subscription, steering, stopping, and cleanup. +- Changes `VIEWPORT_HEIGHT_PCT` from `70` to `85` so internal body sizing matches the shared overlay cap. + +- [ ] **Step 1: Add failing frame, focus, and viewport tests.** + + Add tests asserting the viewer uses `┏━`/`━┛`, renders the dashboard footer vocabulary, and fits within `Math.floor(terminal.rows * 0.85)` rows. Add a focus test: + + ```ts + component.focused = true; + component.handleInput("\x1b[13u"); + expect(component.render(80).join("\n")).toContain("Steer agent"); + component.focused = false; + ``` + + In FleetList tests, assert the custom overlay receives `DASHBOARD_OVERLAY_OPTIONS` and existing activation/key-release behavior still consumes exactly the same keys. + +- [ ] **Step 2: Run focused tests and confirm the visual/focus failures.** + + ```bash + pnpm vitest run tests/conversation-viewer.test.ts tests/fleet-list.test.ts + ``` + + Expected: current scroll/steer/stop tests pass; new shared-frame and focus-forwarding assertions fail. + +- [ ] **Step 3: Reuse the frame and implement `Focusable`.** + + In `ConversationViewer`: + - Implement `Focusable` with `_focused`, getter, and setter. + - Forward focus to the composer when it exists; remove unconditional `input.focused = true`. + - Render header, content viewport, and footer as content passed to `renderDashboardFrame()` instead of maintaining a second border implementation. + - Keep message extraction, truncation limits, live auto-scroll, scroll percentage, steering, two-press stop, and `dispose()` subscription cleanup unchanged. + - Set `VIEWPORT_HEIGHT_PCT = 85` and include the shared frame's four chrome rows in viewport calculations. + + In `FleetList`, replace its inline `90%`/`70%` overlay values with `DASHBOARD_OVERLAY_OPTIONS`; do not change terminal-input capture or roster behavior. + +- [ ] **Step 4: Run viewer/fleet and lifecycle tests.** + + ```bash + pnpm vitest run tests/conversation-viewer.test.ts tests/fleet-list.test.ts tests/agent-manager.test.ts + pnpm typecheck + git diff --check + ``` + + Expected: the viewer stays live after agent completion, steering and stop callbacks fire once, Escape closes, key releases remain ignored by FleetList, and all rows remain ANSI-width safe. + +- [ ] **Step 5: Commit the viewer migration.** + + ```bash + git add src/tui/conversation-viewer.ts src/tui/fleet-list.ts \ + tests/conversation-viewer.test.ts tests/fleet-list.test.ts + git commit -m "refactor: migrate conversation viewer to dashboard frame" + ``` + +### Task 5: Restyle Persistent and Inline Surfaces + +**Files:** + +- Modify: `src/tui/agent-widget.ts` +- Modify: `src/tui/chain-widget.ts` +- Modify: `src/tui/fleet-list.ts` +- Modify: `src/tui/render.ts` +- Modify: `src/index.ts` +- Modify: `tests/agent-widget.test.ts` +- Modify: `tests/chain-widget.test.ts` +- Modify: `tests/fleet-list.test.ts` +- Modify: `tests/render.test.ts` +- Modify: `tests/watchdog-render.test.ts` + +**Interfaces:** + +- No new exported runtime interfaces. +- Preserve widget keys (`agents`, `chain`, `fleet`), placements, timers, status keys, message custom types, expanded/collapsed behavior, and notification details. + +- [ ] **Step 1: Lock the compact visual grammar in failing tests.** + + Update render expectations to require these exact conventions: + + ```text + ╭─ ✦ AGENTS + │ ● worker description · metadata + │ ⎿ activity + ╰─ running/queued summary + ``` + + ```text + ╭─ ✦ CHAIN · chain-id + │ [1/N] ✓ agent + ╰─ completed/running summary + ``` + + FleetList remains unboxed but uses `✦ Agents`, `▸` for the active row, dim `•` separators, and one dashboard-style footer hint. Inline render tests must assert icon + bold subject on the first line, dim metadata on the second line, and indented preview/content below it. + + Preserve existing assertions for maximum widget lines, overflow priority, right-aligned fleet statistics, expanded result fields, output paths, watchdog severity, and grouped notifications. + +- [ ] **Step 2: Run render tests and confirm only expected-string failures.** + + ```bash + pnpm vitest run \ + tests/agent-widget.test.ts \ + tests/chain-widget.test.ts \ + tests/fleet-list.test.ts \ + tests/render.test.ts \ + tests/watchdog-render.test.ts + ``` + + Expected: state/lifecycle assertions pass and the new presentation assertions fail. + +- [ ] **Step 3: Restyle widgets without changing lifecycle code.** + + In AgentWidget and ChainWidget, alter only `renderWidget()`/`renderLines()` output assembly: + - Use `╭─ ✦ TITLE`, `│` body prefixes, and `╰─` summary/last row. + - Keep `success`, `accent`, `warning`, `error`, `muted`, and `dim` semantic roles. + - Keep spinner cadence, overflow caps, finished-agent aging, timers, widget registration, and status text unchanged. + + In FleetList, change only labels, selection marker, separators, and footer copy. Keep its unboxed compact form, right alignment, activation boundary, roster order, and five-agent window. + +- [ ] **Step 4: Normalize inline renderer hierarchy.** + + In `src/tui/render.ts`, centralize only these two formatting helpers: + + ```ts + function statusHeader(icon: string, subject: string, status: string): string; + function metadataLine(parts: readonly string[]): string; + ``` + + Reuse them for subagent calls/results and completion notifications. In `src/index.ts`, apply the same first-line header and second-line metadata structure to watchdog warnings and intercom messages while preserving their custom message types, details, expanded content, and severity colors. + + Do not add a card component: Pi already supplies the native message/tool shell. + +- [ ] **Step 5: Run all UI render and lifecycle tests.** + + ```bash + pnpm vitest run \ + tests/agent-widget.test.ts \ + tests/chain-widget.test.ts \ + tests/fleet-list.test.ts \ + tests/render.test.ts \ + tests/watchdog-render.test.ts \ + tests/notification-renderer.test.ts \ + tests/agent-manager.test.ts + pnpm typecheck + git diff --check + ``` + + Expected: all owned passive and inline surfaces share the agreed hierarchy without changing update timing, placement, payloads, or cleanup. + +- [ ] **Step 6: Commit passive and inline styling.** + + ```bash + git add src/tui/agent-widget.ts src/tui/chain-widget.ts src/tui/fleet-list.ts \ + src/tui/render.ts src/index.ts tests/agent-widget.test.ts tests/chain-widget.test.ts \ + tests/fleet-list.test.ts tests/render.test.ts tests/watchdog-render.test.ts + git commit -m "refactor: unify subagent ui presentation" + ``` + +### Task 6: Document, Verify, and Package the Migration + +**Files:** + +- Modify: `README.md` +- Modify: `CHANGELOG.md` +- Verify: all files changed by Tasks 1–5 + +**Interfaces:** + +- Documentation declares Pi `0.84.3+` and the existing command behavior; it introduces no new configuration keys or flags. + +- [ ] **Step 1: Update compatibility and usage documentation.** + + In README: + - Add `Pi 0.84.3 or newer is required` beside the existing Node requirement. + - Update `/run-chain` documentation to state that foreground execution opens a keyboard-accessible preview; Enter runs, `b` backgrounds, Escape cancels, and `--yes` skips it. + - Update `/agents` and Fleet descriptions to mention centered dashboard overlays and current navigation keys. + + In CHANGELOG, add an Unreleased section containing: + + ```markdown + ## Unreleased + + ### Fixed + + - Handle CSI-u/Kitty keyboard input in the foreground chain preview so `/run-chain` can be confirmed in modern terminals. + + ### Changed + + - Align pi-subagents UI surfaces with the pi-status dashboard visual language and raise the tested Pi baseline to 0.84.3. + ``` + +- [ ] **Step 2: Run the complete automated verification.** + + ```bash + pnpm check + pnpm pack --dry-run + git diff --check + ``` + + Expected: Biome lint, TypeScript, every Vitest suite, package contents, and whitespace checks pass. The tarball includes `src/tui/dashboard-style.ts` through the existing `src` package inclusion. + +- [ ] **Step 3: Perform manual modern-terminal acceptance.** + + In a TUI session using Ghostty, Kitty, or another terminal with CSI-u input enabled: + 1. Run `/run-chain implement -- inspect this repository`; navigate with arrows and `j`/`k`, edit task/model, cancel once, then reopen and confirm with Enter. Verify the first agent starts. + 2. Reopen the chain and press `b`; verify a background chain ID appears and ChainWidget updates. + 3. Run the same command with `--yes`; verify no preview appears. + 4. Open `/agents`; browse agents, enter Settings, cancel a native input, and return without losing keyboard focus. + 5. Start a background agent, activate FleetList from an empty prompt, open ConversationViewer, steer once, and close with Escape. + 6. Resize below the dashboard minimum and back; verify the small-terminal message appears and the selected row returns into view. + 7. Switch Pi themes; verify every owned surface follows the active theme without writing a color configuration. + + Record the terminal name and Pi version in the implementation handoff. Any failed path blocks completion. + +- [ ] **Step 4: Review the final diff for scope.** + + ```bash + git status --short + git diff --stat + git diff -- package.json README.md CHANGELOG.md src/tui src/core/slash-chain.ts tests + ``` + + Expected: no chain execution semantics, schemas, settings formats, agent discovery, manager logic, or unrelated files changed. + +- [ ] **Step 5: Commit documentation and final verification changes.** + + ```bash + git add README.md CHANGELOG.md + git commit -m "docs: document dashboard ui migration" + ``` + +## Completion Criteria + +- `/run-chain` accepts legacy and CSI-u/Kitty input and reaches execution after explicit confirmation. +- Run, Background, Cancel, edit, `--yes`, `--bg`, non-TUI, and preflight paths have runnable regressions. +- All three interactive overlays use the shared dashboard frame and selected-row-aware viewport. +- All three persistent surfaces and all inline renderers use the agreed compact dashboard hierarchy. +- Pi's current theme is the only color source. +- No new runtime dependency, palette, setting, schema, command, or custom form exists. +- `pnpm check`, `pnpm pack --dry-run`, `git diff --check`, and manual modern-terminal acceptance all pass.