Implement agent node functionality in canvas, including connection policies and UI updates. Add support for agent node type in node catalog, templates, and connection validation. Update documentation to reflect new agent capabilities and ensure proper handling of input sources. Enhance adjustment preview to include crop node. Add tests for agent connection policies.
This commit is contained in:
110
tests/agent-node.test.ts
Normal file
110
tests/agent-node.test.ts
Normal file
@@ -0,0 +1,110 @@
|
||||
// @vitest-environment jsdom
|
||||
|
||||
import React from "react";
|
||||
import { act } from "react";
|
||||
import { createRoot, type Root } from "react-dom/client";
|
||||
import { afterEach, beforeEach, describe, expect, it, vi } from "vitest";
|
||||
|
||||
const handleCalls: Array<{ type: string; id?: string }> = [];
|
||||
|
||||
vi.mock("@/components/canvas/nodes/base-node-wrapper", () => ({
|
||||
default: ({ children }: { children: React.ReactNode }) => React.createElement("div", null, children),
|
||||
}));
|
||||
|
||||
vi.mock("@xyflow/react", () => ({
|
||||
Handle: ({ type, id }: { type: string; id?: string }) => {
|
||||
handleCalls.push({ type, id });
|
||||
return React.createElement("div", {
|
||||
"data-handle-type": type,
|
||||
"data-handle-id": id,
|
||||
});
|
||||
},
|
||||
Position: { Left: "left", Right: "right" },
|
||||
}));
|
||||
|
||||
import AgentNode from "@/components/canvas/nodes/agent-node";
|
||||
|
||||
(globalThis as typeof globalThis & { IS_REACT_ACT_ENVIRONMENT?: boolean }).IS_REACT_ACT_ENVIRONMENT = true;
|
||||
|
||||
describe("AgentNode", () => {
|
||||
let container: HTMLDivElement | null = null;
|
||||
let root: Root | null = null;
|
||||
|
||||
beforeEach(() => {
|
||||
handleCalls.length = 0;
|
||||
});
|
||||
|
||||
afterEach(() => {
|
||||
if (root) {
|
||||
act(() => {
|
||||
root?.unmount();
|
||||
});
|
||||
}
|
||||
container?.remove();
|
||||
container = null;
|
||||
root = null;
|
||||
});
|
||||
|
||||
it("renders campaign distributor metadata and input-only handle", async () => {
|
||||
container = document.createElement("div");
|
||||
document.body.appendChild(container);
|
||||
root = createRoot(container);
|
||||
|
||||
await act(async () => {
|
||||
root?.render(
|
||||
React.createElement(AgentNode, {
|
||||
id: "agent-1",
|
||||
selected: false,
|
||||
dragging: false,
|
||||
draggable: true,
|
||||
selectable: true,
|
||||
deletable: true,
|
||||
zIndex: 1,
|
||||
isConnectable: true,
|
||||
type: "agent",
|
||||
data: {
|
||||
templateId: "campaign-distributor",
|
||||
_status: "idle",
|
||||
} as Record<string, unknown>,
|
||||
positionAbsoluteX: 0,
|
||||
positionAbsoluteY: 0,
|
||||
}),
|
||||
);
|
||||
});
|
||||
|
||||
expect(container.textContent).toContain("Campaign Distributor");
|
||||
expect(container.textContent).toContain("Instagram Feed");
|
||||
expect(container.textContent).toContain("Caption-Pakete");
|
||||
expect(handleCalls.filter((call) => call.type === "target")).toHaveLength(1);
|
||||
expect(handleCalls.filter((call) => call.type === "source")).toHaveLength(0);
|
||||
});
|
||||
|
||||
it("falls back to the default template when templateId is missing", async () => {
|
||||
container = document.createElement("div");
|
||||
document.body.appendChild(container);
|
||||
root = createRoot(container);
|
||||
|
||||
await act(async () => {
|
||||
root?.render(
|
||||
React.createElement(AgentNode, {
|
||||
id: "agent-2",
|
||||
selected: true,
|
||||
dragging: false,
|
||||
draggable: true,
|
||||
selectable: true,
|
||||
deletable: true,
|
||||
zIndex: 1,
|
||||
isConnectable: true,
|
||||
type: "agent",
|
||||
data: {
|
||||
_status: "done",
|
||||
} as Record<string, unknown>,
|
||||
positionAbsoluteX: 0,
|
||||
positionAbsoluteY: 0,
|
||||
}),
|
||||
);
|
||||
});
|
||||
|
||||
expect(container.textContent).toContain("Campaign Distributor");
|
||||
});
|
||||
});
|
||||
Reference in New Issue
Block a user