wave-agent-sdk 0.4.0 → 0.5.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/dist/agent.d.ts +28 -5
- package/dist/agent.d.ts.map +1 -1
- package/dist/agent.js +54 -37
- package/dist/constants/tools.d.ts +2 -2
- package/dist/constants/tools.js +2 -2
- package/dist/managers/MemoryRuleManager.js +1 -1
- package/dist/managers/aiManager.d.ts +3 -3
- package/dist/managers/aiManager.d.ts.map +1 -1
- package/dist/managers/aiManager.js +3 -4
- package/dist/managers/backgroundBashManager.d.ts.map +1 -1
- package/dist/managers/backgroundBashManager.js +1 -0
- package/dist/managers/backgroundTaskManager.d.ts +35 -0
- package/dist/managers/backgroundTaskManager.d.ts.map +1 -0
- package/dist/managers/backgroundTaskManager.js +249 -0
- package/dist/managers/foregroundTaskManager.d.ts +9 -0
- package/dist/managers/foregroundTaskManager.d.ts.map +1 -0
- package/dist/managers/foregroundTaskManager.js +20 -0
- package/dist/managers/liveConfigManager.d.ts +1 -1
- package/dist/managers/lspManager.d.ts.map +1 -1
- package/dist/managers/lspManager.js +3 -1
- package/dist/managers/messageManager.d.ts +12 -2
- package/dist/managers/messageManager.d.ts.map +1 -1
- package/dist/managers/messageManager.js +36 -2
- package/dist/managers/permissionManager.d.ts.map +1 -1
- package/dist/managers/permissionManager.js +1 -7
- package/dist/managers/pluginManager.d.ts.map +1 -1
- package/dist/managers/pluginManager.js +3 -2
- package/dist/managers/slashCommandManager.d.ts +3 -0
- package/dist/managers/slashCommandManager.d.ts.map +1 -1
- package/dist/managers/slashCommandManager.js +1 -0
- package/dist/managers/subagentManager.d.ts +11 -2
- package/dist/managers/subagentManager.d.ts.map +1 -1
- package/dist/managers/subagentManager.js +137 -39
- package/dist/managers/toolManager.d.ts +7 -1
- package/dist/managers/toolManager.d.ts.map +1 -1
- package/dist/managers/toolManager.js +9 -3
- package/dist/services/GitService.d.ts.map +1 -1
- package/dist/services/GitService.js +6 -2
- package/dist/services/MarketplaceService.d.ts +2 -2
- package/dist/services/MarketplaceService.d.ts.map +1 -1
- package/dist/services/MarketplaceService.js +18 -11
- package/dist/services/MemoryRuleService.d.ts +1 -1
- package/dist/services/MemoryRuleService.d.ts.map +1 -1
- package/dist/services/MemoryRuleService.js +13 -2
- package/dist/services/memory.js +1 -1
- package/dist/tools/bashTool.d.ts +0 -8
- package/dist/tools/bashTool.d.ts.map +1 -1
- package/dist/tools/bashTool.js +44 -172
- package/dist/tools/editTool.d.ts.map +1 -1
- package/dist/tools/editTool.js +6 -5
- package/dist/tools/multiEditTool.d.ts.map +1 -1
- package/dist/tools/multiEditTool.js +7 -6
- package/dist/tools/taskOutputTool.d.ts +3 -0
- package/dist/tools/taskOutputTool.d.ts.map +1 -0
- package/dist/tools/taskOutputTool.js +149 -0
- package/dist/tools/taskStopTool.d.ts +3 -0
- package/dist/tools/taskStopTool.d.ts.map +1 -0
- package/dist/tools/taskStopTool.js +65 -0
- package/dist/tools/taskTool.d.ts.map +1 -1
- package/dist/tools/taskTool.js +105 -63
- package/dist/tools/types.d.ts +3 -0
- package/dist/tools/types.d.ts.map +1 -1
- package/dist/types/marketplace.d.ts +1 -0
- package/dist/types/marketplace.d.ts.map +1 -1
- package/dist/types/messaging.d.ts +1 -0
- package/dist/types/messaging.d.ts.map +1 -1
- package/dist/types/processes.d.ts +24 -4
- package/dist/types/processes.d.ts.map +1 -1
- package/dist/utils/editUtils.d.ts +2 -11
- package/dist/utils/editUtils.d.ts.map +1 -1
- package/dist/utils/editUtils.js +52 -79
- package/dist/utils/messageOperations.d.ts +3 -1
- package/dist/utils/messageOperations.d.ts.map +1 -1
- package/dist/utils/messageOperations.js +5 -1
- package/package.json +5 -5
- package/src/agent.ts +73 -45
- package/src/constants/tools.ts +2 -2
- package/src/managers/MemoryRuleManager.ts +1 -1
- package/src/managers/aiManager.ts +6 -9
- package/src/managers/backgroundBashManager.ts +1 -0
- package/src/managers/backgroundTaskManager.ts +306 -0
- package/src/managers/foregroundTaskManager.ts +26 -0
- package/src/managers/lspManager.ts +3 -1
- package/src/managers/messageManager.ts +48 -2
- package/src/managers/permissionManager.ts +1 -7
- package/src/managers/pluginManager.ts +4 -3
- package/src/managers/slashCommandManager.ts +4 -0
- package/src/managers/subagentManager.ts +167 -35
- package/src/managers/toolManager.ts +16 -4
- package/src/services/GitService.ts +6 -2
- package/src/services/MarketplaceService.ts +30 -12
- package/src/services/MemoryRuleService.ts +18 -6
- package/src/services/memory.ts +1 -1
- package/src/tools/bashTool.ts +59 -196
- package/src/tools/editTool.ts +6 -17
- package/src/tools/multiEditTool.ts +7 -18
- package/src/tools/taskOutputTool.ts +174 -0
- package/src/tools/taskStopTool.ts +72 -0
- package/src/tools/taskTool.ts +130 -74
- package/src/tools/types.ts +3 -0
- package/src/types/marketplace.ts +1 -0
- package/src/types/messaging.ts +1 -0
- package/src/types/processes.ts +33 -4
- package/src/utils/editUtils.ts +65 -103
- package/src/utils/messageOperations.ts +7 -0
package/src/tools/taskTool.ts
CHANGED
|
@@ -46,6 +46,11 @@ export function createTaskTool(subagentManager: SubagentManager): ToolPlugin {
|
|
|
46
46
|
type: "string",
|
|
47
47
|
description: `The type or name of subagent to use. Available options: ${availableSubagents.map((c) => c.name).join(", ") || "none"}`,
|
|
48
48
|
},
|
|
49
|
+
run_in_background: {
|
|
50
|
+
type: "boolean",
|
|
51
|
+
description:
|
|
52
|
+
"Set to true to run this command in the background. Use TaskOutput to read the output later.",
|
|
53
|
+
},
|
|
49
54
|
},
|
|
50
55
|
required: ["description", "prompt", "subagent_type"],
|
|
51
56
|
},
|
|
@@ -57,80 +62,131 @@ export function createTaskTool(subagentManager: SubagentManager): ToolPlugin {
|
|
|
57
62
|
args: Record<string, unknown>,
|
|
58
63
|
context: ToolContext,
|
|
59
64
|
): Promise<ToolResult> => {
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
77
|
-
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
|
|
88
|
-
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
103
|
-
|
|
104
|
-
|
|
105
|
-
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
114
|
-
|
|
115
|
-
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
65
|
+
return new Promise((resolve) => {
|
|
66
|
+
(async () => {
|
|
67
|
+
// Input validation
|
|
68
|
+
const description = args.description as string;
|
|
69
|
+
const prompt = args.prompt as string;
|
|
70
|
+
const subagent_type = args.subagent_type as string;
|
|
71
|
+
const run_in_background = args.run_in_background as boolean;
|
|
72
|
+
|
|
73
|
+
if (!description || typeof description !== "string") {
|
|
74
|
+
return resolve({
|
|
75
|
+
success: false,
|
|
76
|
+
content: "",
|
|
77
|
+
error: "description parameter is required and must be a string",
|
|
78
|
+
shortResult: "Task delegation failed",
|
|
79
|
+
});
|
|
80
|
+
}
|
|
81
|
+
|
|
82
|
+
if (!prompt || typeof prompt !== "string") {
|
|
83
|
+
return resolve({
|
|
84
|
+
success: false,
|
|
85
|
+
content: "",
|
|
86
|
+
error: "prompt parameter is required and must be a string",
|
|
87
|
+
shortResult: "Task delegation failed",
|
|
88
|
+
});
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
if (!subagent_type || typeof subagent_type !== "string") {
|
|
92
|
+
return resolve({
|
|
93
|
+
success: false,
|
|
94
|
+
content: "",
|
|
95
|
+
error: "subagent_type parameter is required and must be a string",
|
|
96
|
+
shortResult: "Task delegation failed",
|
|
97
|
+
});
|
|
98
|
+
}
|
|
99
|
+
|
|
100
|
+
try {
|
|
101
|
+
// Subagent selection logic with explicit name matching only
|
|
102
|
+
const configuration =
|
|
103
|
+
await subagentManager.findSubagent(subagent_type);
|
|
104
|
+
|
|
105
|
+
if (!configuration) {
|
|
106
|
+
// Error handling for nonexistent subagents with available subagents listing
|
|
107
|
+
const allConfigs = subagentManager.getConfigurations();
|
|
108
|
+
const availableNames = allConfigs.map((c) => c.name).join(", ");
|
|
109
|
+
|
|
110
|
+
return resolve({
|
|
111
|
+
success: false,
|
|
112
|
+
content: "",
|
|
113
|
+
error: `No subagent found matching "${subagent_type}". Available subagents: ${availableNames || "none"}`,
|
|
114
|
+
shortResult: "Subagent not found",
|
|
115
|
+
});
|
|
116
|
+
}
|
|
117
|
+
|
|
118
|
+
// Create subagent instance and execute task
|
|
119
|
+
const instance = await subagentManager.createInstance(
|
|
120
|
+
configuration,
|
|
121
|
+
{
|
|
122
|
+
description,
|
|
123
|
+
prompt,
|
|
124
|
+
subagent_type,
|
|
125
|
+
},
|
|
126
|
+
run_in_background,
|
|
127
|
+
);
|
|
128
|
+
|
|
129
|
+
let isBackgrounded = false;
|
|
130
|
+
|
|
131
|
+
// Register for backgrounding if not already in background
|
|
132
|
+
if (!run_in_background && context.foregroundTaskManager) {
|
|
133
|
+
context.foregroundTaskManager.registerForegroundTask({
|
|
134
|
+
id: instance.subagentId,
|
|
135
|
+
backgroundHandler: async () => {
|
|
136
|
+
isBackgrounded = true;
|
|
137
|
+
const taskId = await subagentManager.backgroundInstance(
|
|
138
|
+
instance.subagentId,
|
|
139
|
+
);
|
|
140
|
+
// Resolve the tool execution early so the main agent can continue
|
|
141
|
+
resolve({
|
|
142
|
+
success: true,
|
|
143
|
+
content: `Task moved to background with ID: ${taskId}. Use TaskOutput to monitor progress.`,
|
|
144
|
+
shortResult: "Task backgrounded",
|
|
145
|
+
});
|
|
146
|
+
},
|
|
147
|
+
});
|
|
148
|
+
}
|
|
149
|
+
|
|
150
|
+
try {
|
|
151
|
+
const result = await subagentManager.executeTask(
|
|
152
|
+
instance,
|
|
153
|
+
prompt,
|
|
154
|
+
context.abortSignal,
|
|
155
|
+
run_in_background,
|
|
156
|
+
);
|
|
157
|
+
|
|
158
|
+
if (isBackgrounded) return;
|
|
159
|
+
|
|
160
|
+
if (run_in_background) {
|
|
161
|
+
return resolve({
|
|
162
|
+
success: true,
|
|
163
|
+
content: `Task started in background with ID: ${result}`,
|
|
164
|
+
shortResult: `Task started in background: ${result}`,
|
|
165
|
+
});
|
|
166
|
+
}
|
|
167
|
+
|
|
168
|
+
return resolve({
|
|
169
|
+
success: true,
|
|
170
|
+
content: result,
|
|
171
|
+
shortResult: `Task completed by ${configuration.name}`,
|
|
172
|
+
});
|
|
173
|
+
} finally {
|
|
174
|
+
if (!run_in_background && context.foregroundTaskManager) {
|
|
175
|
+
context.foregroundTaskManager.unregisterForegroundTask(
|
|
176
|
+
instance.subagentId,
|
|
177
|
+
);
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
} catch (error) {
|
|
181
|
+
return resolve({
|
|
182
|
+
success: false,
|
|
183
|
+
content: "",
|
|
184
|
+
error: `Task delegation failed: ${error instanceof Error ? error.message : String(error)}`,
|
|
185
|
+
shortResult: "Delegation error",
|
|
186
|
+
});
|
|
187
|
+
}
|
|
188
|
+
})();
|
|
189
|
+
});
|
|
134
190
|
},
|
|
135
191
|
|
|
136
192
|
formatCompactParams: (params: Record<string, unknown>) => {
|
package/src/tools/types.ts
CHANGED
|
@@ -39,6 +39,7 @@ export interface ToolResult {
|
|
|
39
39
|
export interface ToolContext {
|
|
40
40
|
abortSignal?: AbortSignal;
|
|
41
41
|
backgroundBashManager?: import("../managers/backgroundBashManager.js").BackgroundBashManager;
|
|
42
|
+
backgroundTaskManager?: import("../managers/backgroundTaskManager.js").BackgroundTaskManager;
|
|
42
43
|
workdir: string;
|
|
43
44
|
/** Permission mode for this tool execution */
|
|
44
45
|
permissionMode?: PermissionMode;
|
|
@@ -54,4 +55,6 @@ export interface ToolContext {
|
|
|
54
55
|
reversionManager?: import("../managers/reversionManager.js").ReversionManager;
|
|
55
56
|
/** Current message ID for associating snapshots */
|
|
56
57
|
messageId?: string;
|
|
58
|
+
/** Foreground task manager for backgrounding tasks */
|
|
59
|
+
foregroundTaskManager?: import("../types/processes.js").IForegroundTaskManager;
|
|
57
60
|
}
|
package/src/types/marketplace.ts
CHANGED
package/src/types/messaging.ts
CHANGED
package/src/types/processes.ts
CHANGED
|
@@ -5,14 +5,43 @@
|
|
|
5
5
|
|
|
6
6
|
import type { ChildProcess } from "child_process";
|
|
7
7
|
|
|
8
|
-
export
|
|
8
|
+
export type BackgroundTaskStatus =
|
|
9
|
+
| "running"
|
|
10
|
+
| "completed"
|
|
11
|
+
| "failed"
|
|
12
|
+
| "killed";
|
|
13
|
+
export type BackgroundTaskType = "shell" | "subagent";
|
|
14
|
+
|
|
15
|
+
export interface BackgroundTask {
|
|
9
16
|
id: string;
|
|
10
|
-
|
|
11
|
-
|
|
17
|
+
type: BackgroundTaskType;
|
|
18
|
+
status: BackgroundTaskStatus;
|
|
12
19
|
startTime: number;
|
|
13
|
-
|
|
20
|
+
endTime?: number;
|
|
21
|
+
command?: string; // for shell
|
|
22
|
+
description?: string; // for subagent
|
|
14
23
|
stdout: string;
|
|
15
24
|
stderr: string;
|
|
16
25
|
exitCode?: number;
|
|
17
26
|
runtime?: number;
|
|
18
27
|
}
|
|
28
|
+
|
|
29
|
+
export interface BackgroundShell extends BackgroundTask {
|
|
30
|
+
type: "shell";
|
|
31
|
+
process: ChildProcess;
|
|
32
|
+
}
|
|
33
|
+
|
|
34
|
+
export interface ForegroundTask {
|
|
35
|
+
id: string;
|
|
36
|
+
backgroundHandler: () => Promise<void>;
|
|
37
|
+
}
|
|
38
|
+
|
|
39
|
+
export interface IForegroundTaskManager {
|
|
40
|
+
registerForegroundTask(task: ForegroundTask): void;
|
|
41
|
+
unregisterForegroundTask(id: string): void;
|
|
42
|
+
}
|
|
43
|
+
|
|
44
|
+
export interface IForegroundTaskManager {
|
|
45
|
+
registerForegroundTask(task: ForegroundTask): void;
|
|
46
|
+
unregisterForegroundTask(id: string): void;
|
|
47
|
+
}
|
package/src/utils/editUtils.ts
CHANGED
|
@@ -1,128 +1,90 @@
|
|
|
1
|
-
import { mkdir, writeFile } from "fs/promises";
|
|
2
|
-
import path from "path";
|
|
3
|
-
import os from "os";
|
|
4
|
-
import { logger } from "./globalLogger.js";
|
|
5
|
-
|
|
6
1
|
/**
|
|
7
2
|
* Utility functions for file editing tools
|
|
8
3
|
*/
|
|
9
4
|
|
|
10
5
|
/**
|
|
11
|
-
*
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
6
|
+
* Escape regular expression special characters
|
|
7
|
+
*/
|
|
8
|
+
export function escapeRegExp(string: string): string {
|
|
9
|
+
return string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
10
|
+
}
|
|
11
|
+
|
|
12
|
+
/**
|
|
13
|
+
* Analyze why an edit failed by finding the best partial match and highlighting mismatches.
|
|
17
14
|
*/
|
|
18
|
-
export function
|
|
15
|
+
export function analyzeEditMismatch(
|
|
19
16
|
content: string,
|
|
20
17
|
searchString: string,
|
|
21
|
-
): string
|
|
22
|
-
|
|
23
|
-
if (content.includes(searchString)) {
|
|
24
|
-
return searchString;
|
|
25
|
-
}
|
|
26
|
-
|
|
18
|
+
): string {
|
|
19
|
+
const contentLines = content.split("\n");
|
|
27
20
|
const searchLines = searchString.split("\n");
|
|
28
|
-
if (searchLines.length === 0) return null;
|
|
29
21
|
|
|
30
|
-
|
|
31
|
-
|
|
22
|
+
if (searchLines.length === 0 || contentLines.length === 0) {
|
|
23
|
+
return "old_string not found in file (empty search or content)";
|
|
24
|
+
}
|
|
32
25
|
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
let isMatch = true;
|
|
26
|
+
let bestMatchIndex = -1;
|
|
27
|
+
let bestMatchScore = -1;
|
|
36
28
|
|
|
29
|
+
// Sliding window to find the best partial match
|
|
30
|
+
for (let i = 0; i <= contentLines.length - searchLines.length; i++) {
|
|
31
|
+
let currentScore = 0;
|
|
37
32
|
for (let j = 0; j < searchLines.length; j++) {
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
const sTrimmed = sLine.trimStart();
|
|
42
|
-
const cTrimmed = cLine.trimStart();
|
|
43
|
-
|
|
44
|
-
// If trimmed content doesn't match, it's not a match
|
|
45
|
-
if (sTrimmed !== cTrimmed) {
|
|
46
|
-
isMatch = false;
|
|
47
|
-
break;
|
|
33
|
+
if (contentLines[i + j] === searchLines[j]) {
|
|
34
|
+
currentScore++;
|
|
48
35
|
}
|
|
36
|
+
}
|
|
49
37
|
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
|
|
38
|
+
// Heuristic: prioritize matches where first or last lines match
|
|
39
|
+
if (contentLines[i] === searchLines[0]) currentScore += 0.5;
|
|
40
|
+
if (
|
|
41
|
+
contentLines[i + searchLines.length - 1] ===
|
|
42
|
+
searchLines[searchLines.length - 1]
|
|
43
|
+
)
|
|
44
|
+
currentScore += 0.5;
|
|
55
45
|
|
|
56
|
-
|
|
57
|
-
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
46
|
+
// Also consider trimmed matches to catch indentation issues
|
|
47
|
+
for (let j = 0; j < searchLines.length; j++) {
|
|
48
|
+
if (
|
|
49
|
+
contentLines[i + j].trim() === searchLines[j].trim() &&
|
|
50
|
+
contentLines[i + j] !== searchLines[j]
|
|
51
|
+
) {
|
|
52
|
+
currentScore += 0.1;
|
|
62
53
|
}
|
|
63
54
|
}
|
|
64
55
|
|
|
65
|
-
if (
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
.join("\n");
|
|
69
|
-
if (foundMatch !== null && foundMatch !== matchCandidate) {
|
|
70
|
-
// Multiple different smart matches found
|
|
71
|
-
return null;
|
|
72
|
-
}
|
|
73
|
-
foundMatch = matchCandidate;
|
|
56
|
+
if (currentScore > bestMatchScore) {
|
|
57
|
+
bestMatchScore = currentScore;
|
|
58
|
+
bestMatchIndex = i;
|
|
74
59
|
}
|
|
75
60
|
}
|
|
76
61
|
|
|
77
|
-
// If
|
|
78
|
-
|
|
79
|
-
|
|
80
|
-
}
|
|
81
|
-
|
|
82
|
-
/**
|
|
83
|
-
* Escape regular expression special characters
|
|
84
|
-
*/
|
|
85
|
-
export function escapeRegExp(string: string): string {
|
|
86
|
-
return string.replace(/[.*+?^${}()|[\]\\]/g, "\\$&");
|
|
87
|
-
}
|
|
88
|
-
|
|
89
|
-
/**
|
|
90
|
-
* Save a snapshot of the old string and current file content for debugging
|
|
91
|
-
*/
|
|
92
|
-
export async function saveEditErrorSnapshot(
|
|
93
|
-
filePath: string,
|
|
94
|
-
oldString: string,
|
|
95
|
-
currentContent: string,
|
|
96
|
-
toolName: string,
|
|
97
|
-
): Promise<string | null> {
|
|
98
|
-
try {
|
|
99
|
-
const timestamp = new Date().toISOString().replace(/[:.]/g, "-");
|
|
100
|
-
const fileName = path.basename(filePath);
|
|
101
|
-
const snapshotDirName = `${timestamp}_${toolName}_${fileName}`;
|
|
102
|
-
const snapshotDir = path.join(
|
|
103
|
-
os.tmpdir(),
|
|
104
|
-
"wave-agent-edit-errors",
|
|
105
|
-
snapshotDirName,
|
|
106
|
-
);
|
|
107
|
-
|
|
108
|
-
await mkdir(snapshotDir, { recursive: true });
|
|
109
|
-
|
|
110
|
-
await Promise.all([
|
|
111
|
-
writeFile(path.join(snapshotDir, "old_string.txt"), oldString, "utf-8"),
|
|
112
|
-
writeFile(
|
|
113
|
-
path.join(snapshotDir, "file_content.txt"),
|
|
114
|
-
currentContent,
|
|
115
|
-
"utf-8",
|
|
116
|
-
),
|
|
117
|
-
]);
|
|
118
|
-
|
|
119
|
-
logger.error(
|
|
120
|
-
`Edit error snapshot saved to: ${snapshotDir}\nFile: ${filePath}\nTool: ${toolName}`,
|
|
121
|
-
);
|
|
62
|
+
// If no decent match found (score <= 0), return generic message
|
|
63
|
+
if (bestMatchScore <= 0) {
|
|
64
|
+
return "old_string not found in file (no similar block found)";
|
|
65
|
+
}
|
|
122
66
|
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
67
|
+
// Generate detailed report
|
|
68
|
+
const reportLines: string[] = [
|
|
69
|
+
`old_string not found in file. Best partial match found at line ${bestMatchIndex + 1}:`,
|
|
70
|
+
];
|
|
71
|
+
|
|
72
|
+
for (let j = 0; j < searchLines.length; j++) {
|
|
73
|
+
const lineNum = bestMatchIndex + j + 1;
|
|
74
|
+
const actualLine = contentLines[bestMatchIndex + j];
|
|
75
|
+
const expectedLine = searchLines[j];
|
|
76
|
+
|
|
77
|
+
if (actualLine === expectedLine) {
|
|
78
|
+
reportLines.push(`${lineNum.toString().padStart(4)} | ${actualLine}`);
|
|
79
|
+
} else {
|
|
80
|
+
reportLines.push(
|
|
81
|
+
`${lineNum.toString().padStart(4)} | - ${expectedLine} (expected)`,
|
|
82
|
+
);
|
|
83
|
+
reportLines.push(
|
|
84
|
+
`${lineNum.toString().padStart(4)} | + ${actualLine} (actual)`,
|
|
85
|
+
);
|
|
86
|
+
}
|
|
127
87
|
}
|
|
88
|
+
|
|
89
|
+
return reportLines.join("\n");
|
|
128
90
|
}
|
|
@@ -504,6 +504,7 @@ export interface AddSubagentBlockParams {
|
|
|
504
504
|
status: "active" | "completed" | "error" | "aborted";
|
|
505
505
|
sessionId: string;
|
|
506
506
|
configuration: SubagentConfiguration;
|
|
507
|
+
runInBackground?: boolean;
|
|
507
508
|
}
|
|
508
509
|
|
|
509
510
|
export interface UpdateSubagentBlockParams {
|
|
@@ -520,6 +521,7 @@ export const addSubagentBlockToMessage = ({
|
|
|
520
521
|
status,
|
|
521
522
|
sessionId,
|
|
522
523
|
configuration,
|
|
524
|
+
runInBackground,
|
|
523
525
|
}: AddSubagentBlockParams): Message[] => {
|
|
524
526
|
const newMessages = [...messages];
|
|
525
527
|
|
|
@@ -544,6 +546,7 @@ export const addSubagentBlockToMessage = ({
|
|
|
544
546
|
status,
|
|
545
547
|
sessionId,
|
|
546
548
|
configuration,
|
|
549
|
+
runInBackground,
|
|
547
550
|
});
|
|
548
551
|
|
|
549
552
|
return newMessages;
|
|
@@ -555,6 +558,7 @@ export const updateSubagentBlockInMessage = (
|
|
|
555
558
|
updates: Partial<{
|
|
556
559
|
status: "active" | "completed" | "error" | "aborted";
|
|
557
560
|
sessionId: string;
|
|
561
|
+
runInBackground: boolean;
|
|
558
562
|
}>,
|
|
559
563
|
): Message[] => {
|
|
560
564
|
const newMessages = [...messages];
|
|
@@ -571,6 +575,9 @@ export const updateSubagentBlockInMessage = (
|
|
|
571
575
|
if (updates.sessionId !== undefined) {
|
|
572
576
|
block.sessionId = updates.sessionId;
|
|
573
577
|
}
|
|
578
|
+
if (updates.runInBackground !== undefined) {
|
|
579
|
+
block.runInBackground = updates.runInBackground;
|
|
580
|
+
}
|
|
574
581
|
return newMessages;
|
|
575
582
|
}
|
|
576
583
|
}
|