mirror of
https://github.com/AutoMaker-Org/automaker.git
synced 2026-02-03 08:53:36 +00:00
feat: enhance log parsing to support <summary> tags for structured output
- Introduced support for <summary> tags in log entries, allowing for better organization and parsing of summary content. - Updated the detectEntryType function to recognize <summary> tags as a preferred format for summaries. - Implemented summary accumulation logic to handle content between <summary> and </summary> tags. - Modified the prompt in auto-mode service to instruct users to wrap their summaries in <summary> tags for consistency in log output.
This commit is contained in:
@@ -156,6 +156,13 @@ function LogEntryItem({ entry, isExpanded, onToggle }: LogEntryItemProps) {
|
|||||||
content = content.trim();
|
content = content.trim();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// For summary entries, remove the <summary> and </summary> tags
|
||||||
|
if (entry.title === "Summary") {
|
||||||
|
content = content.replace(/^<summary>\s*/i, "");
|
||||||
|
content = content.replace(/\s*<\/summary>\s*$/i, "");
|
||||||
|
content = content.trim();
|
||||||
|
}
|
||||||
|
|
||||||
// Try to find and format JSON blocks
|
// Try to find and format JSON blocks
|
||||||
const jsonRegex = /(\{[\s\S]*?\}|\[[\s\S]*?\])/g;
|
const jsonRegex = /(\{[\s\S]*?\}|\[[\s\S]*?\])/g;
|
||||||
let lastIndex = 0;
|
let lastIndex = 0;
|
||||||
@@ -192,7 +199,7 @@ function LogEntryItem({ entry, isExpanded, onToggle }: LogEntryItemProps) {
|
|||||||
}
|
}
|
||||||
|
|
||||||
return parts.length > 0 ? parts : [{ type: "text" as const, content }];
|
return parts.length > 0 ? parts : [{ type: "text" as const, content }];
|
||||||
}, [entry.content, isToolCall]);
|
}, [entry.content, entry.title, isToolCall]);
|
||||||
|
|
||||||
// Get colors - use tool category colors for tool_call entries
|
// Get colors - use tool category colors for tool_call entries
|
||||||
const colorParts = toolCategoryColors.split(" ");
|
const colorParts = toolCategoryColors.split(" ");
|
||||||
|
|||||||
@@ -126,7 +126,9 @@ function detectEntryType(content: string): LogEntryType {
|
|||||||
trimmed.startsWith("✅") ||
|
trimmed.startsWith("✅") ||
|
||||||
trimmed.toLowerCase().includes("success") ||
|
trimmed.toLowerCase().includes("success") ||
|
||||||
trimmed.toLowerCase().includes("completed") ||
|
trimmed.toLowerCase().includes("completed") ||
|
||||||
// Markdown summary headers
|
// Summary tags (preferred format from agent)
|
||||||
|
trimmed.startsWith("<summary>") ||
|
||||||
|
// Markdown summary headers (fallback)
|
||||||
trimmed.match(/^##\s+(Summary|Feature|Changes|Implementation)/i) ||
|
trimmed.match(/^##\s+(Summary|Feature|Changes|Implementation)/i) ||
|
||||||
trimmed.match(/^(I've|I have) (successfully |now )?(completed|finished|implemented)/i)
|
trimmed.match(/^(I've|I have) (successfully |now )?(completed|finished|implemented)/i)
|
||||||
) {
|
) {
|
||||||
@@ -138,10 +140,11 @@ function detectEntryType(content: string): LogEntryType {
|
|||||||
return "warning";
|
return "warning";
|
||||||
}
|
}
|
||||||
|
|
||||||
// Thinking/Preparation info
|
// Thinking/Preparation info (be specific to avoid matching summary content)
|
||||||
if (
|
if (
|
||||||
trimmed.toLowerCase().includes("ultrathink") ||
|
trimmed.toLowerCase().includes("ultrathink") ||
|
||||||
trimmed.toLowerCase().includes("thinking level") ||
|
trimmed.match(/thinking level[:\s]*(low|medium|high|none|\d)/i) ||
|
||||||
|
trimmed.match(/^thinking level\s*$/i) ||
|
||||||
trimmed.toLowerCase().includes("estimated cost") ||
|
trimmed.toLowerCase().includes("estimated cost") ||
|
||||||
trimmed.toLowerCase().includes("estimated time") ||
|
trimmed.toLowerCase().includes("estimated time") ||
|
||||||
trimmed.toLowerCase().includes("budget tokens") ||
|
trimmed.toLowerCase().includes("budget tokens") ||
|
||||||
@@ -346,6 +349,9 @@ function generateTitle(type: LogEntryType, content: string): string {
|
|||||||
return "Error";
|
return "Error";
|
||||||
case "success": {
|
case "success": {
|
||||||
// Check if it's a summary section
|
// Check if it's a summary section
|
||||||
|
if (content.startsWith("<summary>") || content.includes("<summary>")) {
|
||||||
|
return "Summary";
|
||||||
|
}
|
||||||
if (content.match(/^##\s+(Summary|Feature|Changes|Implementation)/i)) {
|
if (content.match(/^##\s+(Summary|Feature|Changes|Implementation)/i)) {
|
||||||
return "Summary";
|
return "Summary";
|
||||||
}
|
}
|
||||||
@@ -420,6 +426,9 @@ export function parseLogOutput(rawOutput: string): LogEntry[] {
|
|||||||
let jsonBraceDepth = 0;
|
let jsonBraceDepth = 0;
|
||||||
let jsonBracketDepth = 0;
|
let jsonBracketDepth = 0;
|
||||||
|
|
||||||
|
// Summary tag accumulation state
|
||||||
|
let inSummaryAccumulation = false;
|
||||||
|
|
||||||
const finalizeEntry = () => {
|
const finalizeEntry = () => {
|
||||||
if (currentEntry && currentContent.length > 0) {
|
if (currentEntry && currentContent.length > 0) {
|
||||||
currentEntry.content = currentContent.join("\n").trim();
|
currentEntry.content = currentContent.join("\n").trim();
|
||||||
@@ -451,6 +460,7 @@ export function parseLogOutput(rawOutput: string): LogEntry[] {
|
|||||||
inJsonAccumulation = false;
|
inJsonAccumulation = false;
|
||||||
jsonBraceDepth = 0;
|
jsonBraceDepth = 0;
|
||||||
jsonBracketDepth = 0;
|
jsonBracketDepth = 0;
|
||||||
|
inSummaryAccumulation = false;
|
||||||
};
|
};
|
||||||
|
|
||||||
let lineIndex = 0;
|
let lineIndex = 0;
|
||||||
@@ -480,6 +490,18 @@ export function parseLogOutput(rawOutput: string): LogEntry[] {
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// If we're in summary accumulation mode, keep accumulating until </summary>
|
||||||
|
if (inSummaryAccumulation) {
|
||||||
|
currentContent.push(line);
|
||||||
|
// Summary is complete when we see closing tag
|
||||||
|
if (trimmedLine.includes("</summary>")) {
|
||||||
|
inSummaryAccumulation = false;
|
||||||
|
// Don't finalize here - let normal flow handle it
|
||||||
|
}
|
||||||
|
lineIndex++;
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
// Detect if this line starts a new entry
|
// Detect if this line starts a new entry
|
||||||
const lineType = detectEntryType(trimmedLine);
|
const lineType = detectEntryType(trimmedLine);
|
||||||
const isNewEntry =
|
const isNewEntry =
|
||||||
@@ -498,8 +520,10 @@ export function parseLogOutput(rawOutput: string): LogEntry[] {
|
|||||||
trimmedLine.match(/\[ERROR\]/i) ||
|
trimmedLine.match(/\[ERROR\]/i) ||
|
||||||
trimmedLine.match(/\[Status\]/i) ||
|
trimmedLine.match(/\[Status\]/i) ||
|
||||||
trimmedLine.toLowerCase().includes("ultrathink preparation") ||
|
trimmedLine.toLowerCase().includes("ultrathink preparation") ||
|
||||||
trimmedLine.toLowerCase().includes("thinking level") ||
|
trimmedLine.match(/thinking level[:\s]*(low|medium|high|none|\d)/i) ||
|
||||||
// Agent summary sections (markdown headers after tool calls)
|
// Summary tags (preferred format from agent)
|
||||||
|
trimmedLine.startsWith("<summary>") ||
|
||||||
|
// Agent summary sections (markdown headers - fallback)
|
||||||
trimmedLine.match(/^##\s+(Summary|Feature|Changes|Implementation)/i) ||
|
trimmedLine.match(/^##\s+(Summary|Feature|Changes|Implementation)/i) ||
|
||||||
// Summary introduction lines
|
// Summary introduction lines
|
||||||
trimmedLine.match(/^All tasks completed/i) ||
|
trimmedLine.match(/^All tasks completed/i) ||
|
||||||
@@ -526,6 +550,11 @@ export function parseLogOutput(rawOutput: string): LogEntry[] {
|
|||||||
},
|
},
|
||||||
};
|
};
|
||||||
currentContent.push(trimmedLine);
|
currentContent.push(trimmedLine);
|
||||||
|
|
||||||
|
// If this is a <summary> tag, start summary accumulation mode
|
||||||
|
if (trimmedLine.startsWith("<summary>") && !trimmedLine.includes("</summary>")) {
|
||||||
|
inSummaryAccumulation = true;
|
||||||
|
}
|
||||||
} else if (isInputLine && currentEntry) {
|
} else if (isInputLine && currentEntry) {
|
||||||
// Start JSON accumulation mode
|
// Start JSON accumulation mode
|
||||||
currentContent.push(trimmedLine);
|
currentContent.push(trimmedLine);
|
||||||
|
|||||||
@@ -1143,7 +1143,22 @@ Implement this feature by:
|
|||||||
4. Add or update tests as needed
|
4. Add or update tests as needed
|
||||||
5. Ensure the code follows existing patterns and conventions
|
5. Ensure the code follows existing patterns and conventions
|
||||||
|
|
||||||
When done, summarize what you implemented and any notes for the developer.`;
|
When done, wrap your final summary in <summary> tags like this:
|
||||||
|
|
||||||
|
<summary>
|
||||||
|
## Summary: [Feature Title]
|
||||||
|
|
||||||
|
### Changes Implemented
|
||||||
|
- [List of changes made]
|
||||||
|
|
||||||
|
### Files Modified
|
||||||
|
- [List of files]
|
||||||
|
|
||||||
|
### Notes for Developer
|
||||||
|
- [Any important notes]
|
||||||
|
</summary>
|
||||||
|
|
||||||
|
This helps parse your summary correctly in the output logs.`;
|
||||||
|
|
||||||
return prompt;
|
return prompt;
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user