Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
Original file line number Diff line number Diff line change
Expand Up @@ -29,6 +29,13 @@ vi.mock("../ProviderIcon", () => ({
vi.mock("../../hooks/useTaskDiffStats", () => ({
useTaskDiffStats: () => ({ stats: null, loading: false }),
}));
vi.mock("../../hooks/useToast", () => ({
useToast: () => ({
addToast: vi.fn(),
removeToast: vi.fn(),
toasts: [],
}),
}));

const noop = () => {};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,13 @@ vi.mock("../PluginSlot", () => ({
vi.mock("../../hooks/useTaskDiffStats", () => ({
useTaskDiffStats: () => ({ stats: null, loading: false }),
}));
vi.mock("../../hooks/useToast", () => ({
useToast: () => ({
addToast: vi.fn(),
removeToast: vi.fn(),
toasts: [],
}),
}));

const noop = () => {};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -60,6 +60,13 @@ vi.mock("../../api", () => ({
vi.mock("../../hooks/useConfirm", () => ({
useConfirm: () => ({ confirm: vi.fn(async () => true) }),
}));
vi.mock("../../hooks/useToast", () => ({
useToast: () => ({
addToast: vi.fn(),
removeToast: vi.fn(),
toasts: [],
}),
}));

const noop = () => {};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -35,14 +35,18 @@ describe("FN-4224 GitHub tracking header layout", () => {

const css = loadAllAppCss();

/*
FNXC:TaskDetailCSS 2026-07-08-13:00:
The github/gitlab tracking header rules were consolidated into a shared selector list (.detail-github-tracking-section .detail-source-header, .detail-gitlab-tracking-section .detail-source-header {…}), so the selector is no longer immediately followed by `{`. Allow the selector list (comma + sibling selector) between the tracked selector and the brace via [^{]* while still pinning the layout contract (flex-wrap/align-items/min-width).
*/
expect(css).toMatch(
/\.detail-github-tracking-section\s+\.detail-source-header\s*\{[^}]*flex-wrap:\s*nowrap;[^}]*align-items:\s*center;[^}]*min-width:\s*0;/,
/\.detail-github-tracking-section\s+\.detail-source-header[^{]*\{[^}]*flex-wrap:\s*nowrap;[^}]*align-items:\s*center;[^}]*min-width:\s*0;/,
);
expect(css).toMatch(
/\.detail-github-tracking-section\s+\.detail-source-summary\s*\{[^}]*flex:\s*1 1 auto;[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;/,
/\.detail-github-tracking-section\s+\.detail-source-summary[^{]*\{[^}]*flex:\s*1 1 auto;[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;/,
);
expect(css).toMatch(
/@media[^{]*\(max-width:\s*768px\)[^{]*\{[\s\S]*?\.detail-github-tracking-section\s+\.detail-source-header\s*\{[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;[^}]*\}[\s\S]*?\.detail-github-tracking-section\s+\.detail-source-summary\s*\{[^}]*flex:\s*1 1 auto;[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;[^}]*\}/,
/@media[^{]*\(max-width:\s*768px\)[^{]*\{[\s\S]*?\.detail-github-tracking-section\s+\.detail-source-header[^{]*\{[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;[^}]*\}[\s\S]*?\.detail-github-tracking-section\s+\.detail-source-summary[^{]*\{[^}]*flex:\s*1 1 auto;[^}]*flex-wrap:\s*nowrap;[^}]*min-width:\s*0;[^}]*\}/,
);
});
});
10 changes: 9 additions & 1 deletion packages/engine/src/__tests__/step-session-executor.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -1399,7 +1399,15 @@ describe("StepSessionExecutor", () => {
agentStore: { saveRun } as any,
} as any);

const results = await executor.executeAll();
// FNXC:EngineTests 2026-07-09-06:00:
// executeAll retries the failing step 3× with sleep() delays between attempts. With
// useFakeTimers({ shouldAdvanceTime: true }) these sleeps advance REAL wall-clock time if
// the test awaits executeAll directly (was 22.6s, ballooning under CI load and busting the
// shard-2 watchdog). Fast-forward the retry sleeps via fake timers like the sibling retry
// tests below, so the loop completes in milliseconds.
const resultsPromise = executor.executeAll();
await vi.advanceTimersByTimeAsync(60_000);
const results = await resultsPromise;

expect(results).toEqual([{ stepIndex: 0, success: false, error: "boom", retries: 3, tokenUsage: undefined }]);
const terminalRun = saveRun.mock.calls.at(-1)?.[0];
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,13 @@ import { cleanup, fireEvent, render, screen } from "@testing-library/react";
import type React from "react";
import type { Task } from "@fusion/core";
import { GraphTaskNode } from "../GraphTaskNode";
/*
FNXC:DependencyGraphTests 2026-07-08-13:10:
GraphTaskNode renders the REAL TaskCard; TaskCard's RuntimeFallbackBadge calls the dashboard's useToast() hook, and this file has no ToastProvider. Mock useToast (same as the dashboard's own TaskCard.test.tsx) to avoid "useToast must be used within ToastProvider".
*/
vi.mock("@fusion/dashboard/app/hooks/useToast", () => ({
useToast: () => ({ addToast: vi.fn(), removeToast: vi.fn(), toasts: [] }),
}));

function task(id = "FN-1"): Task {
return { id, description: id, column: "todo", dependencies: [], steps: [], currentStep: 0, log: [] } as Task;
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,13 @@ import type { Task } from "@fusion/core";
import { afterEach, describe, expect, it, vi } from "vitest";
import { TaskCard } from "@fusion/dashboard/app/components/TaskCard";
import { GraphTaskNode } from "../GraphTaskNode";
/*
FNXC:DependencyGraphTests 2026-07-08-13:10:
GraphTaskNode renders the REAL TaskCard (to verify prop pass-through), and TaskCard now renders RuntimeFallbackBadge which calls the dashboard's useToast() hook. This file has no ToastProvider, so mock useToast the same way the dashboard's own TaskCard.test.tsx does to avoid "useToast must be used within ToastProvider".
*/
vi.mock("@fusion/dashboard/app/hooks/useToast", () => ({
useToast: () => ({ addToast: vi.fn(), removeToast: vi.fn(), toasts: [] }),
}));

function createTask(overrides: Partial<Task> = {}): Task {
return {
Expand Down
Loading