fix(FN-000): scope dashboard project flows
This commit is contained in:
@@ -89,6 +89,21 @@ describe("AgentDetailView", () => {
|
||||
});
|
||||
});
|
||||
|
||||
it("fetches the agent using the active project context", async () => {
|
||||
render(
|
||||
<AgentDetailView
|
||||
agentId="agent-001"
|
||||
projectId="proj_123"
|
||||
onClose={vi.fn()}
|
||||
addToast={vi.fn()}
|
||||
/>
|
||||
);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgent).toHaveBeenCalledWith("agent-001", "proj_123");
|
||||
});
|
||||
});
|
||||
|
||||
it("displays role badge", async () => {
|
||||
render(
|
||||
<AgentDetailView
|
||||
@@ -219,7 +234,7 @@ describe("AgentDetailView", () => {
|
||||
);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgent).toHaveBeenCalledWith("agent-001");
|
||||
expect(mockFetchAgent).toHaveBeenCalledWith("agent-001", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -296,10 +296,13 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(createButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockCreateAgent).toHaveBeenCalledWith({
|
||||
name: "My New Agent",
|
||||
role: "executor",
|
||||
});
|
||||
expect(mockCreateAgent).toHaveBeenCalledWith(
|
||||
{
|
||||
name: "My New Agent",
|
||||
role: "executor",
|
||||
},
|
||||
undefined
|
||||
);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
@@ -393,7 +396,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(startButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-001", "active");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-001", "active", undefined);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
@@ -463,7 +466,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(pauseButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "paused");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "paused", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -496,7 +499,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(stopButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "terminated");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "terminated", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -530,7 +533,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(screen.getByTitle("Resume"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-003", "active");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-003", "active", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -618,7 +621,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.click(screen.getByTitle("Delete"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockDeleteAgent).toHaveBeenCalledWith("agent-004");
|
||||
expect(mockDeleteAgent).toHaveBeenCalledWith("agent-004", undefined);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
@@ -672,7 +675,7 @@ describe("AgentListModal", () => {
|
||||
fireEvent.change(filterSelect, { target: { value: "active" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenCalledWith({ state: "active" });
|
||||
expect(mockFetchAgents).toHaveBeenCalledWith({ state: "active" }, undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -693,13 +696,13 @@ describe("AgentListModal", () => {
|
||||
fireEvent.change(filterSelect, { target: { value: "idle" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith({ state: "idle" });
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith({ state: "idle" }, undefined);
|
||||
});
|
||||
|
||||
fireEvent.change(filterSelect, { target: { value: "all" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith(undefined);
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith(undefined, undefined);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -94,6 +94,13 @@ describe("AgentsView", () => {
|
||||
});
|
||||
});
|
||||
|
||||
it("passes projectId to agent fetches", async () => {
|
||||
render(<AgentsView addToast={mockAddToast} projectId="proj_123" />);
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenCalledWith(undefined, "proj_123");
|
||||
});
|
||||
});
|
||||
|
||||
it("renders empty state when no agents", async () => {
|
||||
mockFetchAgents.mockResolvedValue([]);
|
||||
render(<AgentsView addToast={mockAddToast} />);
|
||||
@@ -220,7 +227,7 @@ describe("AgentsView", () => {
|
||||
fireEvent.change(filterSelect, { target: { value: "active" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenCalledWith({ state: "active" });
|
||||
expect(mockFetchAgents).toHaveBeenCalledWith({ state: "active" }, undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -235,13 +242,13 @@ describe("AgentsView", () => {
|
||||
fireEvent.change(filterSelect, { target: { value: "idle" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith({ state: "idle" });
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith({ state: "idle" }, undefined);
|
||||
});
|
||||
|
||||
fireEvent.change(filterSelect, { target: { value: "all" } });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith(undefined);
|
||||
expect(mockFetchAgents).toHaveBeenLastCalledWith(undefined, undefined);
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -268,7 +275,7 @@ describe("AgentsView", () => {
|
||||
expect(mockCreateAgent).toHaveBeenCalledWith({
|
||||
name: "My Agent",
|
||||
role: "custom",
|
||||
});
|
||||
}, undefined);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
@@ -338,7 +345,7 @@ describe("AgentsView", () => {
|
||||
fireEvent.click(screen.getByTitle("Activate"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-001", "active");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-001", "active", undefined);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
@@ -370,7 +377,7 @@ describe("AgentsView", () => {
|
||||
fireEvent.click(pauseButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "paused");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-002", "paused", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -384,7 +391,7 @@ describe("AgentsView", () => {
|
||||
fireEvent.click(screen.getByTitle("Resume"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-003", "active");
|
||||
expect(mockUpdateAgentState).toHaveBeenCalledWith("agent-003", "active", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -448,7 +455,7 @@ describe("AgentsView", () => {
|
||||
fireEvent.click(screen.getByTitle("Delete"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockDeleteAgent).toHaveBeenCalledWith("agent-004");
|
||||
expect(mockDeleteAgent).toHaveBeenCalledWith("agent-004", undefined);
|
||||
});
|
||||
|
||||
expect(mockAddToast).toHaveBeenCalledWith(
|
||||
|
||||
@@ -140,7 +140,7 @@ describe("App deep link handling", () => {
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123", "proj_123");
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
@@ -160,7 +160,7 @@ describe("App deep link handling", () => {
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-404");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-404", "proj_123");
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
@@ -197,7 +197,7 @@ describe("App deep link handling", () => {
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-789");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-789", "proj_456");
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
@@ -242,7 +242,7 @@ describe("App deep link handling", () => {
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123", "proj_123");
|
||||
});
|
||||
|
||||
// setCurrentProject should NOT be called since we're already on this project
|
||||
@@ -262,7 +262,7 @@ describe("App deep link handling", () => {
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-123", "proj_123");
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
@@ -274,6 +274,44 @@ describe("App deep link handling", () => {
|
||||
});
|
||||
});
|
||||
|
||||
describe("App mission wiring", () => {
|
||||
afterEach(() => {
|
||||
localStorage.removeItem("kb-dashboard-view-mode");
|
||||
});
|
||||
|
||||
it("hides mission controls when no project is selected", async () => {
|
||||
mockCurrentProjectState.currentProject = null;
|
||||
mockProjectsState.projects = [];
|
||||
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchSettings).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
expect(screen.queryByTestId("missions-btn")).toBeNull();
|
||||
});
|
||||
|
||||
it("shows mission controls in project view when a project is selected", async () => {
|
||||
localStorage.setItem("kb-dashboard-view-mode", "project");
|
||||
mockCurrentProjectState.currentProject = {
|
||||
id: "proj_123",
|
||||
name: "Test Project",
|
||||
path: "/test",
|
||||
status: "active",
|
||||
isolationMode: "in-process",
|
||||
createdAt: "",
|
||||
updatedAt: "",
|
||||
};
|
||||
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(screen.getByTestId("missions-btn")).toBeTruthy();
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
describe("App auto-open Settings on unauthenticated", () => {
|
||||
it("auto-opens Settings to Authentication tab when all providers are unauthenticated", async () => {
|
||||
render(<App />);
|
||||
@@ -410,7 +448,7 @@ describe("App global pause (hard stop)", () => {
|
||||
});
|
||||
|
||||
// Should call updateSettings with globalPause: true
|
||||
expect(updateSettings).toHaveBeenCalledWith({ globalPause: true });
|
||||
expect(updateSettings).toHaveBeenCalledWith({ globalPause: true }, "proj_123");
|
||||
});
|
||||
|
||||
it("reverts global pause state on updateSettings failure", async () => {
|
||||
@@ -485,7 +523,7 @@ describe("App engine pause (soft pause)", () => {
|
||||
});
|
||||
|
||||
// Should call updateSettings with enginePaused: true
|
||||
expect(updateSettings).toHaveBeenCalledWith({ enginePaused: true });
|
||||
expect(updateSettings).toHaveBeenCalledWith({ enginePaused: true }, "proj_123");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -638,6 +676,19 @@ describe("App view switching", () => {
|
||||
});
|
||||
});
|
||||
|
||||
it("hides agent view controls when no project is active", async () => {
|
||||
mockCurrentProjectState.currentProject = null;
|
||||
localStorage.setItem("kb-dashboard-view-mode", "overview");
|
||||
|
||||
render(<App />);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(screen.queryByTitle("Agents view")).toBeNull();
|
||||
});
|
||||
|
||||
localStorage.removeItem("kb-dashboard-view-mode");
|
||||
});
|
||||
|
||||
it("renders AgentsView when agents view is selected", async () => {
|
||||
render(<App />);
|
||||
|
||||
|
||||
@@ -55,6 +55,17 @@ describe("Header", () => {
|
||||
expect(btn).toBeDefined();
|
||||
});
|
||||
|
||||
it("renders the missions button when mission management is available", () => {
|
||||
const onOpen = vi.fn();
|
||||
render(<Header onOpenMissions={onOpen} />);
|
||||
expect(screen.getByTestId("missions-btn")).toBeDefined();
|
||||
});
|
||||
|
||||
it("does not render the missions button when mission management is unavailable", () => {
|
||||
render(<Header />);
|
||||
expect(screen.queryByTestId("missions-btn")).toBeNull();
|
||||
});
|
||||
|
||||
it("calls onOpenGitHubImport when import button is clicked", () => {
|
||||
const onOpen = vi.fn();
|
||||
render(<Header onOpenGitHubImport={onOpen} />);
|
||||
|
||||
@@ -167,7 +167,7 @@ describe("ListView", () => {
|
||||
fireEvent.click(row!);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-001");
|
||||
expect(fetchTaskDetail).toHaveBeenCalledWith("FN-001", undefined);
|
||||
});
|
||||
|
||||
expect(mockOnOpenDetail).toHaveBeenCalledWith(mockDetail);
|
||||
|
||||
@@ -119,7 +119,7 @@ describe("PrSection", () => {
|
||||
expect(createPr).toHaveBeenCalledWith("FN-001", {
|
||||
title: "My PR Title",
|
||||
body: undefined,
|
||||
});
|
||||
}, undefined);
|
||||
});
|
||||
|
||||
expect(mockOnPrCreated).toHaveBeenCalledWith(mockPrInfo);
|
||||
@@ -243,7 +243,7 @@ describe("PrSection", () => {
|
||||
fireEvent.click(refreshButton);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(refreshPrStatus).toHaveBeenCalledWith("FN-001");
|
||||
expect(refreshPrStatus).toHaveBeenCalledWith("FN-001", undefined);
|
||||
});
|
||||
|
||||
expect(mockOnPrUpdated).toHaveBeenCalledWith(updatedPr);
|
||||
|
||||
@@ -106,7 +106,7 @@ describe("ScriptsModal", () => {
|
||||
fireEvent.click(screen.getByTestId("script-save-btn"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addScript).toHaveBeenCalledWith("new-script", "echo hello");
|
||||
expect(addScript).toHaveBeenCalledWith("new-script", "echo hello", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Script created", "success");
|
||||
});
|
||||
});
|
||||
@@ -158,7 +158,7 @@ describe("ScriptsModal", () => {
|
||||
fireEvent.click(screen.getByTestId("script-save-btn"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addScript).toHaveBeenCalledWith("my-script_v2", "echo test");
|
||||
expect(addScript).toHaveBeenCalledWith("my-script_v2", "echo test", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -222,7 +222,7 @@ describe("ScriptsModal", () => {
|
||||
fireEvent.click(screen.getByTestId("confirm-delete-script-build"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(removeScript).toHaveBeenCalledWith("build");
|
||||
expect(removeScript).toHaveBeenCalledWith("build", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Script deleted", "success");
|
||||
});
|
||||
});
|
||||
@@ -317,7 +317,7 @@ describe("ScriptsModal", () => {
|
||||
fireEvent.click(screen.getByTestId("script-save-btn"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addScript).toHaveBeenCalledWith("build", "npm run build:prod");
|
||||
expect(addScript).toHaveBeenCalledWith("build", "npm run build:prod", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Script updated", "success");
|
||||
});
|
||||
});
|
||||
|
||||
@@ -33,10 +33,14 @@ vi.mock("../../api", () => ({
|
||||
fetchAuthStatus: vi.fn(() => Promise.resolve({ providers: [{ id: "anthropic", name: "Anthropic", authenticated: false }] })),
|
||||
loginProvider: vi.fn(() => Promise.resolve({ url: "https://auth.example.com/login" })),
|
||||
logoutProvider: vi.fn(() => Promise.resolve({ success: true })),
|
||||
fetchModels: vi.fn(() => Promise.resolve([
|
||||
{ provider: "anthropic", id: "claude-sonnet-4-5", name: "Claude Sonnet 4.5", reasoning: true, contextWindow: 200000 },
|
||||
{ provider: "openai", id: "gpt-4o", name: "GPT-4o", reasoning: false, contextWindow: 128000 },
|
||||
])),
|
||||
fetchModels: vi.fn(() => Promise.resolve({
|
||||
models: [
|
||||
{ provider: "anthropic", id: "claude-sonnet-4-5", name: "Claude Sonnet 4.5", reasoning: true, contextWindow: 200000 },
|
||||
{ provider: "openai", id: "gpt-4o", name: "GPT-4o", reasoning: false, contextWindow: 128000 },
|
||||
],
|
||||
favoriteProviders: [],
|
||||
favoriteModels: [],
|
||||
})),
|
||||
testNtfyNotification: vi.fn(() => Promise.resolve({ success: true })),
|
||||
}));
|
||||
|
||||
@@ -579,7 +583,7 @@ describe("SettingsModal", () => {
|
||||
});
|
||||
|
||||
it("shows empty state when no models available", async () => {
|
||||
(fetchModels as ReturnType<typeof vi.fn>).mockResolvedValueOnce([]);
|
||||
(fetchModels as ReturnType<typeof vi.fn>).mockResolvedValueOnce({ models: [], favoriteProviders: [], favoriteModels: [] });
|
||||
|
||||
render(<SettingsModal onClose={onClose} addToast={addToast} />);
|
||||
await waitFor(() => expect(fetchSettings).toHaveBeenCalled());
|
||||
@@ -649,7 +653,7 @@ describe("SettingsModal", () => {
|
||||
});
|
||||
|
||||
it("shows empty state in Execution Model section when no models available", async () => {
|
||||
(fetchModels as ReturnType<typeof vi.fn>).mockResolvedValueOnce([]);
|
||||
(fetchModels as ReturnType<typeof vi.fn>).mockResolvedValueOnce({ models: [], favoriteProviders: [], favoriteModels: [] });
|
||||
|
||||
render(<SettingsModal onClose={onClose} addToast={addToast} />);
|
||||
await waitFor(() => expect(fetchSettings).toHaveBeenCalled());
|
||||
@@ -1493,7 +1497,7 @@ describe("SettingsModal", () => {
|
||||
fireEvent.click(testButton);
|
||||
|
||||
await waitFor(() => expect(testNtfyNotification).toHaveBeenCalledTimes(1));
|
||||
expect(testNtfyNotification).toHaveBeenCalledWith({ ntfyEnabled: true, ntfyTopic: "my-valid-topic" });
|
||||
expect(testNtfyNotification).toHaveBeenCalledWith({ ntfyEnabled: true, ntfyTopic: "my-valid-topic" }, undefined);
|
||||
});
|
||||
|
||||
it("Success toast is shown when test notification succeeds", async () => {
|
||||
|
||||
@@ -621,7 +621,7 @@ describe("TaskCard clickable dependencies", () => {
|
||||
fireEvent.click(depBadge);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-001");
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-001", undefined);
|
||||
expect(onOpenDetail).toHaveBeenCalledWith(mockDetail);
|
||||
});
|
||||
});
|
||||
@@ -2384,7 +2384,7 @@ describe("TaskCard detail opening", () => {
|
||||
fireEvent.click(cardTitle);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-099");
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-099", undefined);
|
||||
expect(onOpenDetail).toHaveBeenCalledWith(mockDetail);
|
||||
});
|
||||
});
|
||||
@@ -2419,7 +2419,7 @@ describe("TaskCard detail opening", () => {
|
||||
fireEvent.click(screen.getByText("Test task"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-099");
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-099", undefined);
|
||||
expect(onOpenDetail).toHaveBeenCalledWith(mockDetail);
|
||||
expect(onOpenDetail).toHaveBeenCalledTimes(1);
|
||||
});
|
||||
|
||||
@@ -42,7 +42,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.change(screen.getByPlaceholderText(/Add a comment/), { target: { value: "Hello" } });
|
||||
fireEvent.click(screen.getByText("Add Comment"));
|
||||
|
||||
await waitFor(() => expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Hello", "user"));
|
||||
await waitFor(() => expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Hello", "user", undefined));
|
||||
expect(onTaskUpdated).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
@@ -55,7 +55,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.change(screen.getByDisplayValue("Original"), { target: { value: "Updated" } });
|
||||
fireEvent.click(screen.getByText("Save"));
|
||||
|
||||
await waitFor(() => expect(updateTaskComment).toHaveBeenCalledWith("FN-001", "c1", "Updated"));
|
||||
await waitFor(() => expect(updateTaskComment).toHaveBeenCalledWith("FN-001", "c1", "Updated", undefined));
|
||||
expect(onTaskUpdated).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
@@ -66,7 +66,7 @@ describe("TaskComments", () => {
|
||||
render(<TaskComments task={makeTask({ comments: [{ id: "c1", text: "Original", author: "user", createdAt: "2026-01-01T00:00:00.000Z" }] })} addToast={vi.fn()} onTaskUpdated={onTaskUpdated} />);
|
||||
fireEvent.click(screen.getByText("Delete"));
|
||||
|
||||
await waitFor(() => expect(deleteTaskComment).toHaveBeenCalledWith("FN-001", "c1"));
|
||||
await waitFor(() => expect(deleteTaskComment).toHaveBeenCalledWith("FN-001", "c1", undefined));
|
||||
expect(onTaskUpdated).toHaveBeenCalled();
|
||||
});
|
||||
|
||||
@@ -170,7 +170,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.click(screen.getByText("Add Guidance"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addSteeringComment).toHaveBeenCalledWith("FN-001", "Guidance text");
|
||||
expect(addSteeringComment).toHaveBeenCalledWith("FN-001", "Guidance text", undefined);
|
||||
expect(addTaskComment).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
@@ -187,7 +187,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.click(screen.getByText("Add Comment"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "User text", "user");
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "User text", "user", undefined);
|
||||
expect(addSteeringComment).not.toHaveBeenCalled();
|
||||
});
|
||||
});
|
||||
@@ -252,7 +252,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.keyDown(textarea, { key: "Enter", ctrlKey: true });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Keyboard", "user");
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Keyboard", "user", undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -268,7 +268,7 @@ describe("TaskComments", () => {
|
||||
fireEvent.keyDown(textarea, { key: "Enter", metaKey: true });
|
||||
|
||||
await waitFor(() => {
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Mac", "user");
|
||||
expect(addTaskComment).toHaveBeenCalledWith("FN-001", "Mac", "user", undefined);
|
||||
});
|
||||
});
|
||||
});
|
||||
|
||||
@@ -302,7 +302,7 @@ describe("TaskDetailModal", () => {
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpload).toHaveBeenCalledWith("FN-099", imageFile);
|
||||
expect(mockUpload).toHaveBeenCalledWith("FN-099", imageFile, undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Screenshot attached", "success");
|
||||
});
|
||||
});
|
||||
@@ -432,7 +432,7 @@ describe("TaskDetailModal", () => {
|
||||
});
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpload).toHaveBeenCalledWith("FN-099", imageFile);
|
||||
expect(mockUpload).toHaveBeenCalledWith("FN-099", imageFile, undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Screenshot attached", "success");
|
||||
});
|
||||
});
|
||||
@@ -502,7 +502,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(screen.getByText("FN-001"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: ["FN-001"] });
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: ["FN-001"] }, undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -525,7 +525,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(removeButtons[0]); // Remove KB-001
|
||||
|
||||
await waitFor(() => {
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: ["FN-002"] });
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: ["FN-002"] }, undefined);
|
||||
});
|
||||
});
|
||||
|
||||
@@ -1438,7 +1438,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(depLink);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-001");
|
||||
expect(mockFetch).toHaveBeenCalledWith("FN-001", undefined);
|
||||
expect(onOpenDetail).toHaveBeenCalledWith(mockDetail);
|
||||
});
|
||||
});
|
||||
@@ -1497,7 +1497,7 @@ describe("TaskDetailModal", () => {
|
||||
expect(onOpenDetail).not.toHaveBeenCalled();
|
||||
// updateTask should be called to remove the dependency
|
||||
await waitFor(() => {
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: [] });
|
||||
expect(updateTask).toHaveBeenCalledWith("FN-099", { dependencies: [] }, undefined);
|
||||
});
|
||||
});
|
||||
});
|
||||
@@ -1593,7 +1593,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(screen.getByText("Save"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockUpdate).toHaveBeenCalledWith("FN-099", { prompt: "# Updated" });
|
||||
expect(mockUpdate).toHaveBeenCalledWith("FN-099", { prompt: "# Updated" }, undefined);
|
||||
});
|
||||
|
||||
// Should return to view mode
|
||||
@@ -1646,7 +1646,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(screen.getByText("Request AI Revision"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(requestSpecRevision).toHaveBeenCalledWith("FN-099", "Please add more error handling details");
|
||||
expect(requestSpecRevision).toHaveBeenCalledWith("FN-099", "Please add more error handling details", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("AI revision requested. Task moved to triage.", "success");
|
||||
expect(onClose).toHaveBeenCalled();
|
||||
});
|
||||
@@ -1804,7 +1804,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(screen.getByText("Approve Plan"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockApprovePlan).toHaveBeenCalledWith("FN-001");
|
||||
expect(mockApprovePlan).toHaveBeenCalledWith("FN-001", undefined);
|
||||
});
|
||||
expect(addToast).toHaveBeenCalledWith("Plan approved — FN-001 moved to Todo", "success");
|
||||
expect(onClose).toHaveBeenCalled();
|
||||
@@ -1844,7 +1844,7 @@ describe("TaskDetailModal", () => {
|
||||
);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(mockRejectPlan).toHaveBeenCalledWith("FN-001");
|
||||
expect(mockRejectPlan).toHaveBeenCalledWith("FN-001", undefined);
|
||||
});
|
||||
expect(addToast).toHaveBeenCalledWith(
|
||||
"Plan rejected — FN-001 returned to Triage for re-specification",
|
||||
@@ -2393,7 +2393,7 @@ describe("TaskDetailModal", () => {
|
||||
fireEvent.click(screen.getByText("Create Refinement Task"));
|
||||
|
||||
await waitFor(() => {
|
||||
expect(refineTask).toHaveBeenCalledWith("FN-001", "Need to add more tests");
|
||||
expect(refineTask).toHaveBeenCalledWith("FN-001", "Need to add more tests", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Refinement task created: FN-002", "success");
|
||||
expect(onClose).toHaveBeenCalled();
|
||||
});
|
||||
@@ -2597,7 +2597,7 @@ describe("TaskDetailModal", () => {
|
||||
expect(mockUpdate).toHaveBeenCalledWith("FN-001", {
|
||||
title: "New title",
|
||||
description: "New description",
|
||||
});
|
||||
}, undefined);
|
||||
});
|
||||
});
|
||||
|
||||
|
||||
@@ -135,7 +135,7 @@ describe("WorkflowStepManager", () => {
|
||||
description: "New description",
|
||||
prompt: undefined,
|
||||
enabled: true,
|
||||
});
|
||||
}, undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Workflow step created", "success");
|
||||
});
|
||||
});
|
||||
@@ -167,7 +167,7 @@ describe("WorkflowStepManager", () => {
|
||||
await waitFor(() => {
|
||||
expect(updateWorkflowStep).toHaveBeenCalledWith("WS-001", expect.objectContaining({
|
||||
name: "Updated Name",
|
||||
}));
|
||||
}), undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Workflow step updated", "success");
|
||||
});
|
||||
});
|
||||
@@ -192,7 +192,7 @@ describe("WorkflowStepManager", () => {
|
||||
fireEvent.click(confirmBtn);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(deleteWorkflowStep).toHaveBeenCalledWith("WS-001");
|
||||
expect(deleteWorkflowStep).toHaveBeenCalledWith("WS-001", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Workflow step deleted", "success");
|
||||
});
|
||||
});
|
||||
@@ -216,7 +216,7 @@ describe("WorkflowStepManager", () => {
|
||||
fireEvent.click(refineBtn);
|
||||
|
||||
await waitFor(() => {
|
||||
expect(refineWorkflowStepPrompt).toHaveBeenCalledWith("WS-001");
|
||||
expect(refineWorkflowStepPrompt).toHaveBeenCalledWith("WS-001", undefined);
|
||||
expect(addToast).toHaveBeenCalledWith("Prompt refined with AI", "success");
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user