zeitlich 0.2.7 → 0.2.9
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/index.cjs +93 -42
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +2 -2
- package/dist/index.d.ts +2 -2
- package/dist/index.js +92 -41
- package/dist/index.js.map +1 -1
- package/dist/{workflow-CyYHDbrr.d.cts → workflow-C2ShwjC7.d.cts} +50 -18
- package/dist/{workflow-CyYHDbrr.d.ts → workflow-C2ShwjC7.d.ts} +50 -18
- package/dist/workflow.cjs +88 -39
- package/dist/workflow.cjs.map +1 -1
- package/dist/workflow.d.cts +1 -1
- package/dist/workflow.d.ts +1 -1
- package/dist/workflow.js +87 -38
- package/dist/workflow.js.map +1 -1
- package/package.json +1 -1
- package/src/lib/model-invoker.ts +7 -3
- package/src/lib/session.ts +44 -10
- package/src/lib/state-manager.ts +56 -0
- package/src/lib/tool-router.ts +33 -21
- package/src/lib/types.ts +18 -8
- package/src/tools/ask-user-question/handler.ts +3 -3
- package/src/tools/read-file/tool.ts +2 -2
- package/src/tools/subagent/handler.ts +2 -1
- package/src/tools/subagent/tool.ts +4 -4
- package/src/tools/write-file/tool.ts +4 -5
- package/src/workflow.ts +2 -2
package/src/lib/session.ts
CHANGED
|
@@ -24,7 +24,11 @@ import type { MessageContent } from "@langchain/core/messages";
|
|
|
24
24
|
export interface ZeitlichSession<M = unknown> {
|
|
25
25
|
runSession<T extends JsonSerializable<T>>(args: {
|
|
26
26
|
stateManager: AgentStateManager<T>;
|
|
27
|
-
}): Promise<
|
|
27
|
+
}): Promise<{
|
|
28
|
+
finalMessage: M | null;
|
|
29
|
+
exitReason: SessionExitReason;
|
|
30
|
+
usage: ReturnType<AgentStateManager<T>["getTotalUsage"]>;
|
|
31
|
+
}>;
|
|
28
32
|
}
|
|
29
33
|
|
|
30
34
|
/**
|
|
@@ -40,6 +44,7 @@ export interface SessionLifecycleHooks {
|
|
|
40
44
|
export const createSession = async <T extends ToolMap, M = unknown>({
|
|
41
45
|
threadId,
|
|
42
46
|
agentName,
|
|
47
|
+
description,
|
|
43
48
|
maxTurns = 50,
|
|
44
49
|
metadata = {},
|
|
45
50
|
runAgent,
|
|
@@ -86,7 +91,13 @@ export const createSession = async <T extends ToolMap, M = unknown>({
|
|
|
86
91
|
};
|
|
87
92
|
|
|
88
93
|
return {
|
|
89
|
-
runSession: async ({
|
|
94
|
+
runSession: async ({
|
|
95
|
+
stateManager,
|
|
96
|
+
}): Promise<{
|
|
97
|
+
finalMessage: M | null;
|
|
98
|
+
exitReason: SessionExitReason;
|
|
99
|
+
usage: ReturnType<typeof stateManager.getTotalUsage>;
|
|
100
|
+
}> => {
|
|
90
101
|
setHandler(
|
|
91
102
|
defineUpdate<unknown, [MessageContent]>(`add${agentName}Message`),
|
|
92
103
|
async (message: MessageContent) => {
|
|
@@ -115,8 +126,6 @@ export const createSession = async <T extends ToolMap, M = unknown>({
|
|
|
115
126
|
});
|
|
116
127
|
}
|
|
117
128
|
|
|
118
|
-
stateManager.setTools(toolRouter.getToolDefinitions());
|
|
119
|
-
|
|
120
129
|
await initializeThread(threadId);
|
|
121
130
|
if (appendSystemPrompt && systemPrompt && systemPrompt.trim() !== "") {
|
|
122
131
|
await appendSystemMessage(threadId, systemPrompt);
|
|
@@ -134,17 +143,29 @@ export const createSession = async <T extends ToolMap, M = unknown>({
|
|
|
134
143
|
stateManager.incrementTurns();
|
|
135
144
|
const currentTurn = stateManager.getTurns();
|
|
136
145
|
|
|
137
|
-
|
|
146
|
+
stateManager.setTools(toolRouter.getToolDefinitions());
|
|
147
|
+
|
|
148
|
+
const { message, rawToolCalls, usage } = await runAgent({
|
|
138
149
|
threadId,
|
|
139
150
|
agentName,
|
|
140
151
|
metadata,
|
|
152
|
+
systemPrompt,
|
|
153
|
+
description,
|
|
141
154
|
});
|
|
142
155
|
|
|
156
|
+
if (usage) {
|
|
157
|
+
stateManager.updateUsage(usage);
|
|
158
|
+
}
|
|
159
|
+
|
|
143
160
|
// No tools configured - treat any non-end_turn as completed
|
|
144
161
|
if (!toolRouter.hasTools() || rawToolCalls.length === 0) {
|
|
145
162
|
stateManager.complete();
|
|
146
163
|
exitReason = "completed";
|
|
147
|
-
return
|
|
164
|
+
return {
|
|
165
|
+
finalMessage: message,
|
|
166
|
+
exitReason,
|
|
167
|
+
usage: stateManager.getTotalUsage(),
|
|
168
|
+
};
|
|
148
169
|
}
|
|
149
170
|
|
|
150
171
|
// Parse all tool calls uniformly through the router
|
|
@@ -165,9 +186,18 @@ export const createSession = async <T extends ToolMap, M = unknown>({
|
|
|
165
186
|
}
|
|
166
187
|
|
|
167
188
|
// Hooks can call stateManager.waitForInput() to pause the session
|
|
168
|
-
await toolRouter.processToolCalls(
|
|
169
|
-
|
|
170
|
-
|
|
189
|
+
const toolCallResults = await toolRouter.processToolCalls(
|
|
190
|
+
parsedToolCalls,
|
|
191
|
+
{
|
|
192
|
+
turn: currentTurn,
|
|
193
|
+
}
|
|
194
|
+
);
|
|
195
|
+
|
|
196
|
+
for (const result of toolCallResults) {
|
|
197
|
+
if (result.usage) {
|
|
198
|
+
stateManager.updateUsage(result.usage);
|
|
199
|
+
}
|
|
200
|
+
}
|
|
171
201
|
|
|
172
202
|
if (stateManager.getStatus() === "WAITING_FOR_INPUT") {
|
|
173
203
|
const conditionMet = await condition(
|
|
@@ -195,7 +225,11 @@ export const createSession = async <T extends ToolMap, M = unknown>({
|
|
|
195
225
|
await callSessionEnd(exitReason, stateManager.getTurns());
|
|
196
226
|
}
|
|
197
227
|
|
|
198
|
-
return
|
|
228
|
+
return {
|
|
229
|
+
finalMessage: null,
|
|
230
|
+
exitReason,
|
|
231
|
+
usage: stateManager.getTotalUsage(),
|
|
232
|
+
};
|
|
199
233
|
},
|
|
200
234
|
};
|
|
201
235
|
};
|
package/src/lib/state-manager.ts
CHANGED
|
@@ -114,6 +114,25 @@ export interface AgentStateManager<TCustom extends JsonSerializable<TCustom>> {
|
|
|
114
114
|
|
|
115
115
|
/** Set the tools (converts Zod schemas to JSON Schema for serialization) */
|
|
116
116
|
setTools(newTools: ToolDefinition[]): void;
|
|
117
|
+
|
|
118
|
+
/** Update the usage */
|
|
119
|
+
updateUsage(usage: {
|
|
120
|
+
inputTokens?: number;
|
|
121
|
+
outputTokens?: number;
|
|
122
|
+
cachedWriteTokens?: number;
|
|
123
|
+
cachedReadTokens?: number;
|
|
124
|
+
reasonTokens?: number;
|
|
125
|
+
}): void;
|
|
126
|
+
|
|
127
|
+
/** Get the total usage */
|
|
128
|
+
getTotalUsage(): {
|
|
129
|
+
totalInputTokens: number;
|
|
130
|
+
totalOutputTokens: number;
|
|
131
|
+
totalCachedWriteTokens: number;
|
|
132
|
+
totalCachedReadTokens: number;
|
|
133
|
+
totalReasonTokens: number;
|
|
134
|
+
turns: number;
|
|
135
|
+
};
|
|
117
136
|
}
|
|
118
137
|
|
|
119
138
|
/**
|
|
@@ -140,6 +159,11 @@ export function createAgentStateManager<
|
|
|
140
159
|
let version = initialState?.version ?? 0;
|
|
141
160
|
let turns = initialState?.turns ?? 0;
|
|
142
161
|
let tools = initialState?.tools ?? [];
|
|
162
|
+
let totalInputTokens = 0;
|
|
163
|
+
let totalOutputTokens = 0;
|
|
164
|
+
let totalCachedWriteTokens = 0;
|
|
165
|
+
let totalCachedReadTokens = 0;
|
|
166
|
+
let totalReasonTokens = 0;
|
|
143
167
|
|
|
144
168
|
// Tasks state
|
|
145
169
|
const tasks = new Map<string, WorkflowTask>(initialState?.tasks);
|
|
@@ -283,6 +307,38 @@ export function createAgentStateManager<
|
|
|
283
307
|
}
|
|
284
308
|
return deleted;
|
|
285
309
|
},
|
|
310
|
+
|
|
311
|
+
updateUsage(usage: {
|
|
312
|
+
inputTokens?: number;
|
|
313
|
+
outputTokens?: number;
|
|
314
|
+
cachedWriteTokens?: number;
|
|
315
|
+
cachedReadTokens?: number;
|
|
316
|
+
reasonTokens?: number;
|
|
317
|
+
}): void {
|
|
318
|
+
totalInputTokens += usage.inputTokens ?? 0;
|
|
319
|
+
totalOutputTokens += usage.outputTokens ?? 0;
|
|
320
|
+
totalCachedWriteTokens += usage.cachedWriteTokens ?? 0;
|
|
321
|
+
totalCachedReadTokens += usage.cachedReadTokens ?? 0;
|
|
322
|
+
totalReasonTokens += usage.reasonTokens ?? 0;
|
|
323
|
+
},
|
|
324
|
+
|
|
325
|
+
getTotalUsage(): {
|
|
326
|
+
totalInputTokens: number;
|
|
327
|
+
totalOutputTokens: number;
|
|
328
|
+
totalCachedWriteTokens: number;
|
|
329
|
+
totalCachedReadTokens: number;
|
|
330
|
+
totalReasonTokens: number;
|
|
331
|
+
turns: number;
|
|
332
|
+
} {
|
|
333
|
+
return {
|
|
334
|
+
totalInputTokens,
|
|
335
|
+
totalOutputTokens,
|
|
336
|
+
totalCachedWriteTokens,
|
|
337
|
+
totalCachedReadTokens,
|
|
338
|
+
totalReasonTokens,
|
|
339
|
+
turns,
|
|
340
|
+
};
|
|
341
|
+
},
|
|
286
342
|
};
|
|
287
343
|
}
|
|
288
344
|
|
package/src/lib/tool-router.ts
CHANGED
|
@@ -6,13 +6,14 @@ import type {
|
|
|
6
6
|
PreToolUseHookResult,
|
|
7
7
|
SubagentConfig,
|
|
8
8
|
SubagentHooks,
|
|
9
|
+
TokenUsage,
|
|
9
10
|
ToolHooks,
|
|
10
11
|
ToolResultConfig,
|
|
11
12
|
} from "./types";
|
|
12
13
|
import type { SubagentArgs } from "../tools/subagent/tool";
|
|
13
14
|
|
|
14
15
|
import type { z } from "zod";
|
|
15
|
-
import { createSubagentTool } from "../tools/subagent/tool";
|
|
16
|
+
import { createSubagentTool, SUBAGENT_TOOL_NAME } from "../tools/subagent/tool";
|
|
16
17
|
import { createSubagentHandler } from "../tools/subagent/handler";
|
|
17
18
|
|
|
18
19
|
export type { ToolMessageContent };
|
|
@@ -53,7 +54,7 @@ export interface ToolWithHandler<
|
|
|
53
54
|
strict?: boolean;
|
|
54
55
|
max_uses?: number;
|
|
55
56
|
/** Whether this tool is available to the agent (default: true). Disabled tools are excluded from definitions and rejected at parse time. */
|
|
56
|
-
enabled?: boolean;
|
|
57
|
+
enabled?: () => boolean;
|
|
57
58
|
/** Per-tool lifecycle hooks (run in addition to global hooks) */
|
|
58
59
|
hooks?: ToolHooks<z.infer<TSchema>, TResult>;
|
|
59
60
|
}
|
|
@@ -76,7 +77,7 @@ export type ToolMap = Record<
|
|
|
76
77
|
handler: ToolHandler<any, any, any>;
|
|
77
78
|
strict?: boolean;
|
|
78
79
|
max_uses?: number;
|
|
79
|
-
enabled?: boolean;
|
|
80
|
+
enabled?: () => boolean;
|
|
80
81
|
// eslint-disable-next-line @typescript-eslint/no-explicit-any
|
|
81
82
|
hooks?: ToolHooks<any, any>;
|
|
82
83
|
}
|
|
@@ -153,6 +154,8 @@ export interface ToolHandlerResponse<TResult = null> {
|
|
|
153
154
|
* payloads through Temporal's activity payload limit.
|
|
154
155
|
*/
|
|
155
156
|
resultAppended?: boolean;
|
|
157
|
+
/** Token usage from the tool execution (e.g. child agent invocations) */
|
|
158
|
+
usage?: TokenUsage;
|
|
156
159
|
}
|
|
157
160
|
|
|
158
161
|
/**
|
|
@@ -228,6 +231,7 @@ export interface ToolCallResult<
|
|
|
228
231
|
toolCallId: string;
|
|
229
232
|
name: TName;
|
|
230
233
|
data: TResult;
|
|
234
|
+
usage?: TokenUsage;
|
|
231
235
|
}
|
|
232
236
|
|
|
233
237
|
/**
|
|
@@ -412,25 +416,23 @@ export function createToolRouter<T extends ToolMap>(
|
|
|
412
416
|
}
|
|
413
417
|
|
|
414
418
|
/** Check if a tool is enabled (defaults to true when not specified) */
|
|
415
|
-
const isEnabled = (tool: ToolMap[string]): boolean =>
|
|
419
|
+
const isEnabled = (tool: ToolMap[string] | SubagentConfig): boolean =>
|
|
420
|
+
tool.enabled?.() ?? true;
|
|
416
421
|
|
|
417
422
|
if (options.subagents) {
|
|
418
|
-
|
|
419
|
-
(s) => s.enabled !== false
|
|
420
|
-
);
|
|
421
|
-
if (enabledSubagents.length > 0) {
|
|
423
|
+
if (options.subagents.length > 0) {
|
|
422
424
|
// Build per-subagent hook dispatcher keyed by subagent name
|
|
423
425
|
const subagentHooksMap = new Map<string, SubagentHooks>();
|
|
424
|
-
for (const s of
|
|
426
|
+
for (const s of options.subagents) {
|
|
425
427
|
if (s.hooks) subagentHooksMap.set(s.agentName, s.hooks);
|
|
426
428
|
}
|
|
427
429
|
|
|
428
430
|
const resolveSubagentName = (args: unknown): string =>
|
|
429
431
|
(args as SubagentArgs).subagent;
|
|
430
432
|
|
|
431
|
-
toolMap.set(
|
|
432
|
-
...createSubagentTool(
|
|
433
|
-
handler: createSubagentHandler(
|
|
433
|
+
toolMap.set(SUBAGENT_TOOL_NAME, {
|
|
434
|
+
...createSubagentTool(options.subagents),
|
|
435
|
+
handler: createSubagentHandler(options.subagents),
|
|
434
436
|
...(subagentHooksMap.size > 0 && {
|
|
435
437
|
hooks: {
|
|
436
438
|
onPreToolUse: async (ctx): Promise<PreToolUseHookResult> => {
|
|
@@ -655,15 +657,25 @@ export function createToolRouter<T extends ToolMap>(
|
|
|
655
657
|
},
|
|
656
658
|
|
|
657
659
|
getToolDefinitions(): ToolDefinition[] {
|
|
658
|
-
|
|
659
|
-
.filter((
|
|
660
|
-
|
|
661
|
-
|
|
662
|
-
|
|
663
|
-
|
|
664
|
-
|
|
665
|
-
|
|
666
|
-
|
|
660
|
+
const activeSubagents =
|
|
661
|
+
options.subagents?.filter((subagent) => isEnabled(subagent)) ?? [];
|
|
662
|
+
|
|
663
|
+
return [
|
|
664
|
+
...Array.from(toolMap)
|
|
665
|
+
.filter(
|
|
666
|
+
([, tool]) => isEnabled(tool) && tool.name !== SUBAGENT_TOOL_NAME
|
|
667
|
+
)
|
|
668
|
+
.map(([name, tool]) => ({
|
|
669
|
+
name,
|
|
670
|
+
description: tool.description,
|
|
671
|
+
schema: tool.schema,
|
|
672
|
+
strict: tool.strict,
|
|
673
|
+
max_uses: tool.max_uses,
|
|
674
|
+
})),
|
|
675
|
+
...(activeSubagents.length > 0
|
|
676
|
+
? [createSubagentTool(activeSubagents)]
|
|
677
|
+
: []),
|
|
678
|
+
];
|
|
667
679
|
},
|
|
668
680
|
|
|
669
681
|
// --- Methods for processing tool calls ---
|
package/src/lib/types.ts
CHANGED
|
@@ -32,6 +32,10 @@ export interface BaseAgentState {
|
|
|
32
32
|
turns: number;
|
|
33
33
|
tasks: Map<string, WorkflowTask>;
|
|
34
34
|
systemPrompt: string;
|
|
35
|
+
totalInputTokens: number;
|
|
36
|
+
totalOutputTokens: number;
|
|
37
|
+
cachedWriteTokens: number;
|
|
38
|
+
cachedReadtTokens: number;
|
|
35
39
|
}
|
|
36
40
|
|
|
37
41
|
/**
|
|
@@ -50,17 +54,21 @@ export interface AgentFile {
|
|
|
50
54
|
mimeType?: string;
|
|
51
55
|
}
|
|
52
56
|
|
|
57
|
+
export interface TokenUsage {
|
|
58
|
+
inputTokens?: number;
|
|
59
|
+
outputTokens?: number;
|
|
60
|
+
cachedWriteTokens?: number;
|
|
61
|
+
cachedReadTokens?: number;
|
|
62
|
+
reasonTokens?: number;
|
|
63
|
+
}
|
|
64
|
+
|
|
53
65
|
/**
|
|
54
66
|
* Agent response from LLM invocation
|
|
55
67
|
*/
|
|
56
68
|
export interface AgentResponse<M = StoredMessage> {
|
|
57
69
|
message: M;
|
|
58
70
|
rawToolCalls: RawToolCall[];
|
|
59
|
-
usage?:
|
|
60
|
-
input_tokens?: number;
|
|
61
|
-
output_tokens?: number;
|
|
62
|
-
total_tokens?: number;
|
|
63
|
-
};
|
|
71
|
+
usage?: TokenUsage;
|
|
64
72
|
}
|
|
65
73
|
|
|
66
74
|
/**
|
|
@@ -143,9 +151,10 @@ export interface SerializableToolDefinition {
|
|
|
143
151
|
/**
|
|
144
152
|
* Configuration passed to runAgent activity
|
|
145
153
|
*/
|
|
146
|
-
export interface RunAgentConfig {
|
|
154
|
+
export interface RunAgentConfig extends AgentConfig {
|
|
155
|
+
/** The thread ID to use for the session */
|
|
147
156
|
threadId: string;
|
|
148
|
-
|
|
157
|
+
/** Metadata for the session */
|
|
149
158
|
metadata?: Record<string, unknown>;
|
|
150
159
|
}
|
|
151
160
|
|
|
@@ -155,6 +164,7 @@ export interface RunAgentConfig {
|
|
|
155
164
|
export type RunAgentActivity<M = StoredMessage> = (
|
|
156
165
|
config: RunAgentConfig
|
|
157
166
|
) => Promise<AgentResponse<M>>;
|
|
167
|
+
|
|
158
168
|
/**
|
|
159
169
|
* Configuration for appending a tool result
|
|
160
170
|
*/
|
|
@@ -186,7 +196,7 @@ export interface SubagentConfig<TResult extends z.ZodType = z.ZodType> {
|
|
|
186
196
|
/** Description shown to the parent agent explaining what this subagent does */
|
|
187
197
|
description: string;
|
|
188
198
|
/** Whether this subagent is available (default: true). Disabled subagents are excluded from the Subagent tool. */
|
|
189
|
-
enabled?: boolean;
|
|
199
|
+
enabled?: () => boolean;
|
|
190
200
|
/** Temporal workflow function or type name (used with executeChild) */
|
|
191
201
|
workflow: string | Workflow;
|
|
192
202
|
/** Optional task queue - defaults to parent's queue if not specified */
|
|
@@ -1,11 +1,11 @@
|
|
|
1
|
-
import type {
|
|
1
|
+
import type { ActivityToolHandler } from "../../lib/tool-router";
|
|
2
2
|
import type { AskUserQuestionArgs } from "./tool";
|
|
3
3
|
|
|
4
4
|
/**
|
|
5
5
|
* Creates handler for user interaction tool - creates AI messages for display.
|
|
6
6
|
*/
|
|
7
7
|
export const createAskUserQuestionHandler =
|
|
8
|
-
():
|
|
8
|
+
(): ActivityToolHandler<
|
|
9
9
|
AskUserQuestionArgs,
|
|
10
10
|
{
|
|
11
11
|
questions: {
|
|
@@ -16,7 +16,7 @@ export const createAskUserQuestionHandler =
|
|
|
16
16
|
}[];
|
|
17
17
|
}
|
|
18
18
|
> =>
|
|
19
|
-
(args) => {
|
|
19
|
+
async (args) => {
|
|
20
20
|
return {
|
|
21
21
|
toolResponse: "Question submitted",
|
|
22
22
|
data: { questions: args.questions },
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import { z } from "zod";
|
|
2
2
|
import type { ToolDefinition } from "../../lib/tool-router";
|
|
3
3
|
|
|
4
|
-
export const
|
|
4
|
+
export const readFileTool = {
|
|
5
5
|
name: "FileRead" as const,
|
|
6
6
|
description: `Read file contents with optional pagination.
|
|
7
7
|
|
|
@@ -31,4 +31,4 @@ The tool returns the file content in an appropriate format:
|
|
|
31
31
|
strict: true,
|
|
32
32
|
} satisfies ToolDefinition;
|
|
33
33
|
|
|
34
|
-
export type FileReadArgs = z.infer<typeof
|
|
34
|
+
export type FileReadArgs = z.infer<typeof readFileTool.schema>;
|
|
@@ -53,7 +53,7 @@ export function createSubagentHandler<
|
|
|
53
53
|
taskQueue: config.taskQueue ?? parentTaskQueue,
|
|
54
54
|
};
|
|
55
55
|
|
|
56
|
-
const { toolResponse, data } =
|
|
56
|
+
const { toolResponse, data, usage } =
|
|
57
57
|
typeof config.workflow === "string"
|
|
58
58
|
? await executeChild(config.workflow, childOpts)
|
|
59
59
|
: await executeChild(config.workflow, childOpts);
|
|
@@ -66,6 +66,7 @@ export function createSubagentHandler<
|
|
|
66
66
|
return {
|
|
67
67
|
toolResponse,
|
|
68
68
|
data: validated,
|
|
69
|
+
...(usage && { usage }),
|
|
69
70
|
};
|
|
70
71
|
};
|
|
71
72
|
}
|
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
import z from "zod";
|
|
2
2
|
import type { SubagentConfig } from "../../lib/types";
|
|
3
3
|
|
|
4
|
-
const
|
|
4
|
+
export const SUBAGENT_TOOL_NAME = "Subagent" as const;
|
|
5
5
|
|
|
6
6
|
/**
|
|
7
7
|
* Builds the tool description with available subagent information
|
|
@@ -13,13 +13,13 @@ function buildSubagentDescription(subagents: SubagentConfig[]): string {
|
|
|
13
13
|
|
|
14
14
|
return `Launch a new agent to handle complex tasks autonomously.
|
|
15
15
|
|
|
16
|
-
The ${
|
|
16
|
+
The ${SUBAGENT_TOOL_NAME} tool launches specialized agents (subprocesses) that autonomously handle complex tasks. Each agent type has specific capabilities and tools available to it.
|
|
17
17
|
|
|
18
18
|
Available agent types:
|
|
19
19
|
|
|
20
20
|
${subagentList}
|
|
21
21
|
|
|
22
|
-
When using the ${
|
|
22
|
+
When using the ${SUBAGENT_TOOL_NAME} tool, you must specify a subagent parameter to select which agent type to use.
|
|
23
23
|
|
|
24
24
|
Usage notes:
|
|
25
25
|
|
|
@@ -67,7 +67,7 @@ export function createSubagentTool<T extends SubagentConfig[]>(
|
|
|
67
67
|
const names = subagents.map((s) => s.agentName);
|
|
68
68
|
|
|
69
69
|
return {
|
|
70
|
-
name:
|
|
70
|
+
name: SUBAGENT_TOOL_NAME,
|
|
71
71
|
description: buildSubagentDescription(subagents),
|
|
72
72
|
schema: z.object({
|
|
73
73
|
subagent: z.enum(names).describe("The type of subagent to launch"),
|
|
@@ -1,25 +1,24 @@
|
|
|
1
1
|
import { z } from "zod";
|
|
2
2
|
import type { ToolDefinition } from "../../lib/tool-router";
|
|
3
3
|
|
|
4
|
-
export const
|
|
4
|
+
export const writeFileTool = {
|
|
5
5
|
name: "FileWrite" as const,
|
|
6
6
|
description: `Create or overwrite a file with new content.
|
|
7
7
|
|
|
8
8
|
Usage:
|
|
9
|
-
- Provide the absolute path to the file
|
|
10
9
|
- The file will be created if it doesn't exist
|
|
11
10
|
- If the file exists, it will be completely overwritten
|
|
12
11
|
|
|
13
12
|
IMPORTANT:
|
|
14
13
|
- You must read the file first (in this session) before writing to it
|
|
15
14
|
- This is an atomic write operation - the entire file is replaced
|
|
16
|
-
- Path must be
|
|
15
|
+
- Path must be relative to the root of the file system (e.g., "docs/readme.md", not "/docs/readme.md")
|
|
17
16
|
`,
|
|
18
17
|
schema: z.object({
|
|
19
|
-
file_path: z.string().describe("The
|
|
18
|
+
file_path: z.string().describe("The path to the file to write"),
|
|
20
19
|
content: z.string().describe("The content to write to the file"),
|
|
21
20
|
}),
|
|
22
21
|
strict: true,
|
|
23
22
|
} satisfies ToolDefinition;
|
|
24
23
|
|
|
25
|
-
export type FileWriteArgs = z.infer<typeof
|
|
24
|
+
export type FileWriteArgs = z.infer<typeof writeFileTool.schema>;
|
package/src/workflow.ts
CHANGED
|
@@ -113,9 +113,9 @@ export { globTool } from "./tools/glob/tool";
|
|
|
113
113
|
export type { GlobArgs } from "./tools/glob/tool";
|
|
114
114
|
export { grepTool } from "./tools/grep/tool";
|
|
115
115
|
export type { GrepArgs } from "./tools/grep/tool";
|
|
116
|
-
export {
|
|
116
|
+
export { readFileTool } from "./tools/read-file/tool";
|
|
117
117
|
export type { FileReadArgs } from "./tools/read-file/tool";
|
|
118
|
-
export {
|
|
118
|
+
export { writeFileTool } from "./tools/write-file/tool";
|
|
119
119
|
export type { FileWriteArgs } from "./tools/write-file/tool";
|
|
120
120
|
export { editTool } from "./tools/edit/tool";
|
|
121
121
|
export type { FileEditArgs } from "./tools/edit/tool";
|