




























@@ -10,6 +10,7 @@ import {
1010appendAssistantMessageToSessionTranscript,
1111appendExactAssistantMessageToSessionTranscript,
1212readLatestAssistantTextFromSessionTranscript,
13+readTailAssistantTextFromSessionTranscript,
1314} from "./transcript.js";
14151516describe("appendAssistantMessageToSessionTranscript", () => {
@@ -306,6 +307,80 @@ describe("appendAssistantMessageToSessionTranscript", () => {
306307}
307308});
308309310+it("skips transcript-only OpenClaw assistant entries when reading latest assistant text", async () => {
311+writeTranscriptStore();
312+313+const finalResult = await appendExactAssistantMessageToSessionTranscript({
314+ sessionKey,
315+storePath: fixture.storePath(),
316+message: createExactAssistantMessage({ text: "Complete final answer" }),
317+});
318+expect(finalResult.ok).toBe(true);
319+if (!finalResult.ok) {
320+return;
321+}
322+323+await appendAssistantMessageToSessionTranscript({
324+ sessionKey,
325+text: "Earlier retained preview",
326+storePath: fixture.storePath(),
327+});
328+await appendExactAssistantMessageToSessionTranscript({
329+ sessionKey,
330+storePath: fixture.storePath(),
331+message: createExactAssistantMessage({
332+text: "Injected transcript text",
333+provider: "openclaw",
334+model: "gateway-injected",
335+}),
336+});
337+338+const latestAssistantText = await readLatestAssistantTextFromSessionTranscript(
339+finalResult.sessionFile,
340+);
341+expect(latestAssistantText?.id).toBe(finalResult.messageId);
342+expect(latestAssistantText?.text).toBe("Complete final answer");
343+});
344+345+it("does not report transcript-only OpenClaw assistant entries as latest assistant text", async () => {
346+writeTranscriptStore();
347+348+const mirrorResult = await appendAssistantMessageToSessionTranscript({
349+ sessionKey,
350+text: "Only delivery mirror",
351+storePath: fixture.storePath(),
352+});
353+expect(mirrorResult.ok).toBe(true);
354+if (!mirrorResult.ok) {
355+return;
356+}
357+358+const latestAssistantText = await readLatestAssistantTextFromSessionTranscript(
359+mirrorResult.sessionFile,
360+);
361+expect(latestAssistantText).toBeUndefined();
362+});
363+364+it("keeps transcript-only OpenClaw assistant entries available to the tail reader", async () => {
365+writeTranscriptStore();
366+367+const mirrorResult = await appendAssistantMessageToSessionTranscript({
368+ sessionKey,
369+text: "Tail delivery mirror",
370+storePath: fixture.storePath(),
371+});
372+expect(mirrorResult.ok).toBe(true);
373+if (!mirrorResult.ok) {
374+return;
375+}
376+377+const tailAssistantText = await readTailAssistantTextFromSessionTranscript(
378+mirrorResult.sessionFile,
379+);
380+expect(tailAssistantText?.id).toBe(mirrorResult.messageId);
381+expect(tailAssistantText?.text).toBe("Tail delivery mirror");
382+});
383+309384it("does not reuse an older matching assistant message across turns", async () => {
310385writeTranscriptStore();
311386此内容由惯性聚合(RSS阅读器)自动聚合整理,仅供阅读参考。 原文来自 — 版权归原作者所有。