terminal-pilot 0.0.20 → 0.0.21
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/cli.js +544 -259
- package/dist/cli.js.map +4 -4
- package/dist/commands/close-session.js.map +1 -1
- package/dist/commands/create-session.js.map +1 -1
- package/dist/commands/fill.js.map +1 -1
- package/dist/commands/get-session.js.map +1 -1
- package/dist/commands/index.js +220 -126
- package/dist/commands/index.js.map +4 -4
- package/dist/commands/install.js +187 -93
- package/dist/commands/install.js.map +4 -4
- package/dist/commands/installer.js +154 -60
- package/dist/commands/installer.js.map +4 -4
- package/dist/commands/list-sessions.js.map +1 -1
- package/dist/commands/press-key.js.map +1 -1
- package/dist/commands/read-history.js.map +1 -1
- package/dist/commands/read-screen.js.map +1 -1
- package/dist/commands/resize.js.map +1 -1
- package/dist/commands/runtime.js.map +1 -1
- package/dist/commands/screenshot.js.map +1 -1
- package/dist/commands/send-signal.js.map +1 -1
- package/dist/commands/type.js.map +1 -1
- package/dist/commands/uninstall.js +187 -93
- package/dist/commands/uninstall.js.map +4 -4
- package/dist/commands/wait-for-exit.js.map +1 -1
- package/dist/commands/wait-for.js.map +1 -1
- package/dist/testing/cli-repl.js +544 -259
- package/dist/testing/cli-repl.js.map +4 -4
- package/dist/testing/qa-cli.js +544 -259
- package/dist/testing/qa-cli.js.map +4 -4
- package/package.json +2 -1
package/dist/testing/qa-cli.js
CHANGED
|
@@ -85,7 +85,7 @@ function consumeTerminatedString(input, index, allowBellTerminator) {
|
|
|
85
85
|
}
|
|
86
86
|
|
|
87
87
|
// src/cli.ts
|
|
88
|
-
import { realpath as
|
|
88
|
+
import { realpath as realpath3 } from "node:fs/promises";
|
|
89
89
|
import path23 from "node:path";
|
|
90
90
|
import { fileURLToPath as fileURLToPath5 } from "node:url";
|
|
91
91
|
|
|
@@ -99,7 +99,7 @@ import {
|
|
|
99
99
|
Option
|
|
100
100
|
} from "commander";
|
|
101
101
|
|
|
102
|
-
// ../design
|
|
102
|
+
// ../toolcraft-design/src/internal/color-support.ts
|
|
103
103
|
function supportsColor(env = process.env, stream = process.stdout) {
|
|
104
104
|
if (env.FORCE_COLOR !== void 0 && env.FORCE_COLOR !== "0") {
|
|
105
105
|
return true;
|
|
@@ -113,7 +113,7 @@ function supportsColor(env = process.env, stream = process.stdout) {
|
|
|
113
113
|
return typeof env.TERM === "string" && env.TERM.length > 0 && env.TERM !== "dumb";
|
|
114
114
|
}
|
|
115
115
|
|
|
116
|
-
// ../design
|
|
116
|
+
// ../toolcraft-design/src/components/color.ts
|
|
117
117
|
var reset = "\x1B[0m";
|
|
118
118
|
var ansiStyles = {
|
|
119
119
|
reset: { open: reset },
|
|
@@ -215,41 +215,135 @@ function createColor(styles = []) {
|
|
|
215
215
|
}
|
|
216
216
|
var color = createColor();
|
|
217
217
|
|
|
218
|
-
// ../design
|
|
219
|
-
var
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
|
|
223
|
-
number: (text5) => color.cyanBright(text5),
|
|
224
|
-
intro: (text5) => color.bgMagenta.white(` Poe - ${text5} `),
|
|
225
|
-
resolvedSymbol: color.magenta("\u25C7"),
|
|
226
|
-
errorSymbol: color.red("\u25A0"),
|
|
227
|
-
accent: (text5) => color.cyan(text5),
|
|
228
|
-
muted: (text5) => color.dim(text5),
|
|
229
|
-
success: (text5) => color.green(text5),
|
|
230
|
-
warning: (text5) => color.yellow(text5),
|
|
231
|
-
error: (text5) => color.red(text5),
|
|
232
|
-
info: (text5) => color.magenta(text5),
|
|
233
|
-
badge: (text5) => color.bgYellow.black(` ${text5} `)
|
|
218
|
+
// ../toolcraft-design/src/tokens/brand.ts
|
|
219
|
+
var brands = {
|
|
220
|
+
purple: { name: "purple", primary: "#a200ff" },
|
|
221
|
+
blue: { name: "blue", primary: "#2f6fed" },
|
|
222
|
+
green: { name: "green", primary: "#1f9d57" }
|
|
234
223
|
};
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
intro: (text5) => color.bgHex("#a200ff").white(` Poe - ${text5} `),
|
|
241
|
-
resolvedSymbol: color.hex("#a200ff")("\u25C7"),
|
|
242
|
-
errorSymbol: color.hex("#cc0000")("\u25A0"),
|
|
243
|
-
accent: (text5) => color.hex("#006699").bold(text5),
|
|
244
|
-
muted: (text5) => color.hex("#666666")(text5),
|
|
245
|
-
success: (text5) => color.hex("#008800")(text5),
|
|
246
|
-
warning: (text5) => color.hex("#cc6600")(text5),
|
|
247
|
-
error: (text5) => color.hex("#cc0000")(text5),
|
|
248
|
-
info: (text5) => color.hex("#a200ff")(text5),
|
|
249
|
-
badge: (text5) => color.bgHex("#cc6600").white(` ${text5} `)
|
|
224
|
+
|
|
225
|
+
// ../toolcraft-design/src/internal/theme-state.ts
|
|
226
|
+
var defaults = {
|
|
227
|
+
brand: "purple",
|
|
228
|
+
label: "Poe"
|
|
250
229
|
};
|
|
230
|
+
var config = { ...defaults };
|
|
231
|
+
var revision = 0;
|
|
232
|
+
var brandConfigured = false;
|
|
233
|
+
function configureTheme(patch) {
|
|
234
|
+
if (patch.brand !== void 0 && !Object.hasOwn(brands, patch.brand)) {
|
|
235
|
+
throw new Error(`Unknown brand: ${patch.brand}`);
|
|
236
|
+
}
|
|
237
|
+
config = {
|
|
238
|
+
brand: patch.brand ?? config.brand,
|
|
239
|
+
label: patch.label ?? config.label
|
|
240
|
+
};
|
|
241
|
+
if (patch.brand !== void 0) {
|
|
242
|
+
brandConfigured = true;
|
|
243
|
+
}
|
|
244
|
+
revision += 1;
|
|
245
|
+
}
|
|
246
|
+
function getThemeConfig() {
|
|
247
|
+
return { ...config };
|
|
248
|
+
}
|
|
249
|
+
function getThemeRevision() {
|
|
250
|
+
return revision;
|
|
251
|
+
}
|
|
252
|
+
function isThemeBrandConfigured() {
|
|
253
|
+
return brandConfigured;
|
|
254
|
+
}
|
|
251
255
|
|
|
252
|
-
// ../design
|
|
256
|
+
// ../toolcraft-design/src/tokens/colors.ts
|
|
257
|
+
var brand = brands.purple.primary;
|
|
258
|
+
function withStyles(palette, styles) {
|
|
259
|
+
return Object.defineProperty(palette, "styles", {
|
|
260
|
+
value: styles,
|
|
261
|
+
enumerable: false
|
|
262
|
+
});
|
|
263
|
+
}
|
|
264
|
+
function brandColor(activeBrand, purple) {
|
|
265
|
+
return activeBrand.name === "purple" ? purple : color.hex(activeBrand.primary);
|
|
266
|
+
}
|
|
267
|
+
function brandBackground(activeBrand, purple) {
|
|
268
|
+
return activeBrand.name === "purple" ? purple : color.bgHex(activeBrand.primary);
|
|
269
|
+
}
|
|
270
|
+
function createPalette(activeBrand, mode) {
|
|
271
|
+
const isPurple = activeBrand.name === "purple";
|
|
272
|
+
if (mode === "light") {
|
|
273
|
+
const active2 = color.hex(activeBrand.primary);
|
|
274
|
+
const prompt2 = isPurple ? color.hex("#006699") : active2;
|
|
275
|
+
const number2 = isPurple ? color.hex("#0077cc") : active2;
|
|
276
|
+
return withStyles(
|
|
277
|
+
{
|
|
278
|
+
header: (text5) => active2.bold(text5),
|
|
279
|
+
divider: (text5) => color.hex("#666666")(text5),
|
|
280
|
+
prompt: (text5) => prompt2.bold(text5),
|
|
281
|
+
number: (text5) => number2.bold(text5),
|
|
282
|
+
intro: (text5) => color.bgHex(activeBrand.primary).white(` ${getThemeConfig().label} - ${text5} `),
|
|
283
|
+
get resolvedSymbol() {
|
|
284
|
+
return active2("\u25C7");
|
|
285
|
+
},
|
|
286
|
+
get errorSymbol() {
|
|
287
|
+
return color.hex("#cc0000")("\u25A0");
|
|
288
|
+
},
|
|
289
|
+
accent: (text5) => prompt2.bold(text5),
|
|
290
|
+
muted: (text5) => color.hex("#666666")(text5),
|
|
291
|
+
success: (text5) => color.hex("#008800")(text5),
|
|
292
|
+
warning: (text5) => color.hex("#cc6600")(text5),
|
|
293
|
+
error: (text5) => color.hex("#cc0000")(text5),
|
|
294
|
+
info: (text5) => active2(text5),
|
|
295
|
+
badge: (text5) => color.bgHex("#cc6600").white(` ${text5} `)
|
|
296
|
+
},
|
|
297
|
+
{
|
|
298
|
+
accent: { fg: isPurple ? "#006699" : activeBrand.primary, bold: true },
|
|
299
|
+
muted: { fg: "#666666" },
|
|
300
|
+
success: { fg: "#008800" },
|
|
301
|
+
warning: { fg: "#cc6600" },
|
|
302
|
+
error: { fg: "#cc0000" },
|
|
303
|
+
info: { fg: activeBrand.primary }
|
|
304
|
+
}
|
|
305
|
+
);
|
|
306
|
+
}
|
|
307
|
+
const active = brandColor(activeBrand, color.magenta);
|
|
308
|
+
const activeBright = brandColor(activeBrand, color.magentaBright);
|
|
309
|
+
const activeBackground = brandBackground(activeBrand, color.bgMagenta);
|
|
310
|
+
const prompt = isPurple ? color.cyan : active;
|
|
311
|
+
const number = isPurple ? color.cyanBright : active;
|
|
312
|
+
return withStyles(
|
|
313
|
+
{
|
|
314
|
+
header: (text5) => activeBright.bold(text5),
|
|
315
|
+
divider: (text5) => color.dim(text5),
|
|
316
|
+
prompt: (text5) => prompt(text5),
|
|
317
|
+
number: (text5) => number(text5),
|
|
318
|
+
intro: (text5) => activeBackground.white(` ${getThemeConfig().label} - ${text5} `),
|
|
319
|
+
get resolvedSymbol() {
|
|
320
|
+
return active("\u25C7");
|
|
321
|
+
},
|
|
322
|
+
get errorSymbol() {
|
|
323
|
+
return color.red("\u25A0");
|
|
324
|
+
},
|
|
325
|
+
accent: (text5) => prompt(text5),
|
|
326
|
+
muted: (text5) => color.dim(text5),
|
|
327
|
+
success: (text5) => color.green(text5),
|
|
328
|
+
warning: (text5) => color.yellow(text5),
|
|
329
|
+
error: (text5) => color.red(text5),
|
|
330
|
+
info: (text5) => active(text5),
|
|
331
|
+
badge: (text5) => color.bgYellow.black(` ${text5} `)
|
|
332
|
+
},
|
|
333
|
+
{
|
|
334
|
+
accent: { fg: isPurple ? "cyan" : activeBrand.primary, bold: true },
|
|
335
|
+
muted: { dim: true },
|
|
336
|
+
success: { fg: "green" },
|
|
337
|
+
warning: { fg: "yellow" },
|
|
338
|
+
error: { fg: "red" },
|
|
339
|
+
info: { fg: isPurple ? "magenta" : activeBrand.primary }
|
|
340
|
+
}
|
|
341
|
+
);
|
|
342
|
+
}
|
|
343
|
+
var dark = createPalette(brands.purple, "dark");
|
|
344
|
+
var light = createPalette(brands.purple, "light");
|
|
345
|
+
|
|
346
|
+
// ../toolcraft-design/src/tokens/typography.ts
|
|
253
347
|
var typography = {
|
|
254
348
|
bold: (text5) => color.bold(text5),
|
|
255
349
|
dim: (text5) => color.dim(text5),
|
|
@@ -258,14 +352,14 @@ var typography = {
|
|
|
258
352
|
strikethrough: (text5) => color.strikethrough(text5)
|
|
259
353
|
};
|
|
260
354
|
|
|
261
|
-
// ../design
|
|
355
|
+
// ../toolcraft-design/src/tokens/widths.ts
|
|
262
356
|
var widths = {
|
|
263
357
|
header: 60,
|
|
264
358
|
helpColumn: 24,
|
|
265
359
|
maxLine: 80
|
|
266
360
|
};
|
|
267
361
|
|
|
268
|
-
// ../design
|
|
362
|
+
// ../toolcraft-design/src/internal/output-format.ts
|
|
269
363
|
import { AsyncLocalStorage } from "node:async_hooks";
|
|
270
364
|
var VALID_FORMATS = /* @__PURE__ */ new Set(["terminal", "markdown", "json"]);
|
|
271
365
|
var formatStorage = new AsyncLocalStorage();
|
|
@@ -286,7 +380,7 @@ function resetOutputFormatCache() {
|
|
|
286
380
|
cached = void 0;
|
|
287
381
|
}
|
|
288
382
|
|
|
289
|
-
// ../design
|
|
383
|
+
// ../toolcraft-design/src/internal/theme-detect.ts
|
|
290
384
|
function detectThemeFromEnv(env) {
|
|
291
385
|
const apple = env.APPLE_INTERFACE_STYLE;
|
|
292
386
|
if (typeof apple === "string") {
|
|
@@ -323,17 +417,30 @@ function resolveThemeName(env = process.env) {
|
|
|
323
417
|
}
|
|
324
418
|
return "dark";
|
|
325
419
|
}
|
|
326
|
-
var
|
|
420
|
+
var themeCache = /* @__PURE__ */ new Map();
|
|
421
|
+
var cachedRevision = -1;
|
|
327
422
|
function getTheme(env) {
|
|
423
|
+
const themeName = resolveThemeName(env);
|
|
424
|
+
const config2 = getThemeConfig();
|
|
425
|
+
const requestedBrand = env?.POE_BRAND?.toLowerCase();
|
|
426
|
+
const activeBrandName = !isThemeBrandConfigured() && requestedBrand && Object.hasOwn(brands, requestedBrand) ? requestedBrand : config2.brand;
|
|
427
|
+
const revision2 = getThemeRevision();
|
|
428
|
+
if (revision2 !== cachedRevision) {
|
|
429
|
+
themeCache.clear();
|
|
430
|
+
cachedRevision = revision2;
|
|
431
|
+
}
|
|
432
|
+
const cacheKey = `${activeBrandName}:${themeName}`;
|
|
433
|
+
const cachedTheme = themeCache.get(cacheKey);
|
|
328
434
|
if (cachedTheme) {
|
|
329
435
|
return cachedTheme;
|
|
330
436
|
}
|
|
331
|
-
const
|
|
332
|
-
|
|
333
|
-
|
|
437
|
+
const activeBrand = brands[activeBrandName];
|
|
438
|
+
const theme = activeBrandName === "purple" ? themeName === "light" ? light : dark : createPalette(activeBrand, themeName);
|
|
439
|
+
themeCache.set(cacheKey, theme);
|
|
440
|
+
return theme;
|
|
334
441
|
}
|
|
335
442
|
|
|
336
|
-
// ../design
|
|
443
|
+
// ../toolcraft-design/src/components/text.ts
|
|
337
444
|
function renderMarkdownInline(content) {
|
|
338
445
|
return content.replaceAll("\r\n", " ").replaceAll("\n", " ").replaceAll("\r", " ");
|
|
339
446
|
}
|
|
@@ -449,7 +556,7 @@ var text = {
|
|
|
449
556
|
}
|
|
450
557
|
};
|
|
451
558
|
|
|
452
|
-
// ../design
|
|
559
|
+
// ../toolcraft-design/src/components/symbols.ts
|
|
453
560
|
var symbols = {
|
|
454
561
|
get info() {
|
|
455
562
|
const format = resolveOutputFormat();
|
|
@@ -503,12 +610,12 @@ var symbols = {
|
|
|
503
610
|
}
|
|
504
611
|
};
|
|
505
612
|
|
|
506
|
-
// ../design
|
|
613
|
+
// ../toolcraft-design/src/internal/strip-ansi.ts
|
|
507
614
|
function stripAnsi2(value) {
|
|
508
615
|
return value.replace(/\u001b\[[0-9;]*m/g, "");
|
|
509
616
|
}
|
|
510
617
|
|
|
511
|
-
// ../design
|
|
618
|
+
// ../toolcraft-design/src/prompts/primitives/log.ts
|
|
512
619
|
function renderMarkdownInline2(value) {
|
|
513
620
|
return stripAnsi2(value).replaceAll("\r\n", " ").replaceAll("\n", " ").replaceAll("\r", " ");
|
|
514
621
|
}
|
|
@@ -635,7 +742,7 @@ var log = {
|
|
|
635
742
|
error
|
|
636
743
|
};
|
|
637
744
|
|
|
638
|
-
// ../design
|
|
745
|
+
// ../toolcraft-design/src/components/logger.ts
|
|
639
746
|
function createLogger(emitter) {
|
|
640
747
|
const emit = (level, message2) => {
|
|
641
748
|
if (emitter) {
|
|
@@ -696,7 +803,7 @@ function createLogger(emitter) {
|
|
|
696
803
|
}
|
|
697
804
|
var logger = createLogger();
|
|
698
805
|
|
|
699
|
-
// ../design
|
|
806
|
+
// ../toolcraft-design/src/components/help-formatter.ts
|
|
700
807
|
var graphemeSegmenter = new Intl.Segmenter(void 0, { granularity: "grapheme" });
|
|
701
808
|
function normalizeInline(value) {
|
|
702
809
|
return value.replaceAll("\r\n", " ").replaceAll("\n", " ").replaceAll("\r", " ");
|
|
@@ -872,7 +979,7 @@ function formatOptionList(options) {
|
|
|
872
979
|
});
|
|
873
980
|
}
|
|
874
981
|
|
|
875
|
-
// ../design
|
|
982
|
+
// ../toolcraft-design/src/components/help-formatter-plain.ts
|
|
876
983
|
var help_formatter_plain_exports = {};
|
|
877
984
|
__export(help_formatter_plain_exports, {
|
|
878
985
|
formatColumns: () => formatColumns2,
|
|
@@ -1009,7 +1116,7 @@ function formatOptionList2(options) {
|
|
|
1009
1116
|
});
|
|
1010
1117
|
}
|
|
1011
1118
|
|
|
1012
|
-
// ../design
|
|
1119
|
+
// ../toolcraft-design/src/components/table.ts
|
|
1013
1120
|
var reset2 = "\x1B[0m";
|
|
1014
1121
|
var ellipsis = "\u2026";
|
|
1015
1122
|
var graphemeSegmenter2 = new Intl.Segmenter(void 0, { granularity: "grapheme" });
|
|
@@ -1293,7 +1400,7 @@ function renderTable(options) {
|
|
|
1293
1400
|
}
|
|
1294
1401
|
}
|
|
1295
1402
|
|
|
1296
|
-
// ../design
|
|
1403
|
+
// ../toolcraft-design/src/components/detail-card.ts
|
|
1297
1404
|
function wrap(value, width) {
|
|
1298
1405
|
const lines = [];
|
|
1299
1406
|
for (const paragraph of value.split("\n")) {
|
|
@@ -1356,7 +1463,7 @@ ${options.theme.muted(options.badges.map((badge) => badge[0] + badge.slice(1).to
|
|
|
1356
1463
|
return blocks.join("\n\n");
|
|
1357
1464
|
}
|
|
1358
1465
|
|
|
1359
|
-
// ../design
|
|
1466
|
+
// ../toolcraft-design/src/components/template.ts
|
|
1360
1467
|
var MAX_PARTIAL_DEPTH = 100;
|
|
1361
1468
|
var HTML_ESCAPE = {
|
|
1362
1469
|
"&": "&",
|
|
@@ -1768,22 +1875,22 @@ function hasProperty(value, key2) {
|
|
|
1768
1875
|
return Object.prototype.hasOwnProperty.call(value, key2);
|
|
1769
1876
|
}
|
|
1770
1877
|
|
|
1771
|
-
// ../design
|
|
1878
|
+
// ../toolcraft-design/src/components/browser.ts
|
|
1772
1879
|
import { spawn } from "node:child_process";
|
|
1773
1880
|
import process2 from "node:process";
|
|
1774
1881
|
|
|
1775
|
-
// ../design
|
|
1882
|
+
// ../toolcraft-design/src/acp/writer.ts
|
|
1776
1883
|
import { AsyncLocalStorage as AsyncLocalStorage2 } from "node:async_hooks";
|
|
1777
1884
|
var storage = new AsyncLocalStorage2();
|
|
1778
1885
|
|
|
1779
|
-
// ../design
|
|
1886
|
+
// ../toolcraft-design/src/dashboard/terminal-width.ts
|
|
1780
1887
|
var graphemeSegmenter3 = new Intl.Segmenter(void 0, { granularity: "grapheme" });
|
|
1781
1888
|
|
|
1782
|
-
// ../design
|
|
1889
|
+
// ../toolcraft-design/src/dashboard/terminal.ts
|
|
1783
1890
|
import readline from "node:readline";
|
|
1784
1891
|
import { PassThrough } from "node:stream";
|
|
1785
1892
|
|
|
1786
|
-
// ../design
|
|
1893
|
+
// ../toolcraft-design/src/explorer/state.ts
|
|
1787
1894
|
var REGION_HEADER = 1 << 0;
|
|
1788
1895
|
var REGION_LIST = 1 << 1;
|
|
1789
1896
|
var REGION_DETAIL = 1 << 2;
|
|
@@ -1792,10 +1899,10 @@ var REGION_MODAL = 1 << 4;
|
|
|
1792
1899
|
var REGION_TOAST = 1 << 5;
|
|
1793
1900
|
var REGION_ALL = REGION_HEADER | REGION_LIST | REGION_DETAIL | REGION_FOOTER | REGION_MODAL | REGION_TOAST;
|
|
1794
1901
|
|
|
1795
|
-
// ../design
|
|
1902
|
+
// ../toolcraft-design/src/prompts/index.ts
|
|
1796
1903
|
import * as clack from "@clack/prompts";
|
|
1797
1904
|
|
|
1798
|
-
// ../design
|
|
1905
|
+
// ../toolcraft-design/src/prompts/primitives/cancel.ts
|
|
1799
1906
|
import { isCancel } from "@clack/prompts";
|
|
1800
1907
|
function cancel(msg = "") {
|
|
1801
1908
|
if (resolveOutputFormat() !== "terminal") {
|
|
@@ -1806,7 +1913,7 @@ function cancel(msg = "") {
|
|
|
1806
1913
|
`);
|
|
1807
1914
|
}
|
|
1808
1915
|
|
|
1809
|
-
// ../design
|
|
1916
|
+
// ../toolcraft-design/src/prompts/primitives/note.ts
|
|
1810
1917
|
function getVisibleWidth(value) {
|
|
1811
1918
|
return stripAnsi2(value).length;
|
|
1812
1919
|
}
|
|
@@ -1855,10 +1962,10 @@ function note(message2, title) {
|
|
|
1855
1962
|
`);
|
|
1856
1963
|
}
|
|
1857
1964
|
|
|
1858
|
-
// ../design
|
|
1965
|
+
// ../toolcraft-design/src/static/spinner.ts
|
|
1859
1966
|
var SPINNER_FRAMES = Object.freeze(["\u25D2", "\u25D0", "\u25D3", "\u25D1"]);
|
|
1860
1967
|
|
|
1861
|
-
// ../design
|
|
1968
|
+
// ../toolcraft-design/src/prompts/index.ts
|
|
1862
1969
|
async function select2(opts) {
|
|
1863
1970
|
return clack.select(opts);
|
|
1864
1971
|
}
|
|
@@ -1901,19 +2008,19 @@ var ApprovalDeclinedError = class extends UserError {
|
|
|
1901
2008
|
};
|
|
1902
2009
|
|
|
1903
2010
|
// ../toolcraft/src/human-in-loop/config.ts
|
|
1904
|
-
function validateHumanInLoopOnDefine(
|
|
1905
|
-
const label = Array.isArray(
|
|
1906
|
-
if (
|
|
1907
|
-
throw new Error(`${label} '${
|
|
2011
|
+
function validateHumanInLoopOnDefine(config2) {
|
|
2012
|
+
const label = Array.isArray(config2.children) ? "group" : "command";
|
|
2013
|
+
if (config2.confirm === true && config2.humanInLoop !== void 0 && config2.humanInLoop !== null) {
|
|
2014
|
+
throw new Error(`${label} '${config2.name}': use either confirm or humanInLoop, not both`);
|
|
1908
2015
|
}
|
|
1909
|
-
if (
|
|
2016
|
+
if (config2.humanInLoop === void 0 || config2.humanInLoop === null) {
|
|
1910
2017
|
return;
|
|
1911
2018
|
}
|
|
1912
|
-
if (
|
|
1913
|
-
throw new Error(`${label} '${
|
|
2019
|
+
if (config2.humanInLoop.mode !== "sync" && config2.humanInLoop.mode !== "async") {
|
|
2020
|
+
throw new Error(`${label} '${config2.name}': humanInLoop.mode must be "sync" or "async"`);
|
|
1914
2021
|
}
|
|
1915
|
-
if (typeof
|
|
1916
|
-
throw new Error(`${label} '${
|
|
2022
|
+
if (typeof config2.humanInLoop.message !== "function") {
|
|
2023
|
+
throw new Error(`${label} '${config2.name}': humanInLoop.message must be a function`);
|
|
1917
2024
|
}
|
|
1918
2025
|
}
|
|
1919
2026
|
function mergeHumanInLoopFromGroup(groupHumanInLoop, childHumanInLoop) {
|
|
@@ -1989,12 +2096,12 @@ function assertValidBranches(branches, discriminator) {
|
|
|
1989
2096
|
}
|
|
1990
2097
|
}
|
|
1991
2098
|
}
|
|
1992
|
-
function OneOf(
|
|
1993
|
-
assertValidBranches(
|
|
2099
|
+
function OneOf(config2) {
|
|
2100
|
+
assertValidBranches(config2.branches, config2.discriminator);
|
|
1994
2101
|
return {
|
|
1995
2102
|
kind: "oneOf",
|
|
1996
|
-
discriminator:
|
|
1997
|
-
branches:
|
|
2103
|
+
discriminator: config2.discriminator,
|
|
2104
|
+
branches: config2.branches
|
|
1998
2105
|
};
|
|
1999
2106
|
}
|
|
2000
2107
|
|
|
@@ -2244,22 +2351,22 @@ function cloneStringArray(values) {
|
|
|
2244
2351
|
function cloneStringRecord(values) {
|
|
2245
2352
|
return values === void 0 ? void 0 : { ...values };
|
|
2246
2353
|
}
|
|
2247
|
-
function cloneMcpServerConfig(
|
|
2248
|
-
if (
|
|
2354
|
+
function cloneMcpServerConfig(config2) {
|
|
2355
|
+
if (config2 === void 0) {
|
|
2249
2356
|
return void 0;
|
|
2250
2357
|
}
|
|
2251
|
-
if (
|
|
2358
|
+
if (config2.transport === "stdio") {
|
|
2252
2359
|
return {
|
|
2253
2360
|
transport: "stdio",
|
|
2254
|
-
command:
|
|
2255
|
-
args: cloneStringArray(
|
|
2256
|
-
env: cloneStringRecord(
|
|
2361
|
+
command: config2.command,
|
|
2362
|
+
args: cloneStringArray(config2.args),
|
|
2363
|
+
env: cloneStringRecord(config2.env)
|
|
2257
2364
|
};
|
|
2258
2365
|
}
|
|
2259
2366
|
return {
|
|
2260
2367
|
transport: "http",
|
|
2261
|
-
url:
|
|
2262
|
-
headers: cloneStringRecord(
|
|
2368
|
+
url: config2.url,
|
|
2369
|
+
headers: cloneStringRecord(config2.headers)
|
|
2263
2370
|
};
|
|
2264
2371
|
}
|
|
2265
2372
|
function cloneRenameMap(rename5) {
|
|
@@ -2500,57 +2607,57 @@ function resolveCommandScope(ownScope, inheritedScope) {
|
|
|
2500
2607
|
function resolveGroupScope(ownScope, inheritedScope) {
|
|
2501
2608
|
return cloneScope(ownScope ?? inheritedScope);
|
|
2502
2609
|
}
|
|
2503
|
-
function createBaseCommand(
|
|
2610
|
+
function createBaseCommand(config2) {
|
|
2504
2611
|
const command = {
|
|
2505
2612
|
kind: "command",
|
|
2506
|
-
name:
|
|
2507
|
-
description:
|
|
2508
|
-
aliases: [...
|
|
2509
|
-
positional: [...
|
|
2510
|
-
params:
|
|
2511
|
-
secrets: cloneSecrets(
|
|
2512
|
-
scope: resolveCommandScope(
|
|
2513
|
-
confirm:
|
|
2514
|
-
humanInLoop:
|
|
2515
|
-
requires: cloneRequires(
|
|
2516
|
-
handler:
|
|
2517
|
-
render:
|
|
2613
|
+
name: config2.name,
|
|
2614
|
+
description: config2.description,
|
|
2615
|
+
aliases: [...config2.aliases ?? []],
|
|
2616
|
+
positional: [...config2.positional ?? []],
|
|
2617
|
+
params: config2.params,
|
|
2618
|
+
secrets: cloneSecrets(config2.secrets),
|
|
2619
|
+
scope: resolveCommandScope(config2.scope, void 0),
|
|
2620
|
+
confirm: config2.confirm ?? false,
|
|
2621
|
+
humanInLoop: config2.humanInLoop,
|
|
2622
|
+
requires: cloneRequires(config2.requires),
|
|
2623
|
+
handler: config2.handler,
|
|
2624
|
+
render: config2.render
|
|
2518
2625
|
};
|
|
2519
2626
|
Object.defineProperty(command, commandConfigSymbol, {
|
|
2520
2627
|
value: {
|
|
2521
|
-
scope: cloneScope(
|
|
2522
|
-
humanInLoop:
|
|
2523
|
-
secrets: cloneSecrets(
|
|
2524
|
-
requires: cloneRequires(
|
|
2628
|
+
scope: cloneScope(config2.scope),
|
|
2629
|
+
humanInLoop: config2.humanInLoop,
|
|
2630
|
+
secrets: cloneSecrets(config2.secrets),
|
|
2631
|
+
requires: cloneRequires(config2.requires),
|
|
2525
2632
|
sourcePath: inferCommandSourcePath()
|
|
2526
2633
|
}
|
|
2527
2634
|
});
|
|
2528
2635
|
return command;
|
|
2529
2636
|
}
|
|
2530
|
-
function createBaseGroup(
|
|
2637
|
+
function createBaseGroup(config2) {
|
|
2531
2638
|
const group = {
|
|
2532
2639
|
kind: "group",
|
|
2533
|
-
name:
|
|
2534
|
-
description:
|
|
2535
|
-
aliases: [...
|
|
2536
|
-
scope: resolveGroupScope(
|
|
2537
|
-
humanInLoop:
|
|
2538
|
-
secrets: cloneSecrets(
|
|
2539
|
-
requires: cloneRequires(
|
|
2640
|
+
name: config2.name,
|
|
2641
|
+
description: config2.description,
|
|
2642
|
+
aliases: [...config2.aliases ?? []],
|
|
2643
|
+
scope: resolveGroupScope(config2.scope, void 0),
|
|
2644
|
+
humanInLoop: config2.humanInLoop,
|
|
2645
|
+
secrets: cloneSecrets(config2.secrets),
|
|
2646
|
+
requires: cloneRequires(config2.requires),
|
|
2540
2647
|
children: [],
|
|
2541
2648
|
default: void 0
|
|
2542
2649
|
};
|
|
2543
2650
|
Object.defineProperty(group, groupConfigSymbol, {
|
|
2544
2651
|
value: {
|
|
2545
|
-
mcp: cloneMcpServerConfig(
|
|
2546
|
-
scope: cloneScope(
|
|
2547
|
-
humanInLoop:
|
|
2548
|
-
secrets: cloneSecrets(
|
|
2549
|
-
tools: cloneStringArray(
|
|
2550
|
-
rename: cloneRenameMap(
|
|
2551
|
-
requires: cloneRequires(
|
|
2552
|
-
children: [...
|
|
2553
|
-
default:
|
|
2652
|
+
mcp: cloneMcpServerConfig(config2.mcp),
|
|
2653
|
+
scope: cloneScope(config2.scope),
|
|
2654
|
+
humanInLoop: config2.humanInLoop,
|
|
2655
|
+
secrets: cloneSecrets(config2.secrets),
|
|
2656
|
+
tools: cloneStringArray(config2.tools),
|
|
2657
|
+
rename: cloneRenameMap(config2.rename),
|
|
2658
|
+
requires: cloneRequires(config2.requires),
|
|
2659
|
+
children: [...config2.children],
|
|
2660
|
+
default: config2.default
|
|
2554
2661
|
}
|
|
2555
2662
|
});
|
|
2556
2663
|
return group;
|
|
@@ -2653,10 +2760,10 @@ function materializeNode(node, inherited) {
|
|
|
2653
2760
|
}
|
|
2654
2761
|
return materializeGroup(node, inherited);
|
|
2655
2762
|
}
|
|
2656
|
-
function defineCommand(
|
|
2657
|
-
validateHumanInLoopOnDefine(
|
|
2763
|
+
function defineCommand(config2) {
|
|
2764
|
+
validateHumanInLoopOnDefine(config2);
|
|
2658
2765
|
return materializeCommand(
|
|
2659
|
-
createBaseCommand(
|
|
2766
|
+
createBaseCommand(config2),
|
|
2660
2767
|
{
|
|
2661
2768
|
scope: void 0,
|
|
2662
2769
|
humanInLoop: void 0,
|
|
@@ -2665,10 +2772,10 @@ function defineCommand(config) {
|
|
|
2665
2772
|
}
|
|
2666
2773
|
);
|
|
2667
2774
|
}
|
|
2668
|
-
function defineGroup(
|
|
2669
|
-
validateRenameMap(
|
|
2670
|
-
validateHumanInLoopOnDefine(
|
|
2671
|
-
return materializeGroup(createBaseGroup(
|
|
2775
|
+
function defineGroup(config2) {
|
|
2776
|
+
validateRenameMap(config2.rename);
|
|
2777
|
+
validateHumanInLoopOnDefine(config2);
|
|
2778
|
+
return materializeGroup(createBaseGroup(config2), {
|
|
2672
2779
|
scope: void 0,
|
|
2673
2780
|
humanInLoop: void 0,
|
|
2674
2781
|
secrets: {},
|
|
@@ -2837,7 +2944,7 @@ import path3 from "node:path";
|
|
|
2837
2944
|
// ../process-runner/src/docker/docker-execution-env.ts
|
|
2838
2945
|
import { createHash as createHash2, randomBytes as randomBytes2 } from "node:crypto";
|
|
2839
2946
|
import { mkdtempSync as mkdtempSync2, rmSync as rmSync2 } from "node:fs";
|
|
2840
|
-
import { readdir, readFile, writeFile } from "node:fs/promises";
|
|
2947
|
+
import { readdir, readFile, realpath, writeFile } from "node:fs/promises";
|
|
2841
2948
|
import { tmpdir as tmpdir2 } from "node:os";
|
|
2842
2949
|
import path5 from "node:path";
|
|
2843
2950
|
|
|
@@ -4525,7 +4632,7 @@ async function readTaskAtLocation(fs4, rootPath, layout, list, id, validStates,
|
|
|
4525
4632
|
}
|
|
4526
4633
|
return readTaskFile(fs4, list, id, location.path, validStates, initialState, mode);
|
|
4527
4634
|
}
|
|
4528
|
-
function createdFrontmatter(
|
|
4635
|
+
function createdFrontmatter(defaults2, input, initialState, mode) {
|
|
4529
4636
|
const frontmatter = mode !== "passthrough" ? {
|
|
4530
4637
|
$schema: TASK_SCHEMA_ID,
|
|
4531
4638
|
kind: TASK_KIND,
|
|
@@ -4537,7 +4644,7 @@ function createdFrontmatter(defaults, input, initialState, mode) {
|
|
|
4537
4644
|
state: initialState
|
|
4538
4645
|
};
|
|
4539
4646
|
const reservedKeys = reservedFrontmatterKeys(mode);
|
|
4540
|
-
for (const [key2, value] of Object.entries(
|
|
4647
|
+
for (const [key2, value] of Object.entries(defaults2.metadata)) {
|
|
4541
4648
|
if (!reservedKeys.has(key2)) {
|
|
4542
4649
|
setOwnValue(frontmatter, key2, value);
|
|
4543
4650
|
}
|
|
@@ -5283,13 +5390,13 @@ function matchesFilter(task, filter) {
|
|
|
5283
5390
|
}
|
|
5284
5391
|
return true;
|
|
5285
5392
|
}
|
|
5286
|
-
function createTaskRecord(
|
|
5393
|
+
function createTaskRecord(defaults2, input, initialState) {
|
|
5287
5394
|
const taskRecord = Object.assign(/* @__PURE__ */ Object.create(null), {
|
|
5288
5395
|
name: input.name,
|
|
5289
5396
|
state: initialState,
|
|
5290
5397
|
description: input.description ?? ""
|
|
5291
5398
|
});
|
|
5292
|
-
for (const [key2, value] of Object.entries(
|
|
5399
|
+
for (const [key2, value] of Object.entries(defaults2.metadata)) {
|
|
5293
5400
|
if (!RESERVED_TASK_KEYS.has(key2)) {
|
|
5294
5401
|
taskRecord[key2] = value;
|
|
5295
5402
|
}
|
|
@@ -6663,7 +6770,7 @@ function isMissingStateError(error3) {
|
|
|
6663
6770
|
}
|
|
6664
6771
|
|
|
6665
6772
|
// ../toolcraft/src/error-report.ts
|
|
6666
|
-
import { mkdir as mkdir2, realpath, writeFile as writeFile4 } from "node:fs/promises";
|
|
6773
|
+
import { mkdir as mkdir2, realpath as realpath2, writeFile as writeFile4 } from "node:fs/promises";
|
|
6667
6774
|
import { randomUUID as randomUUID3 } from "node:crypto";
|
|
6668
6775
|
import os from "node:os";
|
|
6669
6776
|
import path13 from "node:path";
|
|
@@ -7182,19 +7289,24 @@ function createAuthStoreClientStore(options) {
|
|
|
7182
7289
|
}
|
|
7183
7290
|
};
|
|
7184
7291
|
}
|
|
7185
|
-
function createNamedSecretStore(key2, options,
|
|
7292
|
+
function createNamedSecretStore(key2, options, defaults2) {
|
|
7186
7293
|
const hash = crypto.createHash("sha256").update(key2).digest("hex");
|
|
7187
|
-
const
|
|
7294
|
+
const configuredFilePath = options.fileStore?.filePath;
|
|
7295
|
+
const parsedFilePath = configuredFilePath === void 0 ? null : path11.parse(configuredFilePath);
|
|
7188
7296
|
const fileStore = {
|
|
7189
7297
|
...options.fileStore,
|
|
7190
|
-
|
|
7191
|
-
|
|
7298
|
+
filePath: parsedFilePath === null ? void 0 : path11.join(
|
|
7299
|
+
parsedFilePath.dir,
|
|
7300
|
+
`${parsedFilePath.name}-${hash}${parsedFilePath.ext || ".enc"}`
|
|
7301
|
+
),
|
|
7302
|
+
salt: options.fileStore?.salt ?? defaults2.salt,
|
|
7303
|
+
defaultDirectory: options.fileStore?.defaultDirectory || defaults2.directory,
|
|
7192
7304
|
defaultFileName: parsedFilePath === null ? `${hash}.enc` : `${parsedFilePath.name}-${hash}${parsedFilePath.ext || ".enc"}`
|
|
7193
7305
|
};
|
|
7194
7306
|
const keychainStore = {
|
|
7195
7307
|
...options.keychainStore,
|
|
7196
|
-
service: options.keychainStore?.service ??
|
|
7197
|
-
account: `${options.keychainStore?.account ??
|
|
7308
|
+
service: options.keychainStore?.service ?? defaults2.service,
|
|
7309
|
+
account: `${options.keychainStore?.account ?? defaults2.accountPrefix}:${hash}`
|
|
7198
7310
|
};
|
|
7199
7311
|
return createSecretStore({ ...options, fileStore, keychainStore }).store;
|
|
7200
7312
|
}
|
|
@@ -8794,6 +8906,9 @@ var McpClient = class {
|
|
|
8794
8906
|
const abortPromise = new Promise((_, reject) => {
|
|
8795
8907
|
const rejectWithAbortReason = () => {
|
|
8796
8908
|
sendCancellationNotification();
|
|
8909
|
+
if (requestId !== void 0) {
|
|
8910
|
+
messageLayer.cancelRequest(requestId, signal.reason);
|
|
8911
|
+
}
|
|
8797
8912
|
reject(signal.reason);
|
|
8798
8913
|
};
|
|
8799
8914
|
abortListener = rejectWithAbortReason;
|
|
@@ -8968,11 +9083,13 @@ var StdioTransport = class _StdioTransport {
|
|
|
8968
9083
|
const child = this.child;
|
|
8969
9084
|
this.readable = child.stdout;
|
|
8970
9085
|
this.writable = child.stdin;
|
|
9086
|
+
const stderrDecoder = new TextDecoder();
|
|
8971
9087
|
child.stderr.on("data", (chunk) => {
|
|
8972
|
-
|
|
8973
|
-
|
|
8974
|
-
|
|
8975
|
-
|
|
9088
|
+
const decoded = chunk instanceof Uint8Array ? stderrDecoder.decode(chunk, { stream: true }) : `${stderrDecoder.decode()}${String(chunk)}`;
|
|
9089
|
+
this.appendStderrOutput(decoded);
|
|
9090
|
+
});
|
|
9091
|
+
child.stderr.once("end", () => {
|
|
9092
|
+
this.appendStderrOutput(stderrDecoder.decode());
|
|
8976
9093
|
});
|
|
8977
9094
|
this.closed = new Promise((resolve) => {
|
|
8978
9095
|
let settled = false;
|
|
@@ -9012,6 +9129,15 @@ var StdioTransport = class _StdioTransport {
|
|
|
9012
9129
|
getStderrOutput() {
|
|
9013
9130
|
return this.stderrOutput;
|
|
9014
9131
|
}
|
|
9132
|
+
appendStderrOutput(chunk) {
|
|
9133
|
+
if (chunk.length === 0) {
|
|
9134
|
+
return;
|
|
9135
|
+
}
|
|
9136
|
+
this.stderrOutput += chunk;
|
|
9137
|
+
if (this.stderrOutput.length > _StdioTransport.STDERR_MAX_LENGTH) {
|
|
9138
|
+
this.stderrOutput = this.stderrOutput.slice(-_StdioTransport.STDERR_MAX_LENGTH);
|
|
9139
|
+
}
|
|
9140
|
+
}
|
|
9015
9141
|
dispose(reason = new Error("Stdio transport disposed")) {
|
|
9016
9142
|
void reason;
|
|
9017
9143
|
if (this.disposed) {
|
|
@@ -9419,15 +9545,6 @@ function serializeJsonRpcMessage(message2) {
|
|
|
9419
9545
|
return `${JSON.stringify(message2)}
|
|
9420
9546
|
`;
|
|
9421
9547
|
}
|
|
9422
|
-
function chunkToString(chunk) {
|
|
9423
|
-
if (typeof chunk === "string") {
|
|
9424
|
-
return chunk;
|
|
9425
|
-
}
|
|
9426
|
-
if (chunk instanceof Uint8Array) {
|
|
9427
|
-
return Buffer.from(chunk).toString("utf8");
|
|
9428
|
-
}
|
|
9429
|
-
return String(chunk);
|
|
9430
|
-
}
|
|
9431
9548
|
function normalizeLine(line) {
|
|
9432
9549
|
return line.endsWith("\r") ? line.slice(0, -1) : line;
|
|
9433
9550
|
}
|
|
@@ -9617,6 +9734,16 @@ var JsonRpcMessageLayer = class {
|
|
|
9617
9734
|
}
|
|
9618
9735
|
});
|
|
9619
9736
|
}
|
|
9737
|
+
cancelRequest(requestId, reason) {
|
|
9738
|
+
const pending = this.pendingRequests.get(requestId);
|
|
9739
|
+
if (pending === void 0) {
|
|
9740
|
+
return false;
|
|
9741
|
+
}
|
|
9742
|
+
this.pendingRequests.delete(requestId);
|
|
9743
|
+
clearTimeout(pending.timeout);
|
|
9744
|
+
pending.reject(reason);
|
|
9745
|
+
return true;
|
|
9746
|
+
}
|
|
9620
9747
|
dispose(reason = new Error("JSON-RPC message layer disposed")) {
|
|
9621
9748
|
if (this.disposedError !== void 0) {
|
|
9622
9749
|
return;
|
|
@@ -10685,10 +10812,10 @@ function validateRenameMap2(name, tools, rename5) {
|
|
|
10685
10812
|
}
|
|
10686
10813
|
}
|
|
10687
10814
|
}
|
|
10688
|
-
function createConnection(name,
|
|
10815
|
+
function createConnection(name, config2) {
|
|
10689
10816
|
const connection = {
|
|
10690
10817
|
name,
|
|
10691
|
-
config,
|
|
10818
|
+
config: config2,
|
|
10692
10819
|
async dispose() {
|
|
10693
10820
|
shutdownDisposers.delete(connection.dispose);
|
|
10694
10821
|
connection.connecting = void 0;
|
|
@@ -10755,13 +10882,13 @@ async function writeCache(cachePath, cache) {
|
|
|
10755
10882
|
await assertCachePathHasNoSymlinks(cachePath);
|
|
10756
10883
|
await rename2(tempPath, cachePath);
|
|
10757
10884
|
}
|
|
10758
|
-
async function fetchCache(name,
|
|
10885
|
+
async function fetchCache(name, config2) {
|
|
10759
10886
|
const logger2 = createLogger((message2) => {
|
|
10760
10887
|
process.stderr.write(`${message2}
|
|
10761
10888
|
`);
|
|
10762
10889
|
});
|
|
10763
10890
|
logger2.info(`MCP ${name}: connecting`);
|
|
10764
|
-
const client = await dialUpstream(name,
|
|
10891
|
+
const client = await dialUpstream(name, config2);
|
|
10765
10892
|
try {
|
|
10766
10893
|
logger2.info(`MCP ${name}: listing tools`);
|
|
10767
10894
|
const tools = [];
|
|
@@ -10780,7 +10907,7 @@ async function fetchCache(name, config) {
|
|
|
10780
10907
|
$schema: MCP_PROXY_SCHEMA_URL,
|
|
10781
10908
|
version: 1,
|
|
10782
10909
|
upstream,
|
|
10783
|
-
configFingerprint: fingerprintMcpServerConfig(
|
|
10910
|
+
configFingerprint: fingerprintMcpServerConfig(config2),
|
|
10784
10911
|
fetchedAt: (/* @__PURE__ */ new Date()).toISOString(),
|
|
10785
10912
|
tools
|
|
10786
10913
|
};
|
|
@@ -10850,8 +10977,8 @@ function isRefreshRequested(name, refresh) {
|
|
|
10850
10977
|
}
|
|
10851
10978
|
async function resolveSingleProxy(group, options) {
|
|
10852
10979
|
const internal = getInternalGroupConfig2(group);
|
|
10853
|
-
const
|
|
10854
|
-
if (
|
|
10980
|
+
const config2 = internal.mcp;
|
|
10981
|
+
if (config2 === void 0) {
|
|
10855
10982
|
return;
|
|
10856
10983
|
}
|
|
10857
10984
|
const name = group.name;
|
|
@@ -10861,21 +10988,21 @@ async function resolveSingleProxy(group, options) {
|
|
|
10861
10988
|
let cache;
|
|
10862
10989
|
let shouldWriteCache = false;
|
|
10863
10990
|
if (isRefreshRequested(name, refresh)) {
|
|
10864
|
-
cache = await fetchCache(name,
|
|
10991
|
+
cache = await fetchCache(name, config2);
|
|
10865
10992
|
shouldWriteCache = true;
|
|
10866
10993
|
} else {
|
|
10867
10994
|
const storedCache = await readCache(cachePath);
|
|
10868
|
-
if (storedCache && cacheMatchesConfig(storedCache,
|
|
10995
|
+
if (storedCache && cacheMatchesConfig(storedCache, config2)) {
|
|
10869
10996
|
cache = storedCache;
|
|
10870
10997
|
} else {
|
|
10871
|
-
cache = await fetchCache(name,
|
|
10998
|
+
cache = await fetchCache(name, config2);
|
|
10872
10999
|
shouldWriteCache = true;
|
|
10873
11000
|
}
|
|
10874
11001
|
}
|
|
10875
11002
|
const tools = filterAllowlistedTools(cache.tools, internal.tools);
|
|
10876
11003
|
validateRenameMap2(name, tools, internal.rename);
|
|
10877
11004
|
const previousConnection = getProxyConnection(group);
|
|
10878
|
-
const nextConnection = createConnection(name,
|
|
11005
|
+
const nextConnection = createConnection(name, config2);
|
|
10879
11006
|
try {
|
|
10880
11007
|
replaceProxyChildrenSafely(group, tools, internal.rename, nextConnection);
|
|
10881
11008
|
if (shouldWriteCache) {
|
|
@@ -10900,11 +11027,11 @@ async function resolveSingleProxy(group, options) {
|
|
|
10900
11027
|
);
|
|
10901
11028
|
}
|
|
10902
11029
|
}
|
|
10903
|
-
function cacheMatchesConfig(cache,
|
|
10904
|
-
return cache.configFingerprint === fingerprintMcpServerConfig(
|
|
11030
|
+
function cacheMatchesConfig(cache, config2) {
|
|
11031
|
+
return cache.configFingerprint === fingerprintMcpServerConfig(config2);
|
|
10905
11032
|
}
|
|
10906
|
-
function fingerprintMcpServerConfig(
|
|
10907
|
-
return createHash3("sha256").update(JSON.stringify(
|
|
11033
|
+
function fingerprintMcpServerConfig(config2) {
|
|
11034
|
+
return createHash3("sha256").update(JSON.stringify(config2)).digest("hex");
|
|
10908
11035
|
}
|
|
10909
11036
|
function collectProxyGroups(root) {
|
|
10910
11037
|
const groups = [];
|
|
@@ -10982,20 +11109,20 @@ function parseRefreshEnv(value) {
|
|
|
10982
11109
|
const names = trimmed.split(",").map((entry) => entry.trim()).filter((entry) => entry.length > 0);
|
|
10983
11110
|
return names.length === 0 ? void 0 : new Set(names);
|
|
10984
11111
|
}
|
|
10985
|
-
async function dialUpstream(name,
|
|
11112
|
+
async function dialUpstream(name, config2) {
|
|
10986
11113
|
const client = new McpClient({
|
|
10987
11114
|
clientInfo: {
|
|
10988
11115
|
name: `${DEFAULT_CLIENT_INFO.name}-${name}`,
|
|
10989
11116
|
version: DEFAULT_CLIENT_INFO.version
|
|
10990
11117
|
}
|
|
10991
11118
|
});
|
|
10992
|
-
const transport =
|
|
10993
|
-
command:
|
|
10994
|
-
...
|
|
10995
|
-
...
|
|
11119
|
+
const transport = config2.transport === "stdio" ? new StdioTransport({
|
|
11120
|
+
command: config2.command,
|
|
11121
|
+
...config2.args === void 0 ? {} : { args: config2.args },
|
|
11122
|
+
...config2.env === void 0 ? {} : { env: config2.env }
|
|
10996
11123
|
}) : new HttpTransport({
|
|
10997
|
-
url:
|
|
10998
|
-
...
|
|
11124
|
+
url: config2.url,
|
|
11125
|
+
...config2.headers === void 0 ? {} : { headers: config2.headers }
|
|
10999
11126
|
});
|
|
11000
11127
|
await client.connect(transport);
|
|
11001
11128
|
return client;
|
|
@@ -11005,10 +11132,82 @@ async function resolveMcpProxies(root, options = {}) {
|
|
|
11005
11132
|
await Promise.all(groups.map((group) => resolveSingleProxy(group, options)));
|
|
11006
11133
|
}
|
|
11007
11134
|
|
|
11135
|
+
// ../toolcraft/src/redaction.ts
|
|
11136
|
+
var REDACTED_VALUE = "<redacted>";
|
|
11137
|
+
var SENSITIVE_NAME_PARTS = ["password", "token", "apikey", "secret"];
|
|
11138
|
+
var AUTHORIZATION_HEADER_NAMES = /* @__PURE__ */ new Set(["authorization", "proxyauthorization"]);
|
|
11139
|
+
var SECRET_HEADER_NAMES = /* @__PURE__ */ new Set(["cookie", "setcookie"]);
|
|
11140
|
+
function isPlainObject2(value) {
|
|
11141
|
+
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
11142
|
+
}
|
|
11143
|
+
function normalizeName(name) {
|
|
11144
|
+
return name.toLowerCase().replace(/[^a-z0-9]/g, "");
|
|
11145
|
+
}
|
|
11146
|
+
function isSensitiveName(name) {
|
|
11147
|
+
const normalized = normalizeName(name);
|
|
11148
|
+
return SENSITIVE_NAME_PARTS.some((candidate) => normalized.includes(candidate));
|
|
11149
|
+
}
|
|
11150
|
+
function redactSecretLikeFieldsValue(value, name, seen) {
|
|
11151
|
+
if (name.length > 0 && isSensitiveName(name)) {
|
|
11152
|
+
return REDACTED_VALUE;
|
|
11153
|
+
}
|
|
11154
|
+
if (Array.isArray(value)) {
|
|
11155
|
+
if (seen.has(value)) {
|
|
11156
|
+
return "[Circular]";
|
|
11157
|
+
}
|
|
11158
|
+
seen.add(value);
|
|
11159
|
+
return value.map((entry) => redactSecretLikeFieldsValue(entry, name, seen));
|
|
11160
|
+
}
|
|
11161
|
+
if (isPlainObject2(value)) {
|
|
11162
|
+
if (seen.has(value)) {
|
|
11163
|
+
return "[Circular]";
|
|
11164
|
+
}
|
|
11165
|
+
seen.add(value);
|
|
11166
|
+
return Object.fromEntries(
|
|
11167
|
+
Object.entries(value).map(([key2, entry]) => [
|
|
11168
|
+
key2,
|
|
11169
|
+
redactSecretLikeFieldsValue(entry, key2, seen)
|
|
11170
|
+
])
|
|
11171
|
+
);
|
|
11172
|
+
}
|
|
11173
|
+
return value;
|
|
11174
|
+
}
|
|
11175
|
+
function redactSecretLikeFields(value, name = "") {
|
|
11176
|
+
return redactSecretLikeFieldsValue(value, name, /* @__PURE__ */ new WeakSet());
|
|
11177
|
+
}
|
|
11178
|
+
function parseJsonObjectOrArray(value) {
|
|
11179
|
+
const trimmed = value.trim();
|
|
11180
|
+
if (!trimmed.startsWith("{") && !trimmed.startsWith("[")) {
|
|
11181
|
+
return void 0;
|
|
11182
|
+
}
|
|
11183
|
+
try {
|
|
11184
|
+
const parsed = JSON.parse(trimmed);
|
|
11185
|
+
return isPlainObject2(parsed) || Array.isArray(parsed) ? parsed : void 0;
|
|
11186
|
+
} catch {
|
|
11187
|
+
return void 0;
|
|
11188
|
+
}
|
|
11189
|
+
}
|
|
11190
|
+
function redactHttpBody(body) {
|
|
11191
|
+
if (typeof body === "string") {
|
|
11192
|
+
const parsed = parseJsonObjectOrArray(body);
|
|
11193
|
+
return parsed === void 0 ? body : redactSecretLikeFields(parsed);
|
|
11194
|
+
}
|
|
11195
|
+
return redactSecretLikeFields(body);
|
|
11196
|
+
}
|
|
11197
|
+
function redactHttpHeaderValue(name, value) {
|
|
11198
|
+
const normalized = normalizeName(name);
|
|
11199
|
+
if (AUTHORIZATION_HEADER_NAMES.has(normalized)) {
|
|
11200
|
+
return "Bearer ****";
|
|
11201
|
+
}
|
|
11202
|
+
if (SECRET_HEADER_NAMES.has(normalized) || isSensitiveName(name)) {
|
|
11203
|
+
return REDACTED_VALUE;
|
|
11204
|
+
}
|
|
11205
|
+
return value;
|
|
11206
|
+
}
|
|
11207
|
+
|
|
11008
11208
|
// ../toolcraft/src/error-report.ts
|
|
11009
11209
|
var ERROR_REPORTS_ENV = "TOOLCRAFT_ERROR_REPORTS";
|
|
11010
|
-
|
|
11011
|
-
function isPlainObject2(value) {
|
|
11210
|
+
function isPlainObject3(value) {
|
|
11012
11211
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
11013
11212
|
}
|
|
11014
11213
|
function unwrapOptional(schema) {
|
|
@@ -11018,7 +11217,7 @@ function unwrapOptional(schema) {
|
|
|
11018
11217
|
return schema;
|
|
11019
11218
|
}
|
|
11020
11219
|
function hasHttpContext(error3) {
|
|
11021
|
-
return error3 instanceof Error && error3.name === "HttpError" &&
|
|
11220
|
+
return error3 instanceof Error && error3.name === "HttpError" && isPlainObject3(error3.request) && isPlainObject3(error3.response);
|
|
11022
11221
|
}
|
|
11023
11222
|
function isSkippedError(error3) {
|
|
11024
11223
|
if (error3 instanceof ApprovalDeclinedError) {
|
|
@@ -11055,8 +11254,8 @@ async function assertReportDirWithinProject(projectRoot, reportDir) {
|
|
|
11055
11254
|
throw new Error("Error report directory resolves outside project root.");
|
|
11056
11255
|
}
|
|
11057
11256
|
const [canonicalProjectRoot, canonicalReportDir] = await Promise.all([
|
|
11058
|
-
|
|
11059
|
-
|
|
11257
|
+
realpath2(projectRoot),
|
|
11258
|
+
realpath2(reportDir)
|
|
11060
11259
|
]);
|
|
11061
11260
|
if (!isWithinDirectory(canonicalProjectRoot, canonicalReportDir)) {
|
|
11062
11261
|
throw new Error("Error report directory resolves outside project root.");
|
|
@@ -11111,9 +11310,24 @@ function redactValue(value) {
|
|
|
11111
11310
|
}
|
|
11112
11311
|
return `<set, ${value.length} chars>`;
|
|
11113
11312
|
}
|
|
11114
|
-
function
|
|
11115
|
-
|
|
11116
|
-
|
|
11313
|
+
function collectStringLeaves(value, output) {
|
|
11314
|
+
if (typeof value === "string") {
|
|
11315
|
+
if (value.length > 0) {
|
|
11316
|
+
output.add(value);
|
|
11317
|
+
}
|
|
11318
|
+
return;
|
|
11319
|
+
}
|
|
11320
|
+
if (Array.isArray(value)) {
|
|
11321
|
+
for (const entry of value) {
|
|
11322
|
+
collectStringLeaves(entry, output);
|
|
11323
|
+
}
|
|
11324
|
+
return;
|
|
11325
|
+
}
|
|
11326
|
+
if (isPlainObject3(value)) {
|
|
11327
|
+
for (const entry of Object.values(value)) {
|
|
11328
|
+
collectStringLeaves(entry, output);
|
|
11329
|
+
}
|
|
11330
|
+
}
|
|
11117
11331
|
}
|
|
11118
11332
|
function schemaSecretValue(schema) {
|
|
11119
11333
|
const unwrapped = unwrapOptional(schema);
|
|
@@ -11134,7 +11348,7 @@ function redactParamsValue(value, schema, name) {
|
|
|
11134
11348
|
return "<redacted>";
|
|
11135
11349
|
}
|
|
11136
11350
|
const unwrapped = unwrapOptional(schema);
|
|
11137
|
-
if (unwrapped.kind === "object" &&
|
|
11351
|
+
if (unwrapped.kind === "object" && isPlainObject3(value)) {
|
|
11138
11352
|
return Object.fromEntries(
|
|
11139
11353
|
Object.entries(value).map(([key2, childValue]) => {
|
|
11140
11354
|
const childSchema = unwrapped.shape[key2];
|
|
@@ -11156,6 +11370,52 @@ function redactParams(params17, command) {
|
|
|
11156
11370
|
}
|
|
11157
11371
|
return redactParamsValue(params17, command.params, "");
|
|
11158
11372
|
}
|
|
11373
|
+
function collectSensitiveParamValues(value, schema, name, output) {
|
|
11374
|
+
if (shouldRedactParam(name, schema)) {
|
|
11375
|
+
collectStringLeaves(value, output);
|
|
11376
|
+
return;
|
|
11377
|
+
}
|
|
11378
|
+
const unwrapped = unwrapOptional(schema);
|
|
11379
|
+
if (unwrapped.kind === "object" && isPlainObject3(value)) {
|
|
11380
|
+
for (const [key2, childValue] of Object.entries(value)) {
|
|
11381
|
+
const childSchema = unwrapped.shape[key2];
|
|
11382
|
+
if (childSchema !== void 0) {
|
|
11383
|
+
collectSensitiveParamValues(childValue, childSchema, key2, output);
|
|
11384
|
+
}
|
|
11385
|
+
}
|
|
11386
|
+
return;
|
|
11387
|
+
}
|
|
11388
|
+
if (unwrapped.kind === "array" && Array.isArray(value)) {
|
|
11389
|
+
for (const entry of value) {
|
|
11390
|
+
collectSensitiveParamValues(entry, unwrapped.item, name, output);
|
|
11391
|
+
}
|
|
11392
|
+
}
|
|
11393
|
+
}
|
|
11394
|
+
function createReportStringRedactor(context, env) {
|
|
11395
|
+
const values = /* @__PURE__ */ new Set();
|
|
11396
|
+
for (const value of Object.values(context.secrets ?? {})) {
|
|
11397
|
+
if (value !== void 0 && value.length > 0) {
|
|
11398
|
+
values.add(value);
|
|
11399
|
+
}
|
|
11400
|
+
}
|
|
11401
|
+
for (const [name, secret] of Object.entries(context.command?.secrets ?? {})) {
|
|
11402
|
+
const value = context.secrets?.[name] ?? env[secret.env];
|
|
11403
|
+
if (value !== void 0 && value.length > 0) {
|
|
11404
|
+
values.add(value);
|
|
11405
|
+
}
|
|
11406
|
+
}
|
|
11407
|
+
if (context.command !== void 0) {
|
|
11408
|
+
collectSensitiveParamValues(context.params, context.command.params, "", values);
|
|
11409
|
+
}
|
|
11410
|
+
const orderedValues = [...values].sort((left, right) => right.length - left.length);
|
|
11411
|
+
return (value) => {
|
|
11412
|
+
let redacted = value;
|
|
11413
|
+
for (const secretValue of orderedValues) {
|
|
11414
|
+
redacted = redacted.split(secretValue).join("<redacted>");
|
|
11415
|
+
}
|
|
11416
|
+
return redacted;
|
|
11417
|
+
};
|
|
11418
|
+
}
|
|
11159
11419
|
function commandSecretEnvNames(secrets) {
|
|
11160
11420
|
if (secrets === void 0) {
|
|
11161
11421
|
return [];
|
|
@@ -11209,28 +11469,42 @@ function redactArgv(argv, options) {
|
|
|
11209
11469
|
function stableJson(value) {
|
|
11210
11470
|
return JSON.stringify(value, null, 2) ?? "undefined";
|
|
11211
11471
|
}
|
|
11212
|
-
function redactStructuredErrorField(name, value) {
|
|
11213
|
-
if (typeof value === "string"
|
|
11214
|
-
|
|
11472
|
+
function redactStructuredErrorField(name, value, redactString) {
|
|
11473
|
+
if (typeof value === "string") {
|
|
11474
|
+
const redactedHeaderValue = redactHttpHeaderValue(name, value);
|
|
11475
|
+
if (redactedHeaderValue !== value) {
|
|
11476
|
+
return redactedHeaderValue;
|
|
11477
|
+
}
|
|
11478
|
+
if (isSensitiveName(name)) {
|
|
11479
|
+
return "<redacted>";
|
|
11480
|
+
}
|
|
11481
|
+
return redactString(value);
|
|
11215
11482
|
}
|
|
11216
11483
|
if (Array.isArray(value)) {
|
|
11217
|
-
return value.map((entry) => redactStructuredErrorField(name, entry));
|
|
11484
|
+
return value.map((entry) => redactStructuredErrorField(name, entry, redactString));
|
|
11218
11485
|
}
|
|
11219
|
-
if (
|
|
11486
|
+
if (isPlainObject3(value)) {
|
|
11220
11487
|
return Object.fromEntries(
|
|
11221
|
-
Object.entries(value).map(([key2, entry]) => [
|
|
11488
|
+
Object.entries(value).map(([key2, entry]) => [
|
|
11489
|
+
key2,
|
|
11490
|
+
redactStructuredErrorField(key2, entry, redactString)
|
|
11491
|
+
])
|
|
11222
11492
|
);
|
|
11223
11493
|
}
|
|
11224
11494
|
return value;
|
|
11225
11495
|
}
|
|
11226
|
-
function ownStructuredFields(error3) {
|
|
11496
|
+
function ownStructuredFields(error3, redactString) {
|
|
11227
11497
|
const fields = {};
|
|
11228
11498
|
for (const key2 of Object.keys(error3)) {
|
|
11229
11499
|
if (key2 === "name" || key2 === "message" || key2 === "stack" || key2 === "cause") {
|
|
11230
11500
|
continue;
|
|
11231
11501
|
}
|
|
11232
11502
|
Object.defineProperty(fields, key2, {
|
|
11233
|
-
value: redactStructuredErrorField(
|
|
11503
|
+
value: redactStructuredErrorField(
|
|
11504
|
+
key2,
|
|
11505
|
+
error3[key2],
|
|
11506
|
+
redactString
|
|
11507
|
+
),
|
|
11234
11508
|
enumerable: true,
|
|
11235
11509
|
configurable: true,
|
|
11236
11510
|
writable: true
|
|
@@ -11238,43 +11512,44 @@ function ownStructuredFields(error3) {
|
|
|
11238
11512
|
}
|
|
11239
11513
|
return fields;
|
|
11240
11514
|
}
|
|
11241
|
-
function formatStackChain(error3) {
|
|
11515
|
+
function formatStackChain(error3, redactString) {
|
|
11242
11516
|
const lines = [];
|
|
11243
11517
|
let current = error3;
|
|
11244
11518
|
let index = 0;
|
|
11245
11519
|
while (current !== void 0) {
|
|
11246
11520
|
if (current instanceof Error) {
|
|
11247
|
-
|
|
11248
|
-
|
|
11249
|
-
);
|
|
11521
|
+
const stack = current.stack ?? String(current);
|
|
11522
|
+
lines.push(redactString(index === 0 ? stack : `Caused by: ${stack}`));
|
|
11250
11523
|
current = current.cause;
|
|
11251
11524
|
} else {
|
|
11252
|
-
|
|
11525
|
+
const message2 = String(current);
|
|
11526
|
+
lines.push(redactString(index === 0 ? message2 : `Caused by: ${message2}`));
|
|
11253
11527
|
current = void 0;
|
|
11254
11528
|
}
|
|
11255
11529
|
index += 1;
|
|
11256
11530
|
}
|
|
11257
11531
|
return lines.join("\n");
|
|
11258
11532
|
}
|
|
11259
|
-
function formatHeaderValue(name, value) {
|
|
11260
|
-
return name
|
|
11533
|
+
function formatHeaderValue(name, value, redactString) {
|
|
11534
|
+
return redactString(redactHttpHeaderValue(name, value));
|
|
11261
11535
|
}
|
|
11262
|
-
function formatHeaders(headers) {
|
|
11263
|
-
return Object.entries(headers).map(([name, value]) => `${name}: ${formatHeaderValue(name, value)}`).join("\n");
|
|
11536
|
+
function formatHeaders(headers, redactString) {
|
|
11537
|
+
return Object.entries(headers).map(([name, value]) => `${name}: ${formatHeaderValue(name, value, redactString)}`).join("\n");
|
|
11264
11538
|
}
|
|
11265
|
-
function formatBody(body) {
|
|
11266
|
-
|
|
11267
|
-
|
|
11539
|
+
function formatBody(body, redactString) {
|
|
11540
|
+
const redactedBody = redactHttpBody(body);
|
|
11541
|
+
if (typeof redactedBody === "string") {
|
|
11542
|
+
return redactString(redactedBody);
|
|
11268
11543
|
}
|
|
11269
|
-
return stableJson(
|
|
11544
|
+
return redactString(stableJson(redactedBody));
|
|
11270
11545
|
}
|
|
11271
|
-
function formatHttpTranscript(error3) {
|
|
11546
|
+
function formatHttpTranscript(error3, redactString) {
|
|
11272
11547
|
const requestLines = [
|
|
11273
11548
|
`${error3.request.method} ${error3.request.url}`,
|
|
11274
|
-
formatHeaders(error3.request.headers)
|
|
11549
|
+
formatHeaders(error3.request.headers, redactString)
|
|
11275
11550
|
].filter((line) => line.length > 0);
|
|
11276
11551
|
if (error3.request.body !== void 0) {
|
|
11277
|
-
requestLines.push("", formatBody(error3.request.body));
|
|
11552
|
+
requestLines.push("", formatBody(error3.request.body, redactString));
|
|
11278
11553
|
}
|
|
11279
11554
|
return [
|
|
11280
11555
|
"Request:",
|
|
@@ -11282,9 +11557,9 @@ function formatHttpTranscript(error3) {
|
|
|
11282
11557
|
"",
|
|
11283
11558
|
"Response:",
|
|
11284
11559
|
`${error3.response.status} ${error3.response.statusText}`,
|
|
11285
|
-
formatHeaders(error3.response.headers),
|
|
11560
|
+
formatHeaders(error3.response.headers, redactString),
|
|
11286
11561
|
"",
|
|
11287
|
-
formatBody(error3.response.body)
|
|
11562
|
+
formatBody(error3.response.body, redactString)
|
|
11288
11563
|
].join("\n");
|
|
11289
11564
|
}
|
|
11290
11565
|
function resolveToolcraftVersion(version) {
|
|
@@ -11293,9 +11568,10 @@ function resolveToolcraftVersion(version) {
|
|
|
11293
11568
|
function buildReport(context) {
|
|
11294
11569
|
const env = context.env ?? process.env;
|
|
11295
11570
|
const error3 = context.error;
|
|
11571
|
+
const redactString = createReportStringRedactor(context, env);
|
|
11296
11572
|
const errorName = error3 instanceof Error ? error3.name : typeof error3;
|
|
11297
|
-
const errorMessage = error3 instanceof Error ? error3.message : String(error3);
|
|
11298
|
-
const structuredFields = error3 instanceof Error ? ownStructuredFields(error3) : {};
|
|
11573
|
+
const errorMessage = redactString(error3 instanceof Error ? error3.message : String(error3));
|
|
11574
|
+
const structuredFields = error3 instanceof Error ? ownStructuredFields(error3, redactString) : {};
|
|
11299
11575
|
const secretLines = Object.entries(context.command?.secrets ?? {}).map(([name, secret]) => {
|
|
11300
11576
|
const value = context.secrets?.[name] ?? env[secret.env];
|
|
11301
11577
|
return `${secret.env}=${redactValue(value)}`;
|
|
@@ -11309,7 +11585,9 @@ function buildReport(context) {
|
|
|
11309
11585
|
`platform: ${process.platform} ${process.arch}`,
|
|
11310
11586
|
"",
|
|
11311
11587
|
"Argv",
|
|
11312
|
-
|
|
11588
|
+
redactString(
|
|
11589
|
+
stableJson(redactArgv(context.argv, { command: context.command, secrets: context.secrets }))
|
|
11590
|
+
),
|
|
11313
11591
|
"",
|
|
11314
11592
|
"Resolved Secrets",
|
|
11315
11593
|
...secretLines.length === 0 ? ["<none>"] : secretLines,
|
|
@@ -11318,19 +11596,19 @@ function buildReport(context) {
|
|
|
11318
11596
|
context.commandPath === void 0 || context.commandPath.length === 0 ? "root" : context.commandPath,
|
|
11319
11597
|
"",
|
|
11320
11598
|
"Parsed Params",
|
|
11321
|
-
stableJson(redactParams(context.params, context.command)),
|
|
11599
|
+
redactString(stableJson(redactParams(context.params, context.command))),
|
|
11322
11600
|
"",
|
|
11323
11601
|
"Error",
|
|
11324
11602
|
`name: ${errorName}`,
|
|
11325
11603
|
`message: ${errorMessage}`,
|
|
11326
11604
|
"structured fields:",
|
|
11327
|
-
stableJson(structuredFields),
|
|
11605
|
+
redactString(stableJson(structuredFields)),
|
|
11328
11606
|
"",
|
|
11329
11607
|
"Stack",
|
|
11330
|
-
formatStackChain(error3)
|
|
11608
|
+
formatStackChain(error3, redactString)
|
|
11331
11609
|
];
|
|
11332
11610
|
if (hasHttpContext(error3)) {
|
|
11333
|
-
lines.push("", "HTTP Transcript", formatHttpTranscript(error3));
|
|
11611
|
+
lines.push("", "HTTP Transcript", formatHttpTranscript(error3, redactString));
|
|
11334
11612
|
}
|
|
11335
11613
|
return `${lines.join("\n")}
|
|
11336
11614
|
`;
|
|
@@ -11790,6 +12068,7 @@ ${rendered.join("\n")}`);
|
|
|
11790
12068
|
}
|
|
11791
12069
|
|
|
11792
12070
|
// ../toolcraft/src/cli.ts
|
|
12071
|
+
configureTheme({ brand: "blue", label: "Toolcraft" });
|
|
11793
12072
|
var RESERVED_SERVICE_NAMES = /* @__PURE__ */ new Set([
|
|
11794
12073
|
"params",
|
|
11795
12074
|
"secrets",
|
|
@@ -13223,7 +13502,7 @@ function createEnv2(values = process.env) {
|
|
|
13223
13502
|
}
|
|
13224
13503
|
};
|
|
13225
13504
|
}
|
|
13226
|
-
function
|
|
13505
|
+
function isPlainObject4(value) {
|
|
13227
13506
|
return typeof value === "object" && value !== null && !Array.isArray(value);
|
|
13228
13507
|
}
|
|
13229
13508
|
function hasFieldValue(value) {
|
|
@@ -13332,7 +13611,7 @@ async function loadPresetValues(fields, presetPath) {
|
|
|
13332
13611
|
{ cause: error3 }
|
|
13333
13612
|
);
|
|
13334
13613
|
}
|
|
13335
|
-
if (!
|
|
13614
|
+
if (!isPlainObject4(parsedPreset)) {
|
|
13336
13615
|
throw new UserError(`Preset file "${presetPath}" must contain a JSON object.`);
|
|
13337
13616
|
}
|
|
13338
13617
|
const fieldByPath = new Map(fields.map((field) => [field.displayPath, field]));
|
|
@@ -13351,7 +13630,7 @@ async function loadPresetValues(fields, presetPath) {
|
|
|
13351
13630
|
`Preset file "${presetPath}" contains unknown parameter "${displayPath}".`
|
|
13352
13631
|
);
|
|
13353
13632
|
}
|
|
13354
|
-
if (!
|
|
13633
|
+
if (!isPlainObject4(value)) {
|
|
13355
13634
|
throw new UserError(
|
|
13356
13635
|
`Preset file "${presetPath}" has an invalid value for "${displayPath}". Expected an object, got ${describeReceived(value)}.`
|
|
13357
13636
|
);
|
|
@@ -13394,8 +13673,8 @@ function matchesFixtureValue(expected, actual) {
|
|
|
13394
13673
|
}
|
|
13395
13674
|
return expected.every((item, index) => matchesFixtureValue(item, actual[index]));
|
|
13396
13675
|
}
|
|
13397
|
-
if (
|
|
13398
|
-
if (!
|
|
13676
|
+
if (isPlainObject4(expected)) {
|
|
13677
|
+
if (!isPlainObject4(actual)) {
|
|
13399
13678
|
return false;
|
|
13400
13679
|
}
|
|
13401
13680
|
return Object.entries(expected).every(
|
|
@@ -13458,9 +13737,9 @@ function createFixtureFetch(entries) {
|
|
|
13458
13737
|
};
|
|
13459
13738
|
}
|
|
13460
13739
|
function createFixtureFs(definition) {
|
|
13461
|
-
const fsDefinition =
|
|
13462
|
-
const readFileEntries =
|
|
13463
|
-
const existsEntries =
|
|
13740
|
+
const fsDefinition = isPlainObject4(definition) ? definition : {};
|
|
13741
|
+
const readFileEntries = isPlainObject4(fsDefinition.readFile) ? fsDefinition.readFile : {};
|
|
13742
|
+
const existsEntries = isPlainObject4(fsDefinition.exists) ? fsDefinition.exists : {};
|
|
13464
13743
|
return {
|
|
13465
13744
|
readFile: async (filePath) => {
|
|
13466
13745
|
if (Object.prototype.hasOwnProperty.call(readFileEntries, filePath)) {
|
|
@@ -13483,10 +13762,10 @@ function createFixtureFs(definition) {
|
|
|
13483
13762
|
function resolveFixtureMethodResult(methodName, definition, args) {
|
|
13484
13763
|
if (Array.isArray(definition)) {
|
|
13485
13764
|
for (const entry of definition) {
|
|
13486
|
-
if (!
|
|
13765
|
+
if (!isPlainObject4(entry)) {
|
|
13487
13766
|
continue;
|
|
13488
13767
|
}
|
|
13489
|
-
const explicitMatcher =
|
|
13768
|
+
const explicitMatcher = isPlainObject4(entry.request) ? entry.request : void 0;
|
|
13490
13769
|
const matcher = explicitMatcher ?? Object.fromEntries(
|
|
13491
13770
|
Object.entries(entry).filter(
|
|
13492
13771
|
([key2]) => key2 !== "result" && key2 !== "response" && key2 !== "error"
|
|
@@ -13498,7 +13777,7 @@ function resolveFixtureMethodResult(methodName, definition, args) {
|
|
|
13498
13777
|
matched = matchesFixtureValue(matcher.args, args);
|
|
13499
13778
|
} else if (Object.keys(matcher).length === 0) {
|
|
13500
13779
|
matched = true;
|
|
13501
|
-
} else if (
|
|
13780
|
+
} else if (isPlainObject4(firstArg)) {
|
|
13502
13781
|
matched = matchesFixtureValue(matcher, firstArg);
|
|
13503
13782
|
} else if (args.length === 1 && Object.keys(matcher).length === 1) {
|
|
13504
13783
|
const [[, expectedValue]] = Object.entries(matcher);
|
|
@@ -13519,7 +13798,7 @@ function resolveFixtureMethodResult(methodName, definition, args) {
|
|
|
13519
13798
|
return Promise.resolve(null);
|
|
13520
13799
|
}
|
|
13521
13800
|
}
|
|
13522
|
-
if (
|
|
13801
|
+
if (isPlainObject4(definition)) {
|
|
13523
13802
|
const firstArg = args[0];
|
|
13524
13803
|
if (typeof firstArg === "string" && Object.prototype.hasOwnProperty.call(definition, firstArg)) {
|
|
13525
13804
|
return Promise.resolve(definition[firstArg]);
|
|
@@ -13531,7 +13810,7 @@ function resolveFixtureMethodResult(methodName, definition, args) {
|
|
|
13531
13810
|
return Promise.resolve(null);
|
|
13532
13811
|
}
|
|
13533
13812
|
function createFixtureService(definition) {
|
|
13534
|
-
const methods =
|
|
13813
|
+
const methods = isPlainObject4(definition) ? definition : {};
|
|
13535
13814
|
return new Proxy(
|
|
13536
13815
|
{},
|
|
13537
13816
|
{
|
|
@@ -13629,7 +13908,7 @@ async function resolveFixtureRuntime(command, services, requirementOptions) {
|
|
|
13629
13908
|
};
|
|
13630
13909
|
}
|
|
13631
13910
|
const scenario = await loadFixtureScenario(command, selector);
|
|
13632
|
-
const scenarioServices =
|
|
13911
|
+
const scenarioServices = isPlainObject4(scenario.services) ? scenario.services : {};
|
|
13633
13912
|
const customServiceNames = /* @__PURE__ */ new Set([
|
|
13634
13913
|
...Object.keys(services),
|
|
13635
13914
|
...Object.keys(scenarioServices).filter((name) => !RESERVED_SERVICE_NAMES.has(name))
|
|
@@ -13911,7 +14190,7 @@ function finalizeDynamicValue(schema, value, displayPath, errors2) {
|
|
|
13911
14190
|
if (itemSchema.kind !== "object") {
|
|
13912
14191
|
return value;
|
|
13913
14192
|
}
|
|
13914
|
-
if (!
|
|
14193
|
+
if (!isPlainObject4(value)) {
|
|
13915
14194
|
errors2.push({
|
|
13916
14195
|
path: displayPath,
|
|
13917
14196
|
message: `Invalid value for "${displayPath}". Expected indexed object entries, got ${describeReceived(value)}.`
|
|
@@ -13946,7 +14225,7 @@ function finalizeDynamicValue(schema, value, displayPath, errors2) {
|
|
|
13946
14225
|
);
|
|
13947
14226
|
}
|
|
13948
14227
|
case "object": {
|
|
13949
|
-
if (!
|
|
14228
|
+
if (!isPlainObject4(value)) {
|
|
13950
14229
|
errors2.push({
|
|
13951
14230
|
path: displayPath,
|
|
13952
14231
|
message: `Invalid value for "${displayPath}". Expected an object, got ${describeReceived(value)}.`
|
|
@@ -13977,7 +14256,7 @@ function finalizeDynamicValue(schema, value, displayPath, errors2) {
|
|
|
13977
14256
|
return result;
|
|
13978
14257
|
}
|
|
13979
14258
|
case "record": {
|
|
13980
|
-
if (!
|
|
14259
|
+
if (!isPlainObject4(value)) {
|
|
13981
14260
|
errors2.push({
|
|
13982
14261
|
path: displayPath,
|
|
13983
14262
|
message: `Invalid value for "${displayPath}". Expected an object, got ${describeReceived(value)}.`
|
|
@@ -14403,10 +14682,10 @@ async function executeCommand(state, services, requirementOptions, runtimeOption
|
|
|
14403
14682
|
}
|
|
14404
14683
|
}
|
|
14405
14684
|
function isStringRecord(value) {
|
|
14406
|
-
return
|
|
14685
|
+
return isPlainObject4(value) && Object.values(value).every((entry) => typeof entry === "string");
|
|
14407
14686
|
}
|
|
14408
14687
|
function isHttpErrorLike(error3) {
|
|
14409
|
-
if (!
|
|
14688
|
+
if (!isPlainObject4(error3)) {
|
|
14410
14689
|
return false;
|
|
14411
14690
|
}
|
|
14412
14691
|
if (error3.name !== "HttpError" || typeof error3.message !== "string") {
|
|
@@ -14414,7 +14693,7 @@ function isHttpErrorLike(error3) {
|
|
|
14414
14693
|
}
|
|
14415
14694
|
const request = error3.request;
|
|
14416
14695
|
const response = error3.response;
|
|
14417
|
-
return
|
|
14696
|
+
return isPlainObject4(request) && typeof request.method === "string" && typeof request.url === "string" && isStringRecord(request.headers) && isPlainObject4(response) && typeof response.status === "number" && typeof response.statusText === "string" && isStringRecord(response.headers) && "body" in response;
|
|
14418
14697
|
}
|
|
14419
14698
|
function hasTypedOptionalField(value, field, type2) {
|
|
14420
14699
|
return !(field in value) || typeof value[field] === type2;
|
|
@@ -14423,7 +14702,7 @@ function isNonEmptyString(value) {
|
|
|
14423
14702
|
return typeof value === "string" && value.trim().length > 0;
|
|
14424
14703
|
}
|
|
14425
14704
|
function isProblemDetailsLike(body) {
|
|
14426
|
-
if (!
|
|
14705
|
+
if (!isPlainObject4(body)) {
|
|
14427
14706
|
return false;
|
|
14428
14707
|
}
|
|
14429
14708
|
if (!hasTypedOptionalField(body, "type", "string")) {
|
|
@@ -14444,11 +14723,11 @@ function isProblemDetailsLike(body) {
|
|
|
14444
14723
|
return isNonEmptyString(body.title) || isNonEmptyString(body.detail);
|
|
14445
14724
|
}
|
|
14446
14725
|
function isGraphQLErrorEnvelopeLike(body) {
|
|
14447
|
-
if (!
|
|
14726
|
+
if (!isPlainObject4(body) || !Array.isArray(body.errors) || body.errors.length === 0) {
|
|
14448
14727
|
return false;
|
|
14449
14728
|
}
|
|
14450
14729
|
return body.errors.every((error3) => {
|
|
14451
|
-
if (!
|
|
14730
|
+
if (!isPlainObject4(error3) || typeof error3.message !== "string") {
|
|
14452
14731
|
return false;
|
|
14453
14732
|
}
|
|
14454
14733
|
if ("path" in error3) {
|
|
@@ -14458,7 +14737,7 @@ function isGraphQLErrorEnvelopeLike(body) {
|
|
|
14458
14737
|
}
|
|
14459
14738
|
}
|
|
14460
14739
|
if ("extensions" in error3) {
|
|
14461
|
-
if (!
|
|
14740
|
+
if (!isPlainObject4(error3.extensions)) {
|
|
14462
14741
|
return false;
|
|
14463
14742
|
}
|
|
14464
14743
|
if ("code" in error3.extensions && typeof error3.extensions.code !== "string") {
|
|
@@ -14506,23 +14785,24 @@ function formatGraphQLErrorEnvelopeBody(body) {
|
|
|
14506
14785
|
}).join("\n\n");
|
|
14507
14786
|
}
|
|
14508
14787
|
function formatHttpErrorBody(body) {
|
|
14509
|
-
|
|
14510
|
-
|
|
14788
|
+
const redactedBody = redactHttpBody(body);
|
|
14789
|
+
if (typeof redactedBody === "string") {
|
|
14790
|
+
return redactedBody;
|
|
14511
14791
|
}
|
|
14512
|
-
if (isProblemDetailsLike(
|
|
14513
|
-
return formatProblemDetailsBody(
|
|
14792
|
+
if (isProblemDetailsLike(redactedBody)) {
|
|
14793
|
+
return formatProblemDetailsBody(redactedBody);
|
|
14514
14794
|
}
|
|
14515
|
-
if (isGraphQLErrorEnvelopeLike(
|
|
14516
|
-
return formatGraphQLErrorEnvelopeBody(
|
|
14795
|
+
if (isGraphQLErrorEnvelopeLike(redactedBody)) {
|
|
14796
|
+
return formatGraphQLErrorEnvelopeBody(redactedBody);
|
|
14517
14797
|
}
|
|
14518
|
-
const serialized = JSON.stringify(
|
|
14519
|
-
return serialized === void 0 ? String(
|
|
14798
|
+
const serialized = JSON.stringify(redactedBody, null, 2);
|
|
14799
|
+
return serialized === void 0 ? String(redactedBody) : serialized;
|
|
14520
14800
|
}
|
|
14521
14801
|
function indentHttpErrorBlock(value) {
|
|
14522
14802
|
return value.split("\n").map((line) => ` ${line}`).join("\n");
|
|
14523
14803
|
}
|
|
14524
14804
|
function formatHttpHeaderValue(name, value) {
|
|
14525
|
-
return name
|
|
14805
|
+
return redactHttpHeaderValue(name, value);
|
|
14526
14806
|
}
|
|
14527
14807
|
function formatHttpErrorHeaders(headers) {
|
|
14528
14808
|
return Object.entries(headers).map(
|
|
@@ -14540,7 +14820,11 @@ function renderHttpError(error3, options) {
|
|
|
14540
14820
|
if (detailed) {
|
|
14541
14821
|
lines.push("", "Request headers:", ...formatHttpErrorHeaders(error3.request.headers), "");
|
|
14542
14822
|
if (error3.request.body !== void 0) {
|
|
14543
|
-
lines.push(
|
|
14823
|
+
lines.push(
|
|
14824
|
+
"Request body:",
|
|
14825
|
+
indentHttpErrorBlock(formatHttpErrorBody(error3.request.body)),
|
|
14826
|
+
""
|
|
14827
|
+
);
|
|
14544
14828
|
}
|
|
14545
14829
|
}
|
|
14546
14830
|
lines.push(
|
|
@@ -16629,11 +16913,11 @@ function resolveAgentSupport(input, registry = agentSkillConfigs) {
|
|
|
16629
16913
|
if (!resolvedId) {
|
|
16630
16914
|
return { status: "unknown", input };
|
|
16631
16915
|
}
|
|
16632
|
-
const
|
|
16633
|
-
if (!
|
|
16916
|
+
const config2 = registry[resolvedId];
|
|
16917
|
+
if (!config2) {
|
|
16634
16918
|
return { status: "unsupported", input, id: resolvedId };
|
|
16635
16919
|
}
|
|
16636
|
-
return { status: "supported", input, id: resolvedId, config: { ...
|
|
16920
|
+
return { status: "supported", input, id: resolvedId, config: { ...config2 } };
|
|
16637
16921
|
}
|
|
16638
16922
|
function getAgentConfig(agentId) {
|
|
16639
16923
|
const support = resolveAgentSupport(agentId);
|
|
@@ -17965,14 +18249,14 @@ async function installSkill(agentId, skill, options) {
|
|
|
17965
18249
|
throw new UnsupportedAgentError(agentId);
|
|
17966
18250
|
}
|
|
17967
18251
|
const scope = options.scope ?? "local";
|
|
17968
|
-
const
|
|
18252
|
+
const config2 = support.config;
|
|
17969
18253
|
if (skill.name.length === 0 || skill.name === "." || skill.name === ".." || skill.name.includes("/") || skill.name.includes("\\") || skill.name.includes("\n") || skill.name.includes("\r")) {
|
|
17970
18254
|
throw new Error(`Invalid skill name: ${skill.name}`);
|
|
17971
18255
|
}
|
|
17972
|
-
const skillDir = scope === "global" ?
|
|
18256
|
+
const skillDir = scope === "global" ? config2.globalSkillDir : toHomeRelative(config2.localSkillDir);
|
|
17973
18257
|
const skillFolderPath = `${skillDir}/${skill.name}`;
|
|
17974
18258
|
const skillFilePath = `${skillFolderPath}/SKILL.md`;
|
|
17975
|
-
const displayPath = `${scope === "global" ?
|
|
18259
|
+
const displayPath = `${scope === "global" ? config2.globalSkillDir : config2.localSkillDir}/${skill.name}/SKILL.md`;
|
|
17976
18260
|
const absoluteSkillPath = `${scope === "global" ? options.homeDir : options.cwd}/${skillFilePath.slice(2)}`;
|
|
17977
18261
|
if (await pathExists2(options.fs, absoluteSkillPath)) {
|
|
17978
18262
|
throw new Error(`Skill already exists: ${displayPath}`);
|
|
@@ -18093,17 +18377,17 @@ function resolveHomeRelativePath(targetPath, homeDir) {
|
|
|
18093
18377
|
return targetPath;
|
|
18094
18378
|
}
|
|
18095
18379
|
function getSkillFolderWithHome(agent, scope, cwd, homeDir) {
|
|
18096
|
-
const
|
|
18097
|
-
if (!
|
|
18380
|
+
const config2 = getAgentConfig(agent);
|
|
18381
|
+
if (!config2) {
|
|
18098
18382
|
throwUnsupportedAgent(agent);
|
|
18099
18383
|
}
|
|
18100
18384
|
return {
|
|
18101
18385
|
displayPath: path22.join(
|
|
18102
|
-
scope === "global" ?
|
|
18386
|
+
scope === "global" ? config2.globalSkillDir : config2.localSkillDir,
|
|
18103
18387
|
TERMINAL_PILOT_SKILL_NAME
|
|
18104
18388
|
),
|
|
18105
18389
|
fullPath: path22.join(
|
|
18106
|
-
scope === "global" ? resolveHomeRelativePath(
|
|
18390
|
+
scope === "global" ? resolveHomeRelativePath(config2.globalSkillDir, homeDir) : path22.resolve(cwd, config2.localSkillDir),
|
|
18107
18391
|
TERMINAL_PILOT_SKILL_NAME
|
|
18108
18392
|
)
|
|
18109
18393
|
};
|
|
@@ -19420,6 +19704,7 @@ function createTerminalPilotGroup() {
|
|
|
19420
19704
|
var terminalPilotGroup = Object.freeze(createTerminalPilotGroup());
|
|
19421
19705
|
|
|
19422
19706
|
// src/cli.ts
|
|
19707
|
+
configureTheme({ brand: "green", label: "Terminal Pilot" });
|
|
19423
19708
|
function normalizeArgv(argv) {
|
|
19424
19709
|
if (argv.includes("--json") && !argv.some((argument) => argument === "--output" || argument.startsWith("--output="))) {
|
|
19425
19710
|
return argv.flatMap((argument) => argument === "--json" ? ["--output", "json"] : [argument]);
|
|
@@ -19443,8 +19728,8 @@ async function isDirectExecution(argv) {
|
|
|
19443
19728
|
try {
|
|
19444
19729
|
const modulePath = fileURLToPath5(import.meta.url);
|
|
19445
19730
|
const [resolvedEntryPoint, resolvedModulePath] = await Promise.all([
|
|
19446
|
-
|
|
19447
|
-
|
|
19731
|
+
realpath3(path23.resolve(entryPoint)),
|
|
19732
|
+
realpath3(modulePath)
|
|
19448
19733
|
]);
|
|
19449
19734
|
return resolvedEntryPoint === resolvedModulePath;
|
|
19450
19735
|
} catch {
|