Auto-reply: show tool results before main reply in verbose mode
parent
53c1674382
commit
16e42e6d6d
|
|
@ -300,7 +300,7 @@ export async function runCommandReply(
|
||||||
const parsed = trimmed ? agent.parseOutput(trimmed) : undefined;
|
const parsed = trimmed ? agent.parseOutput(trimmed) : undefined;
|
||||||
const parserProvided = !!parsed;
|
const parserProvided = !!parsed;
|
||||||
|
|
||||||
// Collect one message per assistant text from parseOutput (tau RPC can emit many).
|
// Collect assistant texts and tool results from parseOutput (tau RPC can emit many).
|
||||||
const parsedTexts =
|
const parsedTexts =
|
||||||
parsed?.texts?.map((t) => t.trim()).filter(Boolean) ?? [];
|
parsed?.texts?.map((t) => t.trim()).filter(Boolean) ?? [];
|
||||||
const parsedToolResults =
|
const parsedToolResults =
|
||||||
|
|
@ -309,15 +309,7 @@ export async function runCommandReply(
|
||||||
type ReplyItem = { text: string; media?: string[] };
|
type ReplyItem = { text: string; media?: string[] };
|
||||||
const replyItems: ReplyItem[] = [];
|
const replyItems: ReplyItem[] = [];
|
||||||
|
|
||||||
for (const t of parsedTexts) {
|
// When verbose is on, surface tool results first (before assistant summary) to mirror chat ordering.
|
||||||
const { text: cleanedText, mediaUrls: mediaFound } =
|
|
||||||
splitMediaFromOutput(t);
|
|
||||||
replyItems.push({
|
|
||||||
text: cleanedText,
|
|
||||||
media: mediaFound?.length ? mediaFound : undefined,
|
|
||||||
});
|
|
||||||
}
|
|
||||||
|
|
||||||
if (verboseLevel === "on") {
|
if (verboseLevel === "on") {
|
||||||
for (const tr of parsedToolResults) {
|
for (const tr of parsedToolResults) {
|
||||||
const prefixed = `🛠️ ${tr}`;
|
const prefixed = `🛠️ ${tr}`;
|
||||||
|
|
@ -330,6 +322,15 @@ export async function runCommandReply(
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
for (const t of parsedTexts) {
|
||||||
|
const { text: cleanedText, mediaUrls: mediaFound } =
|
||||||
|
splitMediaFromOutput(t);
|
||||||
|
replyItems.push({
|
||||||
|
text: cleanedText,
|
||||||
|
media: mediaFound?.length ? mediaFound : undefined,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
|
||||||
// If parser gave nothing, fall back to raw stdout as a single message.
|
// If parser gave nothing, fall back to raw stdout as a single message.
|
||||||
if (replyItems.length === 0 && trimmed && !parserProvided) {
|
if (replyItems.length === 0 && trimmed && !parserProvided) {
|
||||||
const { text: cleanedText, mediaUrls: mediaFound } =
|
const { text: cleanedText, mediaUrls: mediaFound } =
|
||||||
|
|
|
||||||
|
|
@ -744,10 +744,9 @@ describe("config and templating", () => {
|
||||||
expect(rpcSpy).toHaveBeenCalled();
|
expect(rpcSpy).toHaveBeenCalled();
|
||||||
const payloads = Array.isArray(res) ? res : res ? [res] : [];
|
const payloads = Array.isArray(res) ? res : res ? [res] : [];
|
||||||
expect(payloads.length).toBeGreaterThanOrEqual(2);
|
expect(payloads.length).toBeGreaterThanOrEqual(2);
|
||||||
expect(payloads[0]?.text).toContain("summary");
|
expect(payloads[0]?.text).toContain("🛠️");
|
||||||
expect(payloads.find((p) => p.text?.includes("🛠️"))?.text).toContain(
|
expect(payloads[0]?.text).toContain("ls output");
|
||||||
"ls output",
|
expect(payloads[1]?.text).toContain("summary");
|
||||||
);
|
|
||||||
});
|
});
|
||||||
|
|
||||||
it("prepends session hint when new session and verbose on", async () => {
|
it("prepends session hint when new session and verbose on", async () => {
|
||||||
|
|
|
||||||
Loading…
Reference in New Issue