@thinkingai/ae-cli 1.0.24 → 1.0.28

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.
Files changed (106) hide show
  1. package/README.md +17 -2
  2. package/README.zh.md +18 -2
  3. package/dist/auth-5NSDQFQB.js +454 -0
  4. package/dist/{auth-4OPL4YWG.js → auth-H2376DEF.js} +2 -2
  5. package/dist/chunk-AD5V3ZPJ.js +217 -0
  6. package/dist/chunk-CAQYQA4R.js +399 -0
  7. package/dist/{chunk-JJCRURTR.js → chunk-CLJF7MQA.js} +1 -1
  8. package/dist/chunk-GSJGPNKK.js +49 -0
  9. package/dist/chunk-IMBKVXKY.js +478 -0
  10. package/dist/chunk-KAEZTSXN.js +99 -0
  11. package/dist/{chunk-MZW6NOVS.js → chunk-LU7SXK4Q.js} +27 -8
  12. package/dist/chunk-OJDNO5QY.js +63 -0
  13. package/dist/{chunk-DC66L5AM.js → chunk-SRJIAOBN.js} +76 -91
  14. package/dist/{chunk-OVHL4JAC.js → chunk-WCHI7725.js} +44 -47
  15. package/dist/{client-TDH6MUWM.js → client-FCMK3XEK.js} +5 -3
  16. package/dist/config-64G36TJL.js +130 -0
  17. package/dist/index.js +50 -17
  18. package/dist/model-EZ6K7FXI.js +134 -0
  19. package/dist/{raw-EM7AP3RT.js → raw-VEF3D6UD.js} +11 -6
  20. package/dist/sync-NRODEVNH.js +385 -0
  21. package/dist/te-agent-7U7JLJKU.js +524 -0
  22. package/dist/{te-analysis-3KFSNUCJ.js → te-analysis-A2OSGHQ4.js} +136 -20
  23. package/dist/{te-audience-GMYJFCSC.js → te-audience-LI67PPGO.js} +5 -4
  24. package/dist/{te-common-YLERCMQI.js → te-common-35WVU3C5.js} +19 -8
  25. package/dist/{te-community-PYDN5A6B.js → te-community-LEAP6PWT.js} +4 -3
  26. package/dist/{te-dataops-ETWS5O3X.js → te-dataops-N2LGZBOX.js} +4 -3
  27. package/dist/{te-engage-ROJVZHDA.js → te-engage-H7C72Z46.js} +105 -49
  28. package/dist/{te-kb-VUNS2CC7.js → te-kb-I2OKTBAI.js} +225 -29
  29. package/dist/{te-meta-3EFWLM3A.js → te-meta-HBTIEDRO.js} +4 -3
  30. package/dist/te-team-EM5OWRQL.js +529 -0
  31. package/package.json +10 -2
  32. package/skills/ae-agent/SKILL.md +134 -0
  33. package/skills/ae-analysis/SKILL.md +1 -1
  34. package/skills/ae-analysis/references/drilldown_user_events.md +1 -1
  35. package/skills/ae-analysis/references/drilldown_users.md +2 -2
  36. package/skills/ae-analysis/references/list_clusters.md +4 -2
  37. package/skills/ae-analysis/references/query_adhoc.md +3 -2
  38. package/skills/ae-analysis/references/query_entity_details.md +1 -1
  39. package/skills/ae-analysis-global/SKILL.md +51 -0
  40. package/skills/ae-analysis-global/references/list_query_clusters.md +67 -0
  41. package/skills/ae-community/SKILL.md +2 -3
  42. package/skills/ae-dataops/SKILL.md +1 -2
  43. package/skills/ae-engage/SKILL.md +26 -2
  44. package/skills/ae-engage/references/add-approver.md +0 -1
  45. package/skills/ae-engage/references/add-channel.md +0 -1
  46. package/skills/ae-engage/references/approver-list.md +0 -1
  47. package/skills/ae-engage/references/build-task-save-guide.md +283 -0
  48. package/skills/ae-engage/references/cancel-query-by-request-id.md +0 -1
  49. package/skills/ae-engage/references/channel-detail.md +0 -1
  50. package/skills/ae-engage/references/channel-list.md +0 -1
  51. package/skills/ae-engage/references/config-channel-detail.md +0 -1
  52. package/skills/ae-engage/references/config-channel-list.md +0 -1
  53. package/skills/ae-engage/references/config-item-analysis-report.md +0 -1
  54. package/skills/ae-engage/references/config-item-detail.md +0 -1
  55. package/skills/ae-engage/references/config-item-list.md +0 -1
  56. package/skills/ae-engage/references/config-item-strategy-comparison.md +0 -1
  57. package/skills/ae-engage/references/config-item-trigger-report.md +0 -1
  58. package/skills/ae-engage/references/copy-config-template.md +0 -1
  59. package/skills/ae-engage/references/delete-channel.md +0 -1
  60. package/skills/ae-engage/references/delete-config-channel.md +0 -1
  61. package/skills/ae-engage/references/delete-config-item.md +0 -1
  62. package/skills/ae-engage/references/delete-flow.md +0 -1
  63. package/skills/ae-engage/references/flow-ab-split-node-report.md +0 -1
  64. package/skills/ae-engage/references/flow-detail.md +0 -1
  65. package/skills/ae-engage/references/flow-list.md +0 -1
  66. package/skills/ae-engage/references/flow-node-config-schema.md +0 -1
  67. package/skills/ae-engage/references/flow-node-detail-report.md +0 -1
  68. package/skills/ae-engage/references/flow-node-overview-report.md +0 -1
  69. package/skills/ae-engage/references/flow-process-report.md +0 -1
  70. package/skills/ae-engage/references/manage-flow.md +0 -1
  71. package/skills/ae-engage/references/manage-strategy.md +0 -1
  72. package/skills/ae-engage/references/manage-task.md +0 -1
  73. package/skills/ae-engage/references/modify-flow-base-info.md +0 -1
  74. package/skills/ae-engage/references/save-task.md +304 -0
  75. package/skills/ae-engage/references/strategy-detail.md +0 -1
  76. package/skills/ae-engage/references/strategy-list.md +0 -1
  77. package/skills/ae-engage/references/task-data-detail.md +0 -1
  78. package/skills/ae-engage/references/task-data-overview.md +0 -1
  79. package/skills/ae-engage/references/task-detail.md +0 -1
  80. package/skills/ae-engage/references/task-experiment-report.md +0 -1
  81. package/skills/ae-engage/references/task-list.md +0 -1
  82. package/skills/ae-engage/references/task-metric-detail.md +0 -1
  83. package/skills/ae-engage/references/task-stats.md +0 -1
  84. package/skills/ae-engage/references/update-channel-status.md +0 -1
  85. package/skills/ae-engage/references/update-config-channel-status.md +0 -1
  86. package/skills/ae-engage/references/validate-flow-node-config.md +0 -1
  87. package/skills/ae-engage/references/whitelist-list.md +0 -1
  88. package/skills/ae-kb/SKILL.md +284 -0
  89. package/skills/ae-team/SKILL.md +164 -0
  90. package/skills/ae-team/references/ai-generate.md +39 -0
  91. package/skills/ae-team/references/create.md +94 -0
  92. package/skills/ae-team/references/delete.md +39 -0
  93. package/skills/ae-team/references/list-projects.md +45 -0
  94. package/skills/ae-team/references/list-templates.md +38 -0
  95. package/skills/ae-team/references/list.md +39 -0
  96. package/skills/ae-team/references/run-artifacts.md +51 -0
  97. package/skills/ae-team/references/run-cancel.md +38 -0
  98. package/skills/ae-team/references/run-chat.md +57 -0
  99. package/skills/ae-team/references/run-reply.md +41 -0
  100. package/skills/ae-team/references/run-result.md +75 -0
  101. package/skills/ae-team/references/run-start.md +73 -0
  102. package/skills/ae-team/references/run-watch.md +82 -0
  103. package/skills/ae-team/references/update.md +47 -0
  104. package/dist/auth-PBPAZQWP.js +0 -168
  105. package/dist/chunk-47MTN54I.js +0 -285
  106. package/dist/config-5ELRYAIH.js +0 -257
