# Plan — Interactive "Answer Claude's Questions" Spec: `docs/superpowers/specs/2026-06-25-interactive-ask-user-design.md` Implement on the shared main tree. Commit explicit paths per task (never `git add -A`). Build with `-c Release` (running Worker locks Debug). No real-Claude tests. ## Task 1 — PendingQuestionRegistry (worker, new file) - `src/ClaudeDo.Worker/Runner/PendingQuestionRegistry.cs`: singleton; `record PendingQuestion(TaskId, QuestionId, Question)`. - `(string QuestionId, Task Answer) Register(taskId, question)` — overwrites any stale entry, `RunContinuationsAsynchronously`. - `bool TryAnswer(taskId, questionId, answer)`; `PendingQuestion? Get(taskId)`; `void Remove(taskId, questionId)`. - Test: `tests/ClaudeDo.Worker.Tests/Runner/PendingQuestionRegistryTests.cs` — register→answer resolves the task; wrong questionId no-ops; Get reflects state; second Register overwrites. ## Task 2 — AskUser MCP tool (worker) - `TaskRunMcpService.cs`: inject `PendingQuestionRegistry`; add `[McpServerTool] async Task AskUser(string question, CancellationToken ct)`: - caller id from `_ctx.Current.CallerTaskId`; register; broadcast `TaskQuestionAsked`. - await answer via `Task.WaitAsync` with a 3-min linked-CTS; on timeout return the fallback string; on request-cancel rethrow. - `finally`: `Remove` + broadcast `TaskQuestionResolved`. - `[Description]`: when to use (only when a wrong guess is costly/irreversible; otherwise proceed). - Test: `tests/ClaudeDo.Worker.Tests/Runner/AskUserToolTests.cs` — answer path returns the answer; timeout path returns fallback (inject a short timeout or a seam) with a fake broadcaster + stub context accessor. ## Task 3 — Wire MCP for all runs + timeout env (worker) - `TaskRunner.RunAsync`: move MCP-identity setup out of the `standalone` gate so every run gets `claudedo_run`; `AllowedTools` = `mcp__claudedo_run__AskUser` always, append `,mcp__claudedo_run__SuggestImprovement` when standalone. Keep token cleanup in `finally`. - `ClaudeProcess.cs`: `psi.Environment["MCP_TOOL_TIMEOUT"] = "200000";`. - System prompt file (PromptKind.System default): add one guidance line about `AskUser`. ## Task 4 — Hub + Broadcaster (worker) - `HubBroadcaster.cs`: `TaskQuestionAsked(taskId, questionId, question)`, `TaskQuestionResolved(taskId, questionId)`. - `WorkerHub.cs`: inject registry; `bool AnswerTaskQuestion(taskId, questionId, answer)`; `PendingQuestionDto? GetPendingQuestion(taskId)`; `record PendingQuestionDto(...)`. - `Program.cs`: register `PendingQuestionRegistry` as singleton. ## Task 5 — UI client (IWorkerClient/WorkerClient + fakes) - `IWorkerClient`: `Task AnswerTaskQuestionAsync(taskId, questionId, answer)`, `Task GetPendingQuestionAsync(taskId)`, events `Action? TaskQuestionAskedEvent`, `Action? TaskQuestionResolvedEvent`; UI DTO record. - `WorkerClient`: implement invokes + `On<...>` handlers raising the events. - Update hand-rolled `IWorkerClient` fakes in Ui.Tests (and Worker.Tests if present). ## Task 6 — TaskMonitorViewModel (hot file) - Subscribe both events (filter by `_subscribedTaskId`); dispose handlers. - Props: `PendingQuestionId`, `PendingQuestion`, `HasPendingQuestion`, `AnswerDraft`, `IsWaitingForInput`. - `SubmitAnswerCommand` (CanExecute: non-empty draft + HasPendingQuestion) → `AnswerTaskQuestionAsync`; clear draft. - Clear pending on `TaskFinished` for this task and in `Reset()`. - Test: `TaskMonitorViewModelTests` — asked event surfaces question; submit invokes client + clears; resolved/finished clears. ## Task 7 — Hydrate on attach (MissionControlViewModel) - In `HydrateAsync`, after `ApplyState`, call `GetPendingQuestionAsync(taskId)`; if present, set the monitor's pending question (re-attach case). ## Task 8 — View banner (hot file, additive) - `MonitorPaneView.axaml`: a `Border DockPanel.Dock="Top"` above `SessionTerminalView`, `IsVisible="{Binding HasPendingQuestion}"`, showing the question text, a `TextBox` bound to `AnswerDraft` (Enter submits), and a Send `Button` → `SubmitAnswerCommand`. Mirror the roadblock-banner styling. ## Task 9 — Localization - `en.json` + `de.json`: `missionControl.question.title`, `.placeholder`, `.send`. Keep parity (Localization.Tests). ## Task 10 — Build + test + verify - `dotnet build` App + Worker `-c Release`; run Worker.Tests, Ui.Tests, Localization.Tests. - Self-review diffs. Flag the two manual verification gaps to Mika. Do not push.