@ai-setting/roy-agent-core 1.6.10 → 1.6.12
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/env/agent/index.js +2 -2
- package/dist/env/event-source/index.js +3 -3
- package/dist/env/index.js +12 -12
- package/dist/env/prompt/index.js +2 -2
- package/dist/env/task/delegate/index.js +3 -3
- package/dist/env/task/index.js +6 -6
- package/dist/env/task/plugins/index.js +2 -2
- package/dist/env/task/storage/index.js +2 -1
- package/dist/env/task/tools/operation/index.js +1 -1
- package/dist/env/workflow/index.js +2 -2
- package/dist/env/workflow/tools/index.js +1 -1
- package/dist/index.js +13 -13
- package/dist/shared/@ai-setting/{roy-agent-core-4mhrz08q.js → roy-agent-core-06574wqa.js} +3 -2
- package/dist/shared/@ai-setting/{roy-agent-core-m38q2azm.js → roy-agent-core-1bvv6s75.js} +3 -1
- package/dist/shared/@ai-setting/{roy-agent-core-wqe84f84.js → roy-agent-core-3bdpnmtg.js} +29 -0
- package/dist/shared/@ai-setting/{roy-agent-core-8bhncxep.js → roy-agent-core-7a3gf3tw.js} +45 -8
- package/dist/shared/@ai-setting/roy-agent-core-9abv4ewh.js +1122 -0
- package/dist/shared/@ai-setting/{roy-agent-core-0cftbg62.js → roy-agent-core-asp5p3zx.js} +1 -1
- package/dist/shared/@ai-setting/{roy-agent-core-38kbfarg.js → roy-agent-core-cxdnzn17.js} +1 -1
- package/dist/shared/@ai-setting/{roy-agent-core-nzpw62d3.js → roy-agent-core-dntkpwqq.js} +8 -8
- package/dist/shared/@ai-setting/{roy-agent-core-g9p7e2ys.js → roy-agent-core-mb7b62sm.js} +51 -13
- package/dist/shared/@ai-setting/{roy-agent-core-trdpar9f.js → roy-agent-core-ms5dp89r.js} +338 -20
- package/dist/shared/@ai-setting/{roy-agent-core-2ek596yd.js → roy-agent-core-q2bw3cwd.js} +1 -1
- package/dist/shared/@ai-setting/{roy-agent-core-y5ymc4f8.js → roy-agent-core-q7rt3x8d.js} +45 -13
- package/dist/shared/@ai-setting/roy-agent-core-rn57psp0.js +396 -0
- package/package.json +1 -1
- package/dist/shared/@ai-setting/roy-agent-core-9xby523m.js +0 -961
- package/dist/shared/@ai-setting/roy-agent-core-t94ktchq.js +0 -213
|
@@ -6,7 +6,7 @@ import {
|
|
|
6
6
|
} from "./roy-agent-core-8wd3qwx5.js";
|
|
7
7
|
import {
|
|
8
8
|
WORKFLOW_EXTRACT_PROMPT
|
|
9
|
-
} from "./roy-agent-core-
|
|
9
|
+
} from "./roy-agent-core-ms5dp89r.js";
|
|
10
10
|
import {
|
|
11
11
|
TaskHookPoints
|
|
12
12
|
} from "./roy-agent-core-1pg0fepg.js";
|
|
@@ -495,7 +495,7 @@ class LarkCliTaskNotifyHook {
|
|
|
495
495
|
await this.sendNotify({
|
|
496
496
|
type: "operation_created" /* OPERATION_CREATED */,
|
|
497
497
|
title: this.getNotifyTitle("operation_created" /* OPERATION_CREATED */),
|
|
498
|
-
content: this.formatOperationCreated(operation),
|
|
498
|
+
content: await this.formatOperationCreated(operation),
|
|
499
499
|
_hookContext: ctx
|
|
500
500
|
});
|
|
501
501
|
}
|
|
@@ -588,6 +588,16 @@ ${content}`;
|
|
|
588
588
|
});
|
|
589
589
|
});
|
|
590
590
|
}
|
|
591
|
+
truncate(text, maxLen) {
|
|
592
|
+
if (text.length <= maxLen)
|
|
593
|
+
return text;
|
|
594
|
+
return text.substring(0, maxLen) + "...";
|
|
595
|
+
}
|
|
596
|
+
appendProjectPathLine(lines, task) {
|
|
597
|
+
if (task?.project_path) {
|
|
598
|
+
lines.push(`- **项目路径**: \`${task.project_path}\``);
|
|
599
|
+
}
|
|
600
|
+
}
|
|
591
601
|
shouldNotify(type) {
|
|
592
602
|
const { notifyTypes } = this.config;
|
|
593
603
|
if (notifyTypes && notifyTypes.length === 0)
|
|
@@ -621,12 +631,12 @@ ${content}`;
|
|
|
621
631
|
lines.push(`- **标题**: ${task.title}`);
|
|
622
632
|
}
|
|
623
633
|
if (task.description) {
|
|
624
|
-
|
|
625
|
-
lines.push(`- **描述**: ${desc}`);
|
|
634
|
+
lines.push(`- **描述**: ${this.truncate(task.description, 100)}`);
|
|
626
635
|
}
|
|
627
636
|
if (task.priority) {
|
|
628
637
|
lines.push(`- **优先级**: ${task.priority}`);
|
|
629
638
|
}
|
|
639
|
+
this.appendProjectPathLine(lines, task);
|
|
630
640
|
return lines.join(`
|
|
631
641
|
`);
|
|
632
642
|
}
|
|
@@ -645,6 +655,7 @@ ${content}`;
|
|
|
645
655
|
if (changes?.current_status) {
|
|
646
656
|
lines.push(`- **当前状态**: ${changes.current_status}`);
|
|
647
657
|
}
|
|
658
|
+
this.appendProjectPathLine(lines, task);
|
|
648
659
|
const changeKeys = Object.keys(changes || {}).filter((k) => !["status", "progress", "current_status"].includes(k));
|
|
649
660
|
if (changeKeys.length > 0) {
|
|
650
661
|
lines.push(`- **变更**: ${changeKeys.join(", ")}`);
|
|
@@ -667,28 +678,49 @@ ${content}`;
|
|
|
667
678
|
this.lastNotifyTimestamps.set(key, now);
|
|
668
679
|
return false;
|
|
669
680
|
}
|
|
670
|
-
formatOperationCreated(operation) {
|
|
681
|
+
async formatOperationCreated(operation, task) {
|
|
682
|
+
const resolvedTask = task ?? await this.resolveTaskForOperation(operation);
|
|
671
683
|
const lines = [];
|
|
684
|
+
if (resolvedTask?.title) {
|
|
685
|
+
lines.push(`- **任务**: ${resolvedTask.title}`);
|
|
686
|
+
}
|
|
672
687
|
if (operation.taskId !== undefined && operation.taskId !== null) {
|
|
673
688
|
lines.push(`- **任务 ID**: #${operation.taskId}`);
|
|
674
689
|
}
|
|
675
|
-
if (operation.
|
|
676
|
-
lines.push(`-
|
|
690
|
+
if (operation.milestoneType) {
|
|
691
|
+
lines.push(`- **里程碑类型**: ${operation.milestoneType}`);
|
|
677
692
|
}
|
|
678
|
-
if (operation.
|
|
679
|
-
lines.push(`- **标题**: ${operation.
|
|
693
|
+
if (operation.milestoneTitle) {
|
|
694
|
+
lines.push(`- **标题**: ${operation.milestoneTitle}`);
|
|
680
695
|
}
|
|
681
|
-
if (operation.
|
|
682
|
-
|
|
683
|
-
const truncated = desc.substring(0, 200) + (desc.length > 200 ? "..." : "");
|
|
684
|
-
lines.push(`- **描述**: ${truncated}`);
|
|
696
|
+
if (operation.milestoneDescription) {
|
|
697
|
+
lines.push(`- **里程碑描述**: ${this.truncate(String(operation.milestoneDescription), 200)}`);
|
|
685
698
|
}
|
|
699
|
+
if (operation.processDescription) {
|
|
700
|
+
lines.push(`- **过程概要**: ${this.truncate(String(operation.processDescription), 200)}`);
|
|
701
|
+
}
|
|
702
|
+
this.appendProjectPathLine(lines, resolvedTask);
|
|
686
703
|
if (operation.sessionId) {
|
|
687
704
|
lines.push(`- **Session**: \`${operation.sessionId}\``);
|
|
688
705
|
}
|
|
689
706
|
return lines.join(`
|
|
690
707
|
`);
|
|
691
708
|
}
|
|
709
|
+
async resolveTaskForOperation(operation) {
|
|
710
|
+
if (operation.taskId === undefined || operation.taskId === null) {
|
|
711
|
+
return;
|
|
712
|
+
}
|
|
713
|
+
const fetch = this.config.fetchTaskById;
|
|
714
|
+
if (!fetch) {
|
|
715
|
+
return;
|
|
716
|
+
}
|
|
717
|
+
try {
|
|
718
|
+
return await fetch(operation.taskId);
|
|
719
|
+
} catch (error) {
|
|
720
|
+
logger3.warn(`fetchTaskById failed for task #${operation.taskId}: ${error}`);
|
|
721
|
+
return;
|
|
722
|
+
}
|
|
723
|
+
}
|
|
692
724
|
}
|
|
693
725
|
__legacyDecorateClassTS([
|
|
694
726
|
TracedAs("lark-cli-task-notify.execute")
|
|
@@ -0,0 +1,396 @@
|
|
|
1
|
+
// src/env/task/tools/operation/create-tool.ts
|
|
2
|
+
import { ZodError } from "zod";
|
|
3
|
+
|
|
4
|
+
// src/env/task/tools/operation/operation-types.ts
|
|
5
|
+
import { z } from "zod";
|
|
6
|
+
var ActionTypeEnum = z.enum([
|
|
7
|
+
"create",
|
|
8
|
+
"progress",
|
|
9
|
+
"milestone",
|
|
10
|
+
"problem",
|
|
11
|
+
"solution",
|
|
12
|
+
"decision",
|
|
13
|
+
"review",
|
|
14
|
+
"completed",
|
|
15
|
+
"workflow_extracted"
|
|
16
|
+
]);
|
|
17
|
+
var PROCESS_DESCRIPTION_MIN_LENGTH = 100;
|
|
18
|
+
var PROCESS_DESCRIPTION_MAX_LENGTH = 150;
|
|
19
|
+
var MILESTONE_DESCRIPTION_MAX_LENGTH = 5000;
|
|
20
|
+
var MILESTONE_TITLE_MIN_LENGTH = 1;
|
|
21
|
+
var MILESTONE_TITLE_MAX_LENGTH = 200;
|
|
22
|
+
var ProcessDescriptionSchema = z.string().min(PROCESS_DESCRIPTION_MIN_LENGTH, {
|
|
23
|
+
message: `process_description 太短(少于 ${PROCESS_DESCRIPTION_MIN_LENGTH} 字符),无法表达过程概要;如无过程信息请省略该字段,细节请回查 sessionId。`
|
|
24
|
+
}).max(PROCESS_DESCRIPTION_MAX_LENGTH, {
|
|
25
|
+
message: `process_description 太长(超过 ${PROCESS_DESCRIPTION_MAX_LENGTH} 字符),会退化为日志细节;操作记录只承担 milestone 概要,完整细节请通过 sessionId 回查 session。`
|
|
26
|
+
}).describe("过程概要(process_description):采取的策略 + 工具步骤概要;" + `严格控制 ${PROCESS_DESCRIPTION_MIN_LENGTH}-${PROCESS_DESCRIPTION_MAX_LENGTH} 字符。` + "操作记录是节点阶段 milestone 摘要,完整过程通过 sessionId 回查 session;" + "milestone_description 才是达成的状态/结果描述。");
|
|
27
|
+
var MilestoneTitleSchema = z.string().min(MILESTONE_TITLE_MIN_LENGTH, { message: "milestone_title 不能为空" }).max(MILESTONE_TITLE_MAX_LENGTH, {
|
|
28
|
+
message: `milestone_title 超过 ${MILESTONE_TITLE_MAX_LENGTH} 字符,建议精简(一行标题即可)。`
|
|
29
|
+
}).describe("里程碑标题(milestone_title):达成的里程碑/状态的一句话标题;" + "必填,1-200 字符。");
|
|
30
|
+
var MilestoneDescriptionSchema = z.string().max(MILESTONE_DESCRIPTION_MAX_LENGTH, {
|
|
31
|
+
message: `milestone_description 超过 ${MILESTONE_DESCRIPTION_MAX_LENGTH} 字符;如需更详细的过程,请改用 process_description。`
|
|
32
|
+
}).optional().describe("状态/结果描述(milestone_description):达成的状态或结果描述;" + "可长可短;过程概要应放在 process_description,不要与本字段重复。");
|
|
33
|
+
var CreateOperationInputSchema = z.object({
|
|
34
|
+
task_id: z.number().describe("Task ID"),
|
|
35
|
+
milestone_type: ActionTypeEnum.optional(),
|
|
36
|
+
milestone_title: MilestoneTitleSchema.optional(),
|
|
37
|
+
milestone_description: MilestoneDescriptionSchema,
|
|
38
|
+
process_description: ProcessDescriptionSchema.optional(),
|
|
39
|
+
action_type: ActionTypeEnum.optional(),
|
|
40
|
+
action_title: z.string().min(1).max(MILESTONE_TITLE_MAX_LENGTH).optional(),
|
|
41
|
+
action_description: z.string().max(MILESTONE_DESCRIPTION_MAX_LENGTH).optional(),
|
|
42
|
+
md_path: z.string().optional().describe("Path to detailed markdown documentation")
|
|
43
|
+
});
|
|
44
|
+
var CreateOperationToolSchema = CreateOperationInputSchema.transform((input) => {
|
|
45
|
+
const deprecatedFields = [];
|
|
46
|
+
let milestoneType = input.milestone_type;
|
|
47
|
+
let milestoneTitle = input.milestone_title;
|
|
48
|
+
let milestoneDescription = input.milestone_description;
|
|
49
|
+
if (!milestoneType && input.action_type) {
|
|
50
|
+
milestoneType = input.action_type;
|
|
51
|
+
deprecatedFields.push("action_type");
|
|
52
|
+
}
|
|
53
|
+
if (!milestoneTitle && input.action_title) {
|
|
54
|
+
milestoneTitle = input.action_title;
|
|
55
|
+
deprecatedFields.push("action_title");
|
|
56
|
+
}
|
|
57
|
+
if (milestoneDescription === undefined && input.action_description !== undefined) {
|
|
58
|
+
milestoneDescription = input.action_description;
|
|
59
|
+
deprecatedFields.push("action_description");
|
|
60
|
+
}
|
|
61
|
+
return {
|
|
62
|
+
task_id: input.task_id,
|
|
63
|
+
milestone_type: milestoneType,
|
|
64
|
+
milestone_title: milestoneTitle,
|
|
65
|
+
milestone_description: milestoneDescription,
|
|
66
|
+
process_description: input.process_description,
|
|
67
|
+
md_path: input.md_path,
|
|
68
|
+
_deprecated_fields_used: deprecatedFields
|
|
69
|
+
};
|
|
70
|
+
});
|
|
71
|
+
var GetOperationToolSchema = z.object({
|
|
72
|
+
operation_id: z.number().describe("Operation ID")
|
|
73
|
+
});
|
|
74
|
+
var ListOperationsToolSchema = z.object({
|
|
75
|
+
task_id: z.number().describe("Task ID"),
|
|
76
|
+
milestone_type: ActionTypeEnum.optional(),
|
|
77
|
+
action_type: ActionTypeEnum.optional(),
|
|
78
|
+
limit: z.number().optional().default(20),
|
|
79
|
+
offset: z.number().optional().default(0)
|
|
80
|
+
}).transform((input) => {
|
|
81
|
+
const deprecatedFields = [];
|
|
82
|
+
let milestoneType = input.milestone_type;
|
|
83
|
+
if (!milestoneType && input.action_type) {
|
|
84
|
+
milestoneType = input.action_type;
|
|
85
|
+
deprecatedFields.push("action_type");
|
|
86
|
+
}
|
|
87
|
+
return {
|
|
88
|
+
task_id: input.task_id,
|
|
89
|
+
milestone_type: milestoneType,
|
|
90
|
+
limit: input.limit,
|
|
91
|
+
offset: input.offset,
|
|
92
|
+
_deprecated_fields_used: deprecatedFields
|
|
93
|
+
};
|
|
94
|
+
});
|
|
95
|
+
var UpdateOperationInputSchema = z.object({
|
|
96
|
+
operation_id: z.number().describe("Operation ID"),
|
|
97
|
+
milestone_title: MilestoneTitleSchema.optional(),
|
|
98
|
+
milestone_description: MilestoneDescriptionSchema,
|
|
99
|
+
process_description: ProcessDescriptionSchema.optional(),
|
|
100
|
+
action_title: z.string().min(1).max(MILESTONE_TITLE_MAX_LENGTH).optional(),
|
|
101
|
+
action_description: z.string().max(MILESTONE_DESCRIPTION_MAX_LENGTH).optional()
|
|
102
|
+
});
|
|
103
|
+
var UpdateOperationToolSchema = UpdateOperationInputSchema.transform((input) => {
|
|
104
|
+
const deprecatedFields = [];
|
|
105
|
+
let milestoneTitle = input.milestone_title;
|
|
106
|
+
let milestoneDescription = input.milestone_description;
|
|
107
|
+
if (!milestoneTitle && input.action_title) {
|
|
108
|
+
milestoneTitle = input.action_title;
|
|
109
|
+
deprecatedFields.push("action_title");
|
|
110
|
+
}
|
|
111
|
+
if (milestoneDescription === undefined && input.action_description !== undefined) {
|
|
112
|
+
milestoneDescription = input.action_description;
|
|
113
|
+
deprecatedFields.push("action_description");
|
|
114
|
+
}
|
|
115
|
+
return {
|
|
116
|
+
operation_id: input.operation_id,
|
|
117
|
+
milestone_title: milestoneTitle,
|
|
118
|
+
milestone_description: milestoneDescription,
|
|
119
|
+
process_description: input.process_description,
|
|
120
|
+
_deprecated_fields_used: deprecatedFields
|
|
121
|
+
};
|
|
122
|
+
});
|
|
123
|
+
var DeleteOperationToolSchema = z.object({
|
|
124
|
+
operation_id: z.number().describe("Operation ID")
|
|
125
|
+
});
|
|
126
|
+
|
|
127
|
+
// src/env/task/tools/operation/create-tool.ts
|
|
128
|
+
function formatZodError(err) {
|
|
129
|
+
const parts = err.issues.map((i) => `${i.path.join(".") || "<root>"}: ${i.message}`);
|
|
130
|
+
return `Invalid parameters: ${parts.join("; ")}`;
|
|
131
|
+
}
|
|
132
|
+
function ensureRequiredMilestoneFields(params) {
|
|
133
|
+
if (!params.milestone_type) {
|
|
134
|
+
return {
|
|
135
|
+
ok: false,
|
|
136
|
+
error: "milestone_type is required (or action_type for backward compatibility). " + "Use one of: create, progress, milestone, problem, solution, decision, review, completed, workflow_extracted."
|
|
137
|
+
};
|
|
138
|
+
}
|
|
139
|
+
if (!params.milestone_title) {
|
|
140
|
+
return {
|
|
141
|
+
ok: false,
|
|
142
|
+
error: "milestone_title is required (or action_title for backward compatibility)."
|
|
143
|
+
};
|
|
144
|
+
}
|
|
145
|
+
return { ok: true, milestoneType: params.milestone_type, milestoneTitle: params.milestone_title };
|
|
146
|
+
}
|
|
147
|
+
function createOperationTool(taskComponent) {
|
|
148
|
+
return {
|
|
149
|
+
name: "task_operation_create",
|
|
150
|
+
description: "Create an operation record for a task. Tracks milestones (state/result) and process (strategy + tool steps). " + "Dual-dimension schema: milestone_type/title/description captures WHAT milestone was reached; " + "process_description (100-150 chars) captures HOW. " + "Legacy action_* fields are accepted as deprecated aliases.",
|
|
151
|
+
parameters: CreateOperationToolSchema,
|
|
152
|
+
execute: async (args, ctx) => {
|
|
153
|
+
let params;
|
|
154
|
+
try {
|
|
155
|
+
const parsed = CreateOperationToolSchema.parse(args);
|
|
156
|
+
params = parsed;
|
|
157
|
+
} catch (e) {
|
|
158
|
+
if (e instanceof ZodError) {
|
|
159
|
+
return {
|
|
160
|
+
success: false,
|
|
161
|
+
output: "",
|
|
162
|
+
error: formatZodError(e),
|
|
163
|
+
metadata: { execution_time_ms: 0 }
|
|
164
|
+
};
|
|
165
|
+
}
|
|
166
|
+
throw e;
|
|
167
|
+
}
|
|
168
|
+
const check = ensureRequiredMilestoneFields(params);
|
|
169
|
+
if (!check.ok) {
|
|
170
|
+
return {
|
|
171
|
+
success: false,
|
|
172
|
+
output: "",
|
|
173
|
+
error: check.error,
|
|
174
|
+
metadata: { execution_time_ms: 0 }
|
|
175
|
+
};
|
|
176
|
+
}
|
|
177
|
+
const sessionId = ctx.session_id || "unknown";
|
|
178
|
+
try {
|
|
179
|
+
const operation = await taskComponent.createOperation({
|
|
180
|
+
taskId: params.task_id,
|
|
181
|
+
sessionId,
|
|
182
|
+
milestoneType: check.milestoneType,
|
|
183
|
+
milestoneTitle: check.milestoneTitle,
|
|
184
|
+
milestoneDescription: params.milestone_description,
|
|
185
|
+
processDescription: params.process_description,
|
|
186
|
+
mdPath: params.md_path
|
|
187
|
+
});
|
|
188
|
+
let output = `Operation created: #${operation.id} for task #${operation.taskId} ` + `[milestone=${operation.milestoneType}] ${operation.milestoneTitle}`;
|
|
189
|
+
const deprecationWarnings = [];
|
|
190
|
+
if (params._deprecated_fields_used.length > 0) {
|
|
191
|
+
deprecationWarnings.push(`⚠️ DEPRECATION NOTICE: 你使用了旧的 action_* 字段 (${params._deprecated_fields_used.join(", ")}),已自动映射到 milestone_* 字段。` + "请尽快迁移到 milestone_type / milestone_title / milestone_description 主字段。");
|
|
192
|
+
}
|
|
193
|
+
if (deprecationWarnings.length > 0) {
|
|
194
|
+
output += `
|
|
195
|
+
|
|
196
|
+
` + deprecationWarnings.join(`
|
|
197
|
+
`);
|
|
198
|
+
}
|
|
199
|
+
return {
|
|
200
|
+
success: true,
|
|
201
|
+
output,
|
|
202
|
+
metadata: {
|
|
203
|
+
execution_time_ms: 0,
|
|
204
|
+
operation_id: operation.id,
|
|
205
|
+
task_id: operation.taskId,
|
|
206
|
+
session_id: operation.sessionId,
|
|
207
|
+
deprecated_fields_used: params._deprecated_fields_used
|
|
208
|
+
}
|
|
209
|
+
};
|
|
210
|
+
} catch (error) {
|
|
211
|
+
return {
|
|
212
|
+
success: false,
|
|
213
|
+
output: "",
|
|
214
|
+
error: error instanceof Error ? error.message : String(error),
|
|
215
|
+
metadata: { execution_time_ms: 0 }
|
|
216
|
+
};
|
|
217
|
+
}
|
|
218
|
+
}
|
|
219
|
+
};
|
|
220
|
+
}
|
|
221
|
+
// src/env/task/tools/operation/get-tool.ts
|
|
222
|
+
function getOperationTool(taskComponent) {
|
|
223
|
+
return {
|
|
224
|
+
name: "task_operation_get",
|
|
225
|
+
description: "Get a single operation record by ID.",
|
|
226
|
+
parameters: GetOperationToolSchema,
|
|
227
|
+
execute: async (args, ctx) => {
|
|
228
|
+
const params = GetOperationToolSchema.parse(args);
|
|
229
|
+
try {
|
|
230
|
+
const operation = await taskComponent.getOperation(params.operation_id);
|
|
231
|
+
if (!operation) {
|
|
232
|
+
return {
|
|
233
|
+
success: false,
|
|
234
|
+
output: "",
|
|
235
|
+
error: `Operation not found: ${params.operation_id}`,
|
|
236
|
+
metadata: { execution_time_ms: 0 }
|
|
237
|
+
};
|
|
238
|
+
}
|
|
239
|
+
return {
|
|
240
|
+
success: true,
|
|
241
|
+
output: JSON.stringify(operation, null, 2),
|
|
242
|
+
metadata: { execution_time_ms: 0 }
|
|
243
|
+
};
|
|
244
|
+
} catch (error) {
|
|
245
|
+
return {
|
|
246
|
+
success: false,
|
|
247
|
+
output: "",
|
|
248
|
+
error: error instanceof Error ? error.message : String(error),
|
|
249
|
+
metadata: { execution_time_ms: 0 }
|
|
250
|
+
};
|
|
251
|
+
}
|
|
252
|
+
}
|
|
253
|
+
};
|
|
254
|
+
}
|
|
255
|
+
// src/env/task/tools/operation/list-tool.ts
|
|
256
|
+
function listOperationsTool(taskComponent) {
|
|
257
|
+
return {
|
|
258
|
+
name: "task_operation_list",
|
|
259
|
+
description: "List operation records for a task with optional filters. " + "Use milestone_type (canonical) or action_type (deprecated, auto-mapped).",
|
|
260
|
+
parameters: ListOperationsToolSchema,
|
|
261
|
+
execute: async (args, ctx) => {
|
|
262
|
+
const parsed = ListOperationsToolSchema.parse(args);
|
|
263
|
+
try {
|
|
264
|
+
const operations = await taskComponent.listOperations({
|
|
265
|
+
taskId: parsed.task_id,
|
|
266
|
+
milestoneType: parsed.milestone_type,
|
|
267
|
+
limit: parsed.limit,
|
|
268
|
+
offset: parsed.offset
|
|
269
|
+
});
|
|
270
|
+
let output = JSON.stringify({ operations, count: operations.length });
|
|
271
|
+
if (parsed._deprecated_fields_used.length > 0) {
|
|
272
|
+
output = `⚠️ DEPRECATION NOTICE: 你使用了旧的 action_type 字段,已自动映射到 milestone_type。
|
|
273
|
+
|
|
274
|
+
` + output;
|
|
275
|
+
}
|
|
276
|
+
return {
|
|
277
|
+
success: true,
|
|
278
|
+
output,
|
|
279
|
+
metadata: {
|
|
280
|
+
execution_time_ms: 0,
|
|
281
|
+
deprecated_fields_used: parsed._deprecated_fields_used
|
|
282
|
+
}
|
|
283
|
+
};
|
|
284
|
+
} catch (error) {
|
|
285
|
+
return {
|
|
286
|
+
success: false,
|
|
287
|
+
output: "",
|
|
288
|
+
error: error instanceof Error ? error.message : String(error),
|
|
289
|
+
metadata: { execution_time_ms: 0 }
|
|
290
|
+
};
|
|
291
|
+
}
|
|
292
|
+
}
|
|
293
|
+
};
|
|
294
|
+
}
|
|
295
|
+
// src/env/task/tools/operation/update-tool.ts
|
|
296
|
+
import { ZodError as ZodError2 } from "zod";
|
|
297
|
+
function formatZodError2(err) {
|
|
298
|
+
const parts = err.issues.map((i) => `${i.path.join(".") || "<root>"}: ${i.message}`);
|
|
299
|
+
return `Invalid parameters: ${parts.join("; ")}`;
|
|
300
|
+
}
|
|
301
|
+
function updateOperationTool(taskComponent) {
|
|
302
|
+
return {
|
|
303
|
+
name: "task_operation_update",
|
|
304
|
+
description: "Update an operation record. Use milestone_title / milestone_description (canonical) " + "or action_title / action_description (deprecated, auto-mapped). " + "process_description captures the process (100-150 chars).",
|
|
305
|
+
parameters: UpdateOperationToolSchema,
|
|
306
|
+
execute: async (args, ctx) => {
|
|
307
|
+
let params;
|
|
308
|
+
try {
|
|
309
|
+
const parsed = UpdateOperationToolSchema.parse(args);
|
|
310
|
+
params = parsed;
|
|
311
|
+
} catch (e) {
|
|
312
|
+
if (e instanceof ZodError2) {
|
|
313
|
+
return {
|
|
314
|
+
success: false,
|
|
315
|
+
output: "",
|
|
316
|
+
error: formatZodError2(e),
|
|
317
|
+
metadata: { execution_time_ms: 0 }
|
|
318
|
+
};
|
|
319
|
+
}
|
|
320
|
+
throw e;
|
|
321
|
+
}
|
|
322
|
+
try {
|
|
323
|
+
const operation = await taskComponent.updateOperation(params.operation_id, {
|
|
324
|
+
milestoneTitle: params.milestone_title,
|
|
325
|
+
milestoneDescription: params.milestone_description,
|
|
326
|
+
processDescription: params.process_description
|
|
327
|
+
});
|
|
328
|
+
if (!operation) {
|
|
329
|
+
return {
|
|
330
|
+
success: false,
|
|
331
|
+
output: "",
|
|
332
|
+
error: `Operation not found: ${params.operation_id}`,
|
|
333
|
+
metadata: { execution_time_ms: 0 }
|
|
334
|
+
};
|
|
335
|
+
}
|
|
336
|
+
let output = `Operation updated: #${operation.id}`;
|
|
337
|
+
if (params._deprecated_fields_used.length > 0) {
|
|
338
|
+
output += `
|
|
339
|
+
|
|
340
|
+
⚠️ DEPRECATION NOTICE: 你使用了旧的 action_* 字段 (${params._deprecated_fields_used.join(", ")}),已自动映射到 milestone_* 字段。` + "请尽快迁移到 milestone_* 字段。";
|
|
341
|
+
}
|
|
342
|
+
return {
|
|
343
|
+
success: true,
|
|
344
|
+
output,
|
|
345
|
+
metadata: {
|
|
346
|
+
execution_time_ms: 0,
|
|
347
|
+
operation,
|
|
348
|
+
deprecated_fields_used: params._deprecated_fields_used
|
|
349
|
+
}
|
|
350
|
+
};
|
|
351
|
+
} catch (error) {
|
|
352
|
+
return {
|
|
353
|
+
success: false,
|
|
354
|
+
output: "",
|
|
355
|
+
error: error instanceof Error ? error.message : String(error),
|
|
356
|
+
metadata: { execution_time_ms: 0 }
|
|
357
|
+
};
|
|
358
|
+
}
|
|
359
|
+
}
|
|
360
|
+
};
|
|
361
|
+
}
|
|
362
|
+
// src/env/task/tools/operation/delete-tool.ts
|
|
363
|
+
function deleteOperationTool(taskComponent) {
|
|
364
|
+
return {
|
|
365
|
+
name: "task_operation_delete",
|
|
366
|
+
description: "Delete an operation record.",
|
|
367
|
+
parameters: DeleteOperationToolSchema,
|
|
368
|
+
execute: async (args, ctx) => {
|
|
369
|
+
const params = DeleteOperationToolSchema.parse(args);
|
|
370
|
+
try {
|
|
371
|
+
const deleted = await taskComponent.deleteOperation(params.operation_id);
|
|
372
|
+
if (!deleted) {
|
|
373
|
+
return {
|
|
374
|
+
success: false,
|
|
375
|
+
output: "",
|
|
376
|
+
error: `Operation not found: ${params.operation_id}`,
|
|
377
|
+
metadata: { execution_time_ms: 0 }
|
|
378
|
+
};
|
|
379
|
+
}
|
|
380
|
+
return {
|
|
381
|
+
success: true,
|
|
382
|
+
output: `Operation deleted: #${params.operation_id}`,
|
|
383
|
+
metadata: { execution_time_ms: 0 }
|
|
384
|
+
};
|
|
385
|
+
} catch (error) {
|
|
386
|
+
return {
|
|
387
|
+
success: false,
|
|
388
|
+
output: "",
|
|
389
|
+
error: error instanceof Error ? error.message : String(error),
|
|
390
|
+
metadata: { execution_time_ms: 0 }
|
|
391
|
+
};
|
|
392
|
+
}
|
|
393
|
+
}
|
|
394
|
+
};
|
|
395
|
+
}
|
|
396
|
+
export { createOperationTool, getOperationTool, listOperationsTool, updateOperationTool, deleteOperationTool };
|