mirror of
https://github.com/Significant-Gravitas/AutoGPT.git
synced 2026-04-30 03:00:41 -04:00
test(frontend/copilot): add tests for splitReasoningAndResponse and isReasoningToolPart
Covers: - isReasoningToolPart returns true for search/reasoning tools, false for action tools - splitReasoningAndResponse: all text (no tools) → all response - splitReasoningAndResponse: text + reasoning tools + text → proper split - splitReasoningAndResponse: text + action tools + text → all response (no split) - splitReasoningAndResponse: mixed reasoning + action tools → only reasoning triggers split - splitReasoningAndResponse: reasoning tools with no text after → all response - splitReasoningAndResponse: action tool after response text stays visible Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
This commit is contained in:
@@ -1,5 +1,29 @@
|
||||
import { describe, expect, it } from "vitest";
|
||||
import { extractWorkspaceArtifacts, filePartToArtifactRef } from "./helpers";
|
||||
import {
|
||||
extractWorkspaceArtifacts,
|
||||
filePartToArtifactRef,
|
||||
isReasoningToolPart,
|
||||
splitReasoningAndResponse,
|
||||
} from "./helpers";
|
||||
import type { MessagePart } from "./helpers";
|
||||
|
||||
function textPart(text: string): MessagePart {
|
||||
return { type: "text", text } as MessagePart;
|
||||
}
|
||||
|
||||
function toolPart(
|
||||
toolName: string,
|
||||
state: string = "output-available",
|
||||
): MessagePart {
|
||||
return {
|
||||
type: `tool-${toolName}`,
|
||||
state,
|
||||
toolCallId: `call-${toolName}`,
|
||||
toolName,
|
||||
args: {},
|
||||
output: "{}",
|
||||
} as unknown as MessagePart;
|
||||
}
|
||||
|
||||
describe("extractWorkspaceArtifacts", () => {
|
||||
it("extracts a single workspace:// link with its markdown title", () => {
|
||||
@@ -101,3 +125,130 @@ describe("filePartToArtifactRef", () => {
|
||||
expect(overridden?.origin).toBe("agent");
|
||||
});
|
||||
});
|
||||
|
||||
describe("isReasoningToolPart", () => {
|
||||
it("returns true for reasoning/search tools", () => {
|
||||
const reasoningTools = [
|
||||
"find_block",
|
||||
"find_agent",
|
||||
"find_library_agent",
|
||||
"search_docs",
|
||||
"get_doc_page",
|
||||
"search_feature_requests",
|
||||
"ask_question",
|
||||
];
|
||||
for (const name of reasoningTools) {
|
||||
expect(isReasoningToolPart(toolPart(name))).toBe(true);
|
||||
}
|
||||
});
|
||||
|
||||
it("returns false for action tools", () => {
|
||||
const actionTools = [
|
||||
"run_block",
|
||||
"run_agent",
|
||||
"create_agent",
|
||||
"edit_agent",
|
||||
"run_mcp_tool",
|
||||
"schedule_agent",
|
||||
"continue_run_block",
|
||||
];
|
||||
for (const name of actionTools) {
|
||||
expect(isReasoningToolPart(toolPart(name))).toBe(false);
|
||||
}
|
||||
});
|
||||
|
||||
it("returns false for text parts", () => {
|
||||
expect(isReasoningToolPart(textPart("hello"))).toBe(false);
|
||||
});
|
||||
});
|
||||
|
||||
describe("splitReasoningAndResponse", () => {
|
||||
it("returns all parts as response when there are no tools", () => {
|
||||
const parts = [textPart("Hello"), textPart("World")];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toEqual([]);
|
||||
expect(result.response).toEqual(parts);
|
||||
});
|
||||
|
||||
it("splits on reasoning tools — text before goes to reasoning", () => {
|
||||
const parts = [
|
||||
textPart("Let me search..."),
|
||||
toolPart("find_block"),
|
||||
textPart("Here is your answer"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toHaveLength(2);
|
||||
expect(result.response).toHaveLength(1);
|
||||
expect((result.response[0] as { text: string }).text).toBe(
|
||||
"Here is your answer",
|
||||
);
|
||||
});
|
||||
|
||||
it("does NOT split on action tools — response before run_block stays visible", () => {
|
||||
const parts = [
|
||||
textPart("Here is my answer"),
|
||||
toolPart("run_block"),
|
||||
textPart("Block finished"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toEqual([]);
|
||||
expect(result.response).toEqual(parts);
|
||||
});
|
||||
|
||||
it("splits only on reasoning tools when both reasoning and action tools are present", () => {
|
||||
const parts = [
|
||||
textPart("Planning..."),
|
||||
toolPart("search_docs"),
|
||||
textPart("Found it. Running now."),
|
||||
toolPart("run_block"),
|
||||
textPart("Done!"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toHaveLength(2);
|
||||
expect(result.response).toHaveLength(3);
|
||||
expect((result.response[0] as { text: string }).text).toBe(
|
||||
"Found it. Running now.",
|
||||
);
|
||||
});
|
||||
|
||||
it("returns all as response when reasoning tools have no text after them", () => {
|
||||
const parts = [
|
||||
textPart("Hello"),
|
||||
toolPart("find_agent"),
|
||||
toolPart("run_block"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toEqual([]);
|
||||
expect(result.response).toEqual(parts);
|
||||
});
|
||||
|
||||
it("handles multiple reasoning tools correctly", () => {
|
||||
const parts = [
|
||||
textPart("Searching..."),
|
||||
toolPart("find_block"),
|
||||
textPart("Found one, searching more..."),
|
||||
toolPart("search_docs"),
|
||||
textPart("Here are the results"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toHaveLength(4);
|
||||
expect(result.response).toHaveLength(1);
|
||||
expect((result.response[0] as { text: string }).text).toBe(
|
||||
"Here are the results",
|
||||
);
|
||||
});
|
||||
|
||||
it("handles action tool after response text without hiding the response", () => {
|
||||
const parts = [
|
||||
toolPart("find_block"),
|
||||
textPart("I found it! Let me run it."),
|
||||
toolPart("run_agent"),
|
||||
];
|
||||
const result = splitReasoningAndResponse(parts);
|
||||
expect(result.reasoning).toHaveLength(1);
|
||||
expect(result.response).toHaveLength(2);
|
||||
expect((result.response[0] as { text: string }).text).toBe(
|
||||
"I found it! Let me run it.",
|
||||
);
|
||||
});
|
||||
});
|
||||
|
||||
Reference in New Issue
Block a user