Skip to content

Commit 601a7a8

Browse files
Copilothotlong
andcommitted
Add snapshot tests for Phase 11-13 components (AgentProgress, FlowViewer, StateMachineViewer, CollaborationOverlay)
Co-authored-by: hotlong <50353452+hotlong@users.noreply.github.com>
1 parent 2590773 commit 601a7a8

File tree

8 files changed

+802
-0
lines changed

8 files changed

+802
-0
lines changed
Lines changed: 60 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,60 @@
1+
/**
2+
* Snapshot tests for the AgentProgress component.
3+
*/
4+
import React from "react";
5+
import { render } from "@testing-library/react-native";
6+
7+
import { AgentProgress } from "~/components/ai/AgentProgress";
8+
import type { AgentTask } from "~/hooks/useAgent";
9+
10+
/* ------------------------------------------------------------------ */
11+
/* Fixtures */
12+
/* ------------------------------------------------------------------ */
13+
14+
const baseTask: AgentTask = {
15+
id: "task-1",
16+
status: "running",
17+
progress: 50,
18+
agentId: "summarizer",
19+
createdAt: "2026-01-01T00:00:00Z",
20+
};
21+
22+
/* ------------------------------------------------------------------ */
23+
/* AgentProgress snapshots */
24+
/* ------------------------------------------------------------------ */
25+
26+
describe("AgentProgress", () => {
27+
it("renders null when task is null", () => {
28+
const tree = render(<AgentProgress task={null} />);
29+
expect(tree.toJSON()).toBeNull();
30+
});
31+
32+
it("renders running task with progress", () => {
33+
const tree = render(<AgentProgress task={baseTask} />);
34+
expect(tree.toJSON()).toMatchSnapshot();
35+
});
36+
37+
it("renders completed task", () => {
38+
const task: AgentTask = { ...baseTask, status: "completed", progress: 100 };
39+
const tree = render(<AgentProgress task={task} />);
40+
expect(tree.toJSON()).toMatchSnapshot();
41+
});
42+
43+
it("renders failed task with error", () => {
44+
const task: AgentTask = {
45+
...baseTask,
46+
status: "failed",
47+
progress: 30,
48+
error: "Agent timed out",
49+
};
50+
const tree = render(<AgentProgress task={task} />);
51+
expect(tree.toJSON()).toMatchSnapshot();
52+
});
53+
54+
it("renders cancel button when running and onCancel provided", () => {
55+
const tree = render(
56+
<AgentProgress task={baseTask} onCancel={jest.fn()} />,
57+
);
58+
expect(tree.toJSON()).toMatchSnapshot();
59+
});
60+
});
Lines changed: 50 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,50 @@
1+
/**
2+
* Snapshot tests for the CollaborationOverlay component.
3+
*/
4+
import React from "react";
5+
import { render } from "@testing-library/react-native";
6+
7+
import { CollaborationOverlay } from "~/components/realtime/CollaborationOverlay";
8+
import type { CollaborationParticipant } from "~/hooks/useCollaboration";
9+
10+
/* ------------------------------------------------------------------ */
11+
/* Fixtures */
12+
/* ------------------------------------------------------------------ */
13+
14+
const participants: CollaborationParticipant[] = [
15+
{
16+
userId: "user1",
17+
name: "Alice",
18+
cursor: { x: 100, y: 200, field: "title" },
19+
status: "active",
20+
color: "#3b82f6",
21+
lastSeen: "2026-01-01T00:00:00Z",
22+
},
23+
];
24+
25+
/* ------------------------------------------------------------------ */
26+
/* CollaborationOverlay snapshots */
27+
/* ------------------------------------------------------------------ */
28+
29+
describe("CollaborationOverlay", () => {
30+
it("renders null when no participants", () => {
31+
const tree = render(
32+
<CollaborationOverlay participants={[]} />,
33+
);
34+
expect(tree.toJSON()).toBeNull();
35+
});
36+
37+
it("renders participant cursors", () => {
38+
const tree = render(
39+
<CollaborationOverlay participants={participants} />,
40+
);
41+
expect(tree.toJSON()).toMatchSnapshot();
42+
});
43+
44+
it("renders without cursors when showCursors is false", () => {
45+
const tree = render(
46+
<CollaborationOverlay participants={participants} showCursors={false} />,
47+
);
48+
expect(tree.toJSON()).toMatchSnapshot();
49+
});
50+
});
Lines changed: 34 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
/**
2+
* Snapshot tests for the FlowViewer component.
3+
*/
4+
import React from "react";
5+
import { render } from "@testing-library/react-native";
6+
7+
import { FlowViewer } from "~/components/automation/FlowViewer";
8+
9+
/* ------------------------------------------------------------------ */
10+
/* Fixtures */
11+
/* ------------------------------------------------------------------ */
12+
13+
const nodes = [
14+
{ id: "1", type: "trigger", label: "Start" },
15+
{ id: "2", type: "action", label: "Send Email" },
16+
];
17+
18+
const edges = [{ id: "e1", source: "1", target: "2", label: "On Submit" }];
19+
20+
/* ------------------------------------------------------------------ */
21+
/* FlowViewer snapshots */
22+
/* ------------------------------------------------------------------ */
23+
24+
describe("FlowViewer", () => {
25+
it("renders empty state when no nodes", () => {
26+
const tree = render(<FlowViewer nodes={[]} edges={[]} />);
27+
expect(tree.toJSON()).toMatchSnapshot();
28+
});
29+
30+
it("renders nodes with edges", () => {
31+
const tree = render(<FlowViewer nodes={nodes} edges={edges} />);
32+
expect(tree.toJSON()).toMatchSnapshot();
33+
});
34+
});
Lines changed: 51 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,51 @@
1+
/**
2+
* Snapshot tests for the StateMachineViewer component.
3+
*/
4+
import React from "react";
5+
import { render } from "@testing-library/react-native";
6+
7+
import { StateMachineViewer } from "~/components/workflow/StateMachineViewer";
8+
9+
/* ------------------------------------------------------------------ */
10+
/* Fixtures */
11+
/* ------------------------------------------------------------------ */
12+
13+
const states = [
14+
{ name: "draft", type: "initial" as const, label: "Draft" },
15+
{ name: "published", type: "final" as const, label: "Published" },
16+
];
17+
18+
const transitions = [
19+
{ from: "draft", to: "published", event: "publish", label: "Publish" },
20+
];
21+
22+
/* ------------------------------------------------------------------ */
23+
/* StateMachineViewer snapshots */
24+
/* ------------------------------------------------------------------ */
25+
26+
describe("StateMachineViewer", () => {
27+
it("renders empty state when no states", () => {
28+
const tree = render(
29+
<StateMachineViewer states={[]} transitions={[]} />,
30+
);
31+
expect(tree.toJSON()).toMatchSnapshot();
32+
});
33+
34+
it("renders states with transitions", () => {
35+
const tree = render(
36+
<StateMachineViewer states={states} transitions={transitions} />,
37+
);
38+
expect(tree.toJSON()).toMatchSnapshot();
39+
});
40+
41+
it("highlights current state", () => {
42+
const tree = render(
43+
<StateMachineViewer
44+
states={states}
45+
transitions={transitions}
46+
currentState="draft"
47+
/>,
48+
);
49+
expect(tree.toJSON()).toMatchSnapshot();
50+
});
51+
});

0 commit comments

Comments
 (0)