@@ -0,0 +1,524 @@
1
+ import {
2
+ deleteFromMainApp,
3
+ getFromMainApp,
4
+ patchToMainApp,
5
+ postToMainApp,
6
+ uploadToMainApp
7
+ } from "./chunk-AD5V3ZPJ.js";
8
+ import "./chunk-KAEZTSXN.js";
9
+ import "./chunk-SRJIAOBN.js";
10
+
11
+ // src/commands/te-agent/models.ts
12
+ var BASE_PATH = "/api/sandbox/agent/models";
13
+ var listModels = {
14
+ service: "agent",
15
+ command: "+list-models",
16
+ description: "List models visible to current user (personal / company / system)",
17
+ flags: [
18
+ { name: "scope", type: "string", required: false, desc: "Filter by scope: personal | company | system" }
19
+ ],
20
+ risk: "read",
21
+ validate: (ctx) => {
22
+ const scope = ctx.str("scope");
23
+ if (scope && !["personal", "company", "system"].includes(scope)) {
24
+ throw new Error("--scope must be personal, company, or system");
25
+ }
26
+ },
27
+ dryRun: (ctx) => {
28
+ const scope = ctx.str("scope");
29
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
30
+ return { method: "GET", url: `${BASE_PATH}${qs}` };
31
+ },
32
+ execute: async (ctx) => {
33
+ const scope = ctx.str("scope");
34
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
35
+ return getFromMainApp(`${BASE_PATH}${qs}`);
36
+ }
37
+ };
38
+ var addModel = {
39
+ service: "agent",
40
+ command: "+add-model",
41
+ description: "Add a custom model (personal scope)",
42
+ flags: [
43
+ { name: "model-id", type: "string", required: true, desc: "Model identifier (e.g. gpt-4o)" },
44
+ { name: "name", type: "string", required: true, desc: "Display name" },
45
+ { name: "base-url", type: "string", required: true, desc: "API base URL" },
46
+ { name: "api-key", type: "string", required: false, desc: "API key" },
47
+ { name: "provider", type: "string", required: false, desc: "Provider name" },
48
+ { name: "description", type: "string", required: false, desc: "Description" },
49
+ { name: "context-length", type: "number", required: false, desc: "Context window length" }
50
+ ],
51
+ risk: "write",
52
+ validate: (ctx) => {
53
+ const baseUrl = ctx.str("baseUrl");
54
+ try {
55
+ new URL(baseUrl);
56
+ } catch {
57
+ throw new Error("--base-url must be a valid URL");
58
+ }
59
+ },
60
+ dryRun: (ctx) => ({
61
+ method: "POST",
62
+ url: BASE_PATH,
63
+ body: {
64
+ modelId: ctx.str("modelId"),
65
+ displayName: ctx.str("name"),
66
+ baseUrl: ctx.str("baseUrl"),
67
+ apiKey: ctx.str("apiKey") || void 0,
68
+ provider: ctx.str("provider") || void 0,
69
+ description: ctx.str("description") || void 0,
70
+ contextLength: ctx.num("contextLength") || void 0
71
+ }
72
+ }),
73
+ execute: async (ctx) => {
74
+ return postToMainApp(BASE_PATH, {
75
+ modelId: ctx.str("modelId"),
76
+ displayName: ctx.str("name"),
77
+ baseUrl: ctx.str("baseUrl"),
78
+ apiKey: ctx.str("apiKey") || void 0,
79
+ provider: ctx.str("provider") || void 0,
80
+ description: ctx.str("description") || void 0,
81
+ contextLength: ctx.num("contextLength") || void 0
82
+ });
83
+ }
84
+ };
85
+ var delModel = {
86
+ service: "agent",
87
+ command: "+del-model",
88
+ description: "Delete a personal model",
89
+ flags: [
90
+ { name: "id", type: "string", required: true, desc: "Model record ID (CUID)" }
91
+ ],
92
+ risk: "write",
93
+ dryRun: (ctx) => ({
94
+ method: "DELETE",
95
+ url: `${BASE_PATH}?id=${encodeURIComponent(ctx.str("id"))}`
96
+ }),
97
+ execute: async (ctx) => {
98
+ return deleteFromMainApp(`${BASE_PATH}?id=${encodeURIComponent(ctx.str("id"))}`);
99
+ }
100
+ };
101
+ var toggleModel = {
102
+ service: "agent",
103
+ command: "+toggle-model",
104
+ description: "Enable or disable a model",
105
+ flags: [
106
+ { name: "id", type: "string", required: true, desc: "Model record ID (CUID)" },
107
+ { name: "enabled", type: "boolean", required: true, desc: "true to enable, false to disable" }
108
+ ],
109
+ risk: "write",
110
+ dryRun: (ctx) => ({
111
+ method: "PATCH",
112
+ url: BASE_PATH,
113
+ body: { id: ctx.str("id"), enabled: ctx.bool("enabled") }
114
+ }),
115
+ execute: async (ctx) => {
116
+ return patchToMainApp(BASE_PATH, {
117
+ id: ctx.str("id"),
118
+ enabled: ctx.bool("enabled")
119
+ });
120
+ }
121
+ };
122
+
123
+ // src/commands/te-agent/mcps.ts
124
+ var BASE_PATH2 = "/api/sandbox/agent/mcp-servers";
125
+ var listMcps = {
126
+ service: "agent",
127
+ command: "+list-mcps",
128
+ description: "List MCP servers visible to current user",
129
+ flags: [
130
+ { name: "scope", type: "string", required: false, desc: "Filter by scope: personal | company | system" }
131
+ ],
132
+ risk: "read",
133
+ validate: (ctx) => {
134
+ const scope = ctx.str("scope");
135
+ if (scope && !["personal", "company", "system"].includes(scope)) {
136
+ throw new Error("--scope must be personal, company, or system");
137
+ }
138
+ },
139
+ dryRun: (ctx) => {
140
+ const scope = ctx.str("scope");
141
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
142
+ return { method: "GET", url: `${BASE_PATH2}${qs}` };
143
+ },
144
+ execute: async (ctx) => {
145
+ const scope = ctx.str("scope");
146
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
147
+ return getFromMainApp(`${BASE_PATH2}${qs}`);
148
+ }
149
+ };
150
+ var addMcp = {
151
+ service: "agent",
152
+ command: "+add-mcp",
153
+ description: "Add an MCP server (personal scope)",
154
+ flags: [
155
+ { name: "name", type: "string", required: true, desc: "Server name (2-64 chars, letter start, [a-zA-Z0-9_-])" },
156
+ { name: "url", type: "string", required: true, desc: "MCP server URL" },
157
+ { name: "display-name", type: "string", required: false, desc: "Display name (max 100)" },
158
+ { name: "description", type: "string", required: false, desc: "Description (max 255)" },
159
+ { name: "transport", type: "string", required: false, default: "http", desc: "Transport: sse | http" },
160
+ { name: "headers", type: "json", required: false, desc: "HTTP headers as JSON object" }
161
+ ],
162
+ risk: "write",
163
+ validate: (ctx) => {
164
+ const name = ctx.str("name");
165
+ if (!/^[a-zA-Z][a-zA-Z0-9_-]*$/.test(name)) {
166
+ throw new Error("--name must start with a letter and contain only letters, digits, _, or -");
167
+ }
168
+ if (name.length < 2 || name.length > 64) {
169
+ throw new Error("--name length must be between 2 and 64");
170
+ }
171
+ try {
172
+ new URL(ctx.str("url"));
173
+ } catch {
174
+ throw new Error("--url must be a valid URL");
175
+ }
176
+ if (!/^https?:\/\//i.test(ctx.str("url"))) {
177
+ throw new Error("--url only supports http:// or https:// protocols");
178
+ }
179
+ const transport = ctx.str("transport");
180
+ if (transport && !["sse", "http"].includes(transport)) {
181
+ throw new Error("--transport must be sse or http");
182
+ }
183
+ },
184
+ dryRun: (ctx) => ({
185
+ method: "POST",
186
+ url: BASE_PATH2,
187
+ body: {
188
+ name: ctx.str("name"),
189
+ url: ctx.str("url"),
190
+ displayName: ctx.str("displayName") || void 0,
191
+ description: ctx.str("description") || void 0,
192
+ transport: ctx.str("transport") || "http",
193
+ headers: ctx.json("headers") || void 0
194
+ }
195
+ }),
196
+ execute: async (ctx) => {
197
+ return postToMainApp(BASE_PATH2, {
198
+ name: ctx.str("name"),
199
+ url: ctx.str("url"),
200
+ displayName: ctx.str("displayName") || void 0,
201
+ description: ctx.str("description") || void 0,
202
+ transport: ctx.str("transport") || "http",
203
+ headers: ctx.json("headers") || void 0
204
+ });
205
+ }
206
+ };
207
+ var delMcp = {
208
+ service: "agent",
209
+ command: "+del-mcp",
210
+ description: "Delete a personal MCP server",
211
+ flags: [
212
+ { name: "id", type: "string", required: true, desc: "MCP server record ID (CUID)" }
213
+ ],
214
+ risk: "write",
215
+ dryRun: (ctx) => ({
216
+ method: "DELETE",
217
+ url: `${BASE_PATH2}?id=${encodeURIComponent(ctx.str("id"))}`
218
+ }),
219
+ execute: async (ctx) => {
220
+ return deleteFromMainApp(`${BASE_PATH2}?id=${encodeURIComponent(ctx.str("id"))}`);
221
+ }
222
+ };
223
+ var toggleMcp = {
224
+ service: "agent",
225
+ command: "+toggle-mcp",
226
+ description: "Enable or disable an MCP server",
227
+ flags: [
228
+ { name: "id", type: "string", required: true, desc: "MCP server record ID (CUID)" },
229
+ { name: "enabled", type: "boolean", required: true, desc: "true to enable, false to disable" }
230
+ ],
231
+ risk: "write",
232
+ dryRun: (ctx) => ({
233
+ method: "PATCH",
234
+ url: BASE_PATH2,
235
+ body: { id: ctx.str("id"), enabled: ctx.bool("enabled") }
236
+ }),
237
+ execute: async (ctx) => {
238
+ return patchToMainApp(BASE_PATH2, {
239
+ id: ctx.str("id"),
240
+ enabled: ctx.bool("enabled")
241
+ });
242
+ }
243
+ };
244
+
245
+ // src/commands/te-agent/skills.ts
246
+ var BASE_PATH3 = "/api/sandbox/agent/skills";
247
+ async function resolveInstructions(raw) {
248
+ if (raw === "@-") {
249
+ const chunks = [];
250
+ for await (const chunk of process.stdin) {
251
+ chunks.push(chunk);
252
+ }
253
+ const text = Buffer.concat(chunks).toString("utf8").trim();
254
+ if (!text) throw new Error("stdin is empty; cannot read instructions");
255
+ return text;
256
+ }
257
+ return raw;
258
+ }
259
+ var listSkills = {
260
+ service: "agent",
261
+ command: "+list-skills",
262
+ description: "List Skills visible to current user",
263
+ flags: [
264
+ { name: "scope", type: "string", required: false, desc: "Filter by scope: personal | company | system" }
265
+ ],
266
+ risk: "read",
267
+ validate: (ctx) => {
268
+ const scope = ctx.str("scope");
269
+ if (scope && !["personal", "company", "system"].includes(scope)) {
270
+ throw new Error("--scope must be personal, company, or system");
271
+ }
272
+ },
273
+ dryRun: (ctx) => {
274
+ const scope = ctx.str("scope");
275
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
276
+ return { method: "GET", url: `${BASE_PATH3}${qs}` };
277
+ },
278
+ execute: async (ctx) => {
279
+ const scope = ctx.str("scope");
280
+ const qs = scope ? `?scope=${encodeURIComponent(scope)}` : "";
281
+ return getFromMainApp(`${BASE_PATH3}${qs}`);
282
+ }
283
+ };
284
+ var addSkill = {
285
+ service: "agent",
286
+ command: "+add-skill",
287
+ description: "Create a custom Skill (personal scope)",
288
+ flags: [
289
+ { name: "name", type: "string", required: true, desc: "Skill name (1-80 chars)" },
290
+ { name: "description", type: "string", required: true, desc: "Skill description" },
291
+ { name: "instructions", type: "string", required: true, desc: "Skill instructions (use @- to read from stdin)" },
292
+ { name: "display-name", type: "string", required: false, desc: "Display name (max 100)" }
293
+ ],
294
+ risk: "write",
295
+ validate: (ctx) => {
296
+ const name = ctx.str("name");
297
+ if (name.length < 1 || name.length > 80) {
298
+ throw new Error("--name length must be between 1 and 80");
299
+ }
300
+ },
301
+ dryRun: (ctx) => ({
302
+ method: "POST",
303
+ url: BASE_PATH3,
304
+ body: {
305
+ name: ctx.str("name"),
306
+ description: ctx.str("description"),
307
+ instructions: ctx.str("instructions") === "@-" ? "(from stdin)" : ctx.str("instructions"),
308
+ displayName: ctx.str("displayName") || void 0
309
+ }
310
+ }),
311
+ execute: async (ctx) => {
312
+ const instructions = await resolveInstructions(ctx.str("instructions"));
313
+ return postToMainApp(BASE_PATH3, {
314
+ name: ctx.str("name"),
315
+ description: ctx.str("description"),
316
+ instructions,
317
+ displayName: ctx.str("displayName") || void 0
318
+ });
319
+ }
320
+ };
321
+ var delSkill = {
322
+ service: "agent",
323
+ command: "+del-skill",
324
+ description: "Delete a personal Skill (physical delete)",
325
+ flags: [
326
+ { name: "id", type: "string", required: true, desc: "Skill record ID (CUID)" }
327
+ ],
328
+ risk: "write",
329
+ dryRun: (ctx) => ({
330
+ method: "DELETE",
331
+ url: `${BASE_PATH3}?id=${encodeURIComponent(ctx.str("id"))}`
332
+ }),
333
+ execute: async (ctx) => {
334
+ return deleteFromMainApp(`${BASE_PATH3}?id=${encodeURIComponent(ctx.str("id"))}`);
335
+ }
336
+ };
337
+ var toggleSkill = {
338
+ service: "agent",
339
+ command: "+toggle-skill",
340
+ description: "Enable or disable a Skill",
341
+ flags: [
342
+ { name: "id", type: "string", required: true, desc: "Skill record ID (CUID)" },
343
+ { name: "enabled", type: "boolean", required: true, desc: "true to enable, false to disable" }
344
+ ],
345
+ risk: "write",
346
+ dryRun: (ctx) => ({
347
+ method: "PATCH",
348
+ url: BASE_PATH3,
349
+ body: { id: ctx.str("id"), enabled: ctx.bool("enabled") }
350
+ }),
351
+ execute: async (ctx) => {
352
+ return patchToMainApp(BASE_PATH3, {
353
+ id: ctx.str("id"),
354
+ enabled: ctx.bool("enabled")
355
+ });
356
+ }
357
+ };
358
+
359
+ // src/commands/te-agent/attachments.ts
360
+ import { readFileSync, existsSync } from "fs";
361
+ import { resolve, basename, extname } from "path";
362
+ var LIST_PATH = "/api/sandbox/agent/attachments";
363
+ var UPLOAD_PATH = "/api/sandbox/agent/attachments/upload";
364
+ function guessMimeType(filePath) {
365
+ const ext = extname(filePath).toLowerCase();
366
+ const map = {
367
+ ".png": "image/png",
368
+ ".jpg": "image/jpeg",
369
+ ".jpeg": "image/jpeg",
370
+ ".gif": "image/gif",
371
+ ".webp": "image/webp",
372
+ ".svg": "image/svg+xml",
373
+ ".pdf": "application/pdf",
374
+ ".md": "text/markdown",
375
+ ".txt": "text/plain",
376
+ ".csv": "text/csv",
377
+ ".json": "application/json",
378
+ ".html": "text/html",
379
+ ".xml": "application/xml",
380
+ ".doc": "application/msword",
381
+ ".docx": "application/vnd.openxmlformats-officedocument.wordprocessingml.document",
382
+ ".xls": "application/vnd.ms-excel",
383
+ ".xlsx": "application/vnd.openxmlformats-officedocument.spreadsheetml.sheet",
384
+ ".pptx": "application/vnd.openxmlformats-officedocument.presentationml.presentation",
385
+ ".zip": "application/zip"
386
+ };
387
+ return map[ext] || "application/octet-stream";
388
+ }
389
+ function resolveFilePaths(ctx) {
390
+ const file = ctx.str("file");
391
+ const files = ctx.str("files");
392
+ if (file && files) {
393
+ throw new Error("--file and --files cannot be used together");
394
+ }
395
+ if (!file && !files) {
396
+ throw new Error("Either --file or --files must be specified");
397
+ }
398
+ if (file) return [file];
399
+ try {
400
+ const parsed = JSON.parse(files);
401
+ if (!Array.isArray(parsed)) throw new Error("--files must be a JSON array");
402
+ return parsed.map((p) => {
403
+ if (typeof p !== "string") throw new Error("--files array elements must be strings");
404
+ return p;
405
+ });
406
+ } catch (err) {
407
+ if (err instanceof SyntaxError) throw new Error("--files must be a valid JSON array");
408
+ throw err;
409
+ }
410
+ }
411
+ async function uploadFiles(filePaths) {
412
+ const formData = new FormData();
413
+ for (const filePath of filePaths) {
414
+ const resolved = resolve(filePath);
415
+ if (!existsSync(resolved)) {
416
+ throw new Error(`File not found: ${resolved}`);
417
+ }
418
+ const buffer = readFileSync(resolved);
419
+ const mimeType = guessMimeType(resolved);
420
+ const blob = new Blob([buffer], { type: mimeType });
421
+ formData.append("file", blob, basename(resolved));
422
+ }
423
+ return uploadToMainApp(UPLOAD_PATH, formData);
424
+ }
425
+ var listAttachments = {
426
+ service: "agent",
427
+ command: "+list-attachments",
428
+ description: "List user attachments (paginated)",
429
+ flags: [
430
+ { name: "q", type: "string", required: false, desc: "Search keyword" },
431
+ { name: "type", type: "string", required: false, desc: "Filter by type: image | document" },
432
+ { name: "page", type: "number", required: false, desc: "Page number (default 1)" },
433
+ { name: "page-size", type: "number", required: false, desc: "Page size (default 20, max 100)" }
434
+ ],
435
+ risk: "read",
436
+ validate: (ctx) => {
437
+ const type = ctx.str("type");
438
+ if (type && !["image", "document"].includes(type)) {
439
+ throw new Error("--type must be image or document");
440
+ }
441
+ },
442
+ dryRun: (ctx) => {
443
+ const params = new URLSearchParams();
444
+ if (ctx.str("q")) params.set("q", ctx.str("q"));
445
+ if (ctx.str("type")) params.set("type", ctx.str("type"));
446
+ if (ctx.num("page")) params.set("page", String(ctx.num("page")));
447
+ if (ctx.num("pageSize")) params.set("pageSize", String(ctx.num("pageSize")));
448
+ const qs = params.toString();
449
+ return { method: "GET", url: `${LIST_PATH}${qs ? "?" + qs : ""}` };
450
+ },
451
+ execute: async (ctx) => {
452
+ const params = new URLSearchParams();
453
+ if (ctx.str("q")) params.set("q", ctx.str("q"));
454
+ if (ctx.str("type")) params.set("type", ctx.str("type"));
455
+ if (ctx.num("page")) params.set("page", String(ctx.num("page")));
456
+ if (ctx.num("pageSize")) params.set("pageSize", String(ctx.num("pageSize")));
457
+ const qs = params.toString();
458
+ return getFromMainApp(`${LIST_PATH}${qs ? "?" + qs : ""}`);
459
+ }
460
+ };
461
+ var addAttachment = {
462
+ service: "agent",
463
+ command: "+add-attachment",
464
+ description: "Upload sandbox file(s) to attachment library",
465
+ flags: [
466
+ { name: "file", type: "string", required: false, desc: "Single file path" },
467
+ { name: "files", type: "string", required: false, desc: `JSON array of file paths, e.g. '["./a.png","./b.pdf"]'` }
468
+ ],
469
+ risk: "write",
470
+ validate: (ctx) => {
471
+ resolveFilePaths(ctx);
472
+ },
473
+ dryRun: (ctx) => {
474
+ const paths = resolveFilePaths(ctx);
475
+ return { method: "POST", url: UPLOAD_PATH, body: { files: paths } };
476
+ },
477
+ execute: async (ctx) => {
478
+ const paths = resolveFilePaths(ctx);
479
+ return uploadFiles(paths);
480
+ }
481
+ };
482
+ var delAttachment = {
483
+ service: "agent",
484
+ command: "+del-attachment",
485
+ description: "Soft-delete an attachment",
486
+ flags: [
487
+ { name: "id", type: "string", required: true, desc: "Attachment ID" }
488
+ ],
489
+ risk: "write",
490
+ dryRun: (ctx) => ({
491
+ method: "DELETE",
492
+ url: `${LIST_PATH}?id=${encodeURIComponent(ctx.str("id"))}`
493
+ }),
494
+ execute: async (ctx) => {
495
+ return deleteFromMainApp(`${LIST_PATH}?id=${encodeURIComponent(ctx.str("id"))}`);
496
+ }
497
+ };
498
+
499
+ // src/commands/te-agent/index.ts
500
+ var commands = [
501
+ // Model management
502
+ listModels,
503
+ addModel,
504
+ delModel,
505
+ toggleModel,
506
+ // MCP server management
507
+ listMcps,
508
+ addMcp,
509
+ delMcp,
510
+ toggleMcp,
511
+ // Skill management
512
+ listSkills,
513
+ addSkill,
514
+ delSkill,
515
+ toggleSkill,
516
+ // Attachment library management
517
+ listAttachments,
518
+ addAttachment,
519
+ delAttachment
520
+ ];
521
+ var te_agent_default = commands;
522
+ export {
523
+ te_agent_default as default
524
+ };