fix(dashboard): align planning tests with clarification default-off (#2299)
## Summary - Full Suite [29643371961](https://github.com/Runfusion/Fusion/actions/runs/29643371961) after #2298: shards 1–2 green; shard 3 confirm Other race; shard 4 MCP + re-emit planning tests. - MCP lane mock: follow-up prompts return `complete` (product defaults clarification off). - Re-emit suite: pass `clarificationEnabled: true` so multi-question interview invariants still run. - Confirm Other UI test: `findByTestId("planning-other-input")` after click. ## Test plan - [x] mcp-lane-forwarding + planning-answered-question-reemit (14) - [x] confirm Other desktop/mobile planning-flow - [ ] Full Suite all 4 shards green on main <!-- This is an auto-generated comment: release notes by coderabbit.ai --> ## Summary by CodeRabbit * **Tests** * Improved automated coverage for planning-mode interviews, including “Other” responses and follow-up prompts. * Increased test reliability by handling asynchronous input updates more consistently. * Added validation for clarification-enabled interviews and completion behavior in MCP forwarding scenarios. <!-- end of auto-generated comment: release notes by coderabbit.ai -->
This commit is contained in:
@@ -835,15 +835,22 @@ describe("PlanningModeModal", () => {
|
||||
expect(screen.getByTestId("planning-option-other")).toBeInTheDocument();
|
||||
expect(screen.queryByTestId("planning-other-input")).toBeNull();
|
||||
|
||||
/*
|
||||
FNXC:PlanningModeOptions 2026-07-18-12:15:
|
||||
Full Suite shard 3 (29643371961) failed when fireEvent.click(Other) did not flush
|
||||
isOtherSelected before the synchronous getByTestId(planning-other-input) under CI
|
||||
load. Await findByTestId after the confirm Other button click (same settle discipline
|
||||
as multi-select Other) before asserting Continue enablement and the _other payload.
|
||||
*/
|
||||
const continueButton = screen.getByRole("button", { name: "Continue" });
|
||||
fireEvent.click(screen.getByTestId("planning-option-other"));
|
||||
expect(screen.getByTestId("planning-other-input")).toBeInTheDocument();
|
||||
const otherInput = await screen.findByTestId("planning-other-input");
|
||||
expect(continueButton).toBeDisabled();
|
||||
|
||||
fireEvent.change(screen.getByTestId("planning-other-input"), { target: { value: " " } });
|
||||
fireEvent.change(otherInput, { target: { value: " " } });
|
||||
expect(continueButton).toBeDisabled();
|
||||
|
||||
fireEvent.change(screen.getByTestId("planning-other-input"), {
|
||||
fireEvent.change(otherInput, {
|
||||
target: { value: " Ask a different scoping question " },
|
||||
});
|
||||
expect(continueButton).toBeEnabled();
|
||||
|
||||
@@ -3,21 +3,41 @@
|
||||
import { beforeEach, describe, expect, it, vi } from "vitest";
|
||||
|
||||
const { createFnAgentMock, resolveMcpServersForStoreMock } = vi.hoisted(() => ({
|
||||
/*
|
||||
FNXC:DashboardTests 2026-07-18-12:20:
|
||||
Planning defaults clarificationEnabled=false, so createSession forces a summary after the
|
||||
first question (continueToSummaryAfterSuppressedQuestion). Mock every follow-up prompt as a
|
||||
complete payload so MCP-forwarding assertions exercise the default product path instead of
|
||||
throwing Clarification-disabled follow-up did not produce a summary.
|
||||
*/
|
||||
createFnAgentMock: vi.fn(async () => ({
|
||||
session: {
|
||||
state: { messages: [] as Array<{ role: string; content: string }> },
|
||||
prompt: vi.fn(async function (this: { state: { messages: Array<{ role: string; content: string }> } }, _message: string) {
|
||||
const alreadyAnswered = this.state.messages.some((message) => message.role === "assistant");
|
||||
this.state.messages.push({
|
||||
role: "assistant",
|
||||
content: JSON.stringify({
|
||||
type: "question",
|
||||
data: {
|
||||
id: "q1",
|
||||
text: "What should be built?",
|
||||
type: "text",
|
||||
required: true,
|
||||
},
|
||||
}),
|
||||
content: JSON.stringify(
|
||||
alreadyAnswered
|
||||
? {
|
||||
type: "complete",
|
||||
data: {
|
||||
title: "Build a feature",
|
||||
description: "Materialized MCP planning summary",
|
||||
suggestedSize: "M",
|
||||
keyDeliverables: ["docs MCP available"],
|
||||
},
|
||||
}
|
||||
: {
|
||||
type: "question",
|
||||
data: {
|
||||
id: "q1",
|
||||
text: "What should be built?",
|
||||
type: "text",
|
||||
required: true,
|
||||
},
|
||||
},
|
||||
),
|
||||
});
|
||||
}),
|
||||
dispose: vi.fn(),
|
||||
|
||||
@@ -156,11 +156,22 @@ function setupAgent(behaviors: TurnBehavior[]) {
|
||||
async function startSessionAtFirstQuestion(
|
||||
agent: ReturnType<typeof setupAgent>,
|
||||
): Promise<string> {
|
||||
/*
|
||||
FNXC:PlanningRetry 2026-07-18-12:20:
|
||||
createSessionWithAgent defaults clarificationEnabled=false, which suppresses the first
|
||||
question into continueToSummaryAfterSuppressedQuestion and consumes the next mock prompt
|
||||
turn (often the hung turn these re-emit tests need). Opt into clarification so the
|
||||
multi-question interview invariants under test still run.
|
||||
*/
|
||||
const sessionId = await createSessionWithAgent(
|
||||
"10.0.2.20",
|
||||
"Plan a feature",
|
||||
"/tmp/project",
|
||||
MOCK_TASK_STORE,
|
||||
undefined,
|
||||
undefined,
|
||||
undefined,
|
||||
{ clarificationEnabled: true },
|
||||
);
|
||||
planningStreamManager.consumeInitialTurn(sessionId)?.();
|
||||
await agent.firstQuestionEmitted;
|
||||
|
||||
Reference in New Issue
Block a user