Files
automaker/libs/utils/tests/conversation-utils.test.ts
Kacper 30f4315c17 test: Add comprehensive tests for platform and utils packages
Added extensive test coverage for previously untested files:

Platform package (94.69% coverage, +47 tests):
- paths.test.ts: 22 tests for path construction and directory creation
- security.test.ts: 25 tests for path validation and security

Utils package (94.3% coverage, +109 tests):
- logger.test.ts: 23 tests for logging with levels
- fs-utils.test.ts: 20 tests for safe file operations
- conversation-utils.test.ts: 24 tests for message formatting
- image-handler.test.ts: 25 tests for image processing
- prompt-builder.test.ts: 17 tests for prompt construction

Coverage improvements:
- Platform: 63.71% → 94.69% stmts, 40% → 97.14% funcs
- Utils: 19.51% → 94.3% stmts, 18.51% → 100% funcs

Updated thresholds to enforce high quality:
- Platform: 90% lines/stmts, 95% funcs, 75% branches
- Utils: 90% lines/stmts, 95% funcs, 85% branches

Total new tests: 156 (platform: 47, utils: 109)
All tests passing with new coverage thresholds.

🤖 Generated with [Claude Code](https://claude.com/claude-code)

Co-Authored-By: Claude Sonnet 4.5 <noreply@anthropic.com>
2025-12-20 23:35:31 +01:00

262 lines
8.2 KiB
TypeScript

import { describe, it, expect } from "vitest";
import type { ConversationMessage } from "@automaker/types";
import {
extractTextFromContent,
normalizeContentBlocks,
formatHistoryAsText,
convertHistoryToMessages,
} from "../src/conversation-utils";
describe("conversation-utils.ts", () => {
describe("extractTextFromContent", () => {
it("should extract text from string content", () => {
const content = "Hello, world!";
const result = extractTextFromContent(content);
expect(result).toBe("Hello, world!");
});
it("should extract text from array content with text blocks", () => {
const content = [
{ type: "text", text: "First block" },
{ type: "text", text: "Second block" },
];
const result = extractTextFromContent(content);
expect(result).toBe("First block\nSecond block");
});
it("should filter out non-text blocks", () => {
const content = [
{ type: "text", text: "Text block" },
{ type: "image", source: { data: "..." } },
{ type: "text", text: "Another text" },
];
const result = extractTextFromContent(content);
expect(result).toBe("Text block\nAnother text");
});
it("should handle empty text blocks", () => {
const content = [
{ type: "text", text: "First" },
{ type: "text" },
{ type: "text", text: "Third" },
];
const result = extractTextFromContent(content);
expect(result).toBe("First\n\nThird");
});
it("should return empty string for array with only non-text blocks", () => {
const content = [
{ type: "image", source: {} },
{ type: "tool_use", source: {} },
];
const result = extractTextFromContent(content);
expect(result).toBe("");
});
it("should return empty string for empty array", () => {
const content: Array<{ type: string; text?: string }> = [];
const result = extractTextFromContent(content);
expect(result).toBe("");
});
});
describe("normalizeContentBlocks", () => {
it("should convert string to array of text blocks", () => {
const content = "Simple text";
const result = normalizeContentBlocks(content);
expect(result).toEqual([{ type: "text", text: "Simple text" }]);
});
it("should return array as-is", () => {
const content = [
{ type: "text", text: "First" },
{ type: "image", source: {} },
];
const result = normalizeContentBlocks(content);
expect(result).toBe(content);
expect(result).toEqual(content);
});
it("should handle empty string", () => {
const content = "";
const result = normalizeContentBlocks(content);
expect(result).toEqual([{ type: "text", text: "" }]);
});
it("should handle multiline string", () => {
const content = "Line 1\nLine 2\nLine 3";
const result = normalizeContentBlocks(content);
expect(result).toEqual([{ type: "text", text: "Line 1\nLine 2\nLine 3" }]);
});
});
describe("formatHistoryAsText", () => {
it("should format empty history as empty string", () => {
const history: ConversationMessage[] = [];
const result = formatHistoryAsText(history);
expect(result).toBe("");
});
it("should format single user message", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "Hello!" },
];
const result = formatHistoryAsText(history);
expect(result).toBe("Previous conversation:\n\nUser: Hello!\n\n---\n\n");
});
it("should format single assistant message", () => {
const history: ConversationMessage[] = [
{ role: "assistant", content: "Hi there!" },
];
const result = formatHistoryAsText(history);
expect(result).toBe(
"Previous conversation:\n\nAssistant: Hi there!\n\n---\n\n"
);
});
it("should format conversation with multiple messages", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "What's 2+2?" },
{ role: "assistant", content: "The answer is 4." },
{ role: "user", content: "Thanks!" },
];
const result = formatHistoryAsText(history);
expect(result).toBe(
"Previous conversation:\n\n" +
"User: What's 2+2?\n\n" +
"Assistant: The answer is 4.\n\n" +
"User: Thanks!\n\n" +
"---\n\n"
);
});
it("should handle array content by extracting text", () => {
const history: ConversationMessage[] = [
{
role: "user",
content: [
{ type: "text", text: "First part" },
{ type: "text", text: "Second part" },
],
},
];
const result = formatHistoryAsText(history);
expect(result).toBe(
"Previous conversation:\n\nUser: First part\nSecond part\n\n---\n\n"
);
});
it("should handle mixed string and array content", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "String message" },
{
role: "assistant",
content: [{ type: "text", text: "Array message" }],
},
];
const result = formatHistoryAsText(history);
expect(result).toContain("User: String message");
expect(result).toContain("Assistant: Array message");
});
});
describe("convertHistoryToMessages", () => {
it("should convert empty history", () => {
const history: ConversationMessage[] = [];
const result = convertHistoryToMessages(history);
expect(result).toEqual([]);
});
it("should convert single user message", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "Hello!" },
];
const result = convertHistoryToMessages(history);
expect(result).toHaveLength(1);
expect(result[0]).toMatchObject({
type: "user",
session_id: "",
message: {
role: "user",
content: [{ type: "text", text: "Hello!" }],
},
parent_tool_use_id: null,
});
});
it("should convert single assistant message", () => {
const history: ConversationMessage[] = [
{ role: "assistant", content: "Hi there!" },
];
const result = convertHistoryToMessages(history);
expect(result).toHaveLength(1);
expect(result[0]).toMatchObject({
type: "assistant",
session_id: "",
message: {
role: "assistant",
content: [{ type: "text", text: "Hi there!" }],
},
parent_tool_use_id: null,
});
});
it("should preserve array content as-is", () => {
const content = [
{ type: "text", text: "Text" },
{ type: "image", source: { data: "..." } },
];
const history: ConversationMessage[] = [{ role: "user", content }];
const result = convertHistoryToMessages(history);
expect(result[0].message.content).toEqual(content);
});
it("should convert multiple messages", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "First" },
{ role: "assistant", content: "Second" },
{ role: "user", content: "Third" },
];
const result = convertHistoryToMessages(history);
expect(result).toHaveLength(3);
expect(result[0].type).toBe("user");
expect(result[1].type).toBe("assistant");
expect(result[2].type).toBe("user");
});
it("should set session_id to empty string", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "Test" },
];
const result = convertHistoryToMessages(history);
expect(result[0].session_id).toBe("");
});
it("should set parent_tool_use_id to null", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "Test" },
];
const result = convertHistoryToMessages(history);
expect(result[0].parent_tool_use_id).toBeNull();
});
it("should normalize string content to blocks", () => {
const history: ConversationMessage[] = [
{ role: "user", content: "String content" },
];
const result = convertHistoryToMessages(history);
expect(result[0].message.content).toEqual([
{ type: "text", text: "String content" },
]);
});
});
});