Spaces:
Paused
Paused
| import { describe, expect, it } from "vitest"; | |
| import { buildTranscript, type RunLogChunk } from "./transcript"; | |
| import type { UIAdapterModule } from "./types"; | |
| describe("buildTranscript", () => { | |
| const ts = "2026-03-20T13:00:00.000Z"; | |
| const chunks: RunLogChunk[] = [ | |
| { ts, stream: "stdout", chunk: "opened /Users/dotta/project\n" }, | |
| { ts, stream: "stderr", chunk: "stderr /Users/dotta/project" }, | |
| ]; | |
| it("defaults username censoring to off when options are omitted", () => { | |
| const entries = buildTranscript(chunks, (line, entryTs) => [{ kind: "stdout", ts: entryTs, text: line }]); | |
| expect(entries).toEqual([ | |
| { kind: "stdout", ts, text: "opened /Users/dotta/project" }, | |
| { kind: "stderr", ts, text: "stderr /Users/dotta/project" }, | |
| ]); | |
| }); | |
| it("still redacts usernames when explicitly enabled", () => { | |
| const entries = buildTranscript(chunks, (line, entryTs) => [{ kind: "stdout", ts: entryTs, text: line }], { | |
| censorUsernameInLogs: true, | |
| }); | |
| expect(entries).toEqual([ | |
| { kind: "stdout", ts, text: "opened /Users/d****/project" }, | |
| { kind: "stderr", ts, text: "stderr /Users/d****/project" }, | |
| ]); | |
| }); | |
| it("creates a fresh stateful parser for each transcript build", () => { | |
| const statefulAdapter: UIAdapterModule = { | |
| type: "stateful_test", | |
| label: "Stateful Test", | |
| parseStdoutLine: (line, entryTs) => [{ kind: "stdout", ts: entryTs, text: line }], | |
| createStdoutParser: () => { | |
| let pending: string | null = null; | |
| return { | |
| parseLine: (line, entryTs) => { | |
| if (line.startsWith("begin:")) { | |
| pending = line.slice("begin:".length); | |
| return []; | |
| } | |
| if (line === "finish" && pending) { | |
| const text = `completed:${pending}`; | |
| pending = null; | |
| return [{ kind: "stdout", ts: entryTs, text }]; | |
| } | |
| return [{ kind: "stdout", ts: entryTs, text: `literal:${line}` }]; | |
| }, | |
| reset: () => { | |
| pending = null; | |
| }, | |
| }; | |
| }, | |
| ConfigFields: () => null, | |
| buildAdapterConfig: () => ({}), | |
| }; | |
| const first = buildTranscript( | |
| [{ ts, stream: "stdout", chunk: "begin:task-a\n" }], | |
| statefulAdapter, | |
| ); | |
| const second = buildTranscript( | |
| [{ ts, stream: "stdout", chunk: "finish\n" }], | |
| statefulAdapter, | |
| ); | |
| expect(first).toEqual([]); | |
| expect(second).toEqual([{ kind: "stdout", ts, text: "literal:finish" }]); | |
| }); | |
| }); | |