@agiflowai/one-mcp 0.3.2 → 0.3.4
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.cjs +89 -41
- package/dist/cli.mjs +89 -41
- package/dist/{http-xi_ha63Y.mjs → http-DEoeeLtl.mjs} +163 -130
- package/dist/{http-C4IfZSwW.cjs → http-TVcVma3Q.cjs} +163 -130
- package/dist/index.cjs +1 -1
- package/dist/index.mjs +1 -1
- package/package.json +1 -1
package/dist/cli.cjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
const require_http = require('./http-
|
|
2
|
+
const require_http = require('./http-TVcVma3Q.cjs');
|
|
3
3
|
let node_fs_promises = require("node:fs/promises");
|
|
4
4
|
let node_path = require("node:path");
|
|
5
5
|
let liquidjs = require("liquidjs");
|
|
@@ -148,14 +148,27 @@ const listToolsCommand = new commander.Command("list-tools").description("List a
|
|
|
148
148
|
process.exit(1);
|
|
149
149
|
}
|
|
150
150
|
const toolsByServer = {};
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
151
|
+
const toolResults = await Promise.all(clients.map(async (client) => {
|
|
152
|
+
try {
|
|
153
|
+
const tools = await client.listTools();
|
|
154
|
+
const blacklist = new Set(client.toolBlacklist || []);
|
|
155
|
+
const filteredTools = tools.filter((t) => !blacklist.has(t.name));
|
|
156
|
+
return {
|
|
157
|
+
serverName: client.serverName,
|
|
158
|
+
tools: filteredTools,
|
|
159
|
+
error: null
|
|
160
|
+
};
|
|
161
|
+
} catch (error) {
|
|
162
|
+
return {
|
|
163
|
+
serverName: client.serverName,
|
|
164
|
+
tools: [],
|
|
165
|
+
error
|
|
166
|
+
};
|
|
167
|
+
}
|
|
168
|
+
}));
|
|
169
|
+
for (const { serverName, tools, error } of toolResults) {
|
|
170
|
+
if (error && !options.json) console.error(`Failed to list tools from ${serverName}:`, error);
|
|
171
|
+
toolsByServer[serverName] = tools;
|
|
159
172
|
}
|
|
160
173
|
if (options.json) console.log(JSON.stringify(toolsByServer, null, 2));
|
|
161
174
|
else for (const [serverName, tools] of Object.entries(toolsByServer)) {
|
|
@@ -229,43 +242,60 @@ const describeToolsCommand = new commander.Command("describe-tools").description
|
|
|
229
242
|
const foundTools = [];
|
|
230
243
|
const foundSkills = [];
|
|
231
244
|
const notFoundTools = [...toolNames];
|
|
232
|
-
|
|
233
|
-
|
|
245
|
+
const filteredClients = clients.filter((client) => !options.server || client.serverName === options.server);
|
|
246
|
+
const toolResults = await Promise.all(filteredClients.map(async (client) => {
|
|
234
247
|
try {
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
server: client.serverName,
|
|
241
|
-
name: tool.name,
|
|
242
|
-
description: tool.description,
|
|
243
|
-
inputSchema: tool.inputSchema
|
|
244
|
-
});
|
|
245
|
-
const idx = notFoundTools.indexOf(toolName);
|
|
246
|
-
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
247
|
-
}
|
|
248
|
-
}
|
|
248
|
+
return {
|
|
249
|
+
client,
|
|
250
|
+
tools: await client.listTools(),
|
|
251
|
+
error: null
|
|
252
|
+
};
|
|
249
253
|
} catch (error) {
|
|
254
|
+
return {
|
|
255
|
+
client,
|
|
256
|
+
tools: [],
|
|
257
|
+
error
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
}));
|
|
261
|
+
for (const { client, tools, error } of toolResults) {
|
|
262
|
+
if (error) {
|
|
250
263
|
if (!options.json) console.error(`Failed to list tools from ${client.serverName}:`, error);
|
|
264
|
+
continue;
|
|
251
265
|
}
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
name: skill.name,
|
|
261
|
-
location: skill.basePath,
|
|
262
|
-
instructions: skill.content
|
|
266
|
+
for (const toolName of toolNames) {
|
|
267
|
+
const tool = tools.find((t) => t.name === toolName);
|
|
268
|
+
if (tool) {
|
|
269
|
+
foundTools.push({
|
|
270
|
+
server: client.serverName,
|
|
271
|
+
name: tool.name,
|
|
272
|
+
description: tool.description,
|
|
273
|
+
inputSchema: tool.inputSchema
|
|
263
274
|
});
|
|
264
275
|
const idx = notFoundTools.indexOf(toolName);
|
|
265
276
|
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
266
277
|
}
|
|
267
278
|
}
|
|
268
279
|
}
|
|
280
|
+
if (skillService && notFoundTools.length > 0) {
|
|
281
|
+
const skillsToCheck = [...notFoundTools];
|
|
282
|
+
const skillResults = await Promise.all(skillsToCheck.map(async (toolName) => {
|
|
283
|
+
const skillName = toolName.startsWith("skill__") ? toolName.slice(7) : toolName;
|
|
284
|
+
return {
|
|
285
|
+
toolName,
|
|
286
|
+
skill: await skillService.getSkill(skillName)
|
|
287
|
+
};
|
|
288
|
+
}));
|
|
289
|
+
for (const { toolName, skill } of skillResults) if (skill) {
|
|
290
|
+
foundSkills.push({
|
|
291
|
+
name: skill.name,
|
|
292
|
+
location: skill.basePath,
|
|
293
|
+
instructions: skill.content
|
|
294
|
+
});
|
|
295
|
+
const idx = notFoundTools.indexOf(toolName);
|
|
296
|
+
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
269
299
|
const nextSteps = [];
|
|
270
300
|
if (foundTools.length > 0) nextSteps.push("For MCP tools: Use the use_tool function with toolName and toolArgs based on the inputSchema above.");
|
|
271
301
|
if (foundSkills.length > 0) nextSteps.push(`For skill, just follow skill's description to continue.`);
|
|
@@ -398,11 +428,29 @@ const useToolCommand = new commander.Command("use-tool").description("Execute an
|
|
|
398
428
|
process.exit(1);
|
|
399
429
|
}
|
|
400
430
|
}
|
|
431
|
+
const searchResults = await Promise.all(clients.map(async (client$1) => {
|
|
432
|
+
try {
|
|
433
|
+
const hasTool = (await client$1.listTools()).some((t) => t.name === toolName);
|
|
434
|
+
return {
|
|
435
|
+
serverName: client$1.serverName,
|
|
436
|
+
hasTool,
|
|
437
|
+
error: null
|
|
438
|
+
};
|
|
439
|
+
} catch (error) {
|
|
440
|
+
return {
|
|
441
|
+
serverName: client$1.serverName,
|
|
442
|
+
hasTool: false,
|
|
443
|
+
error
|
|
444
|
+
};
|
|
445
|
+
}
|
|
446
|
+
}));
|
|
401
447
|
const matchingServers = [];
|
|
402
|
-
for (const
|
|
403
|
-
if (
|
|
404
|
-
|
|
405
|
-
|
|
448
|
+
for (const { serverName, hasTool, error } of searchResults) {
|
|
449
|
+
if (error) {
|
|
450
|
+
if (!options.json) console.error(`Failed to list tools from ${serverName}:`, error);
|
|
451
|
+
continue;
|
|
452
|
+
}
|
|
453
|
+
if (hasTool) matchingServers.push(serverName);
|
|
406
454
|
}
|
|
407
455
|
if (matchingServers.length === 0) {
|
|
408
456
|
const cwd = process.env.PROJECT_PATH || process.cwd();
|
|
@@ -1003,7 +1051,7 @@ const prefetchCommand = new commander.Command("prefetch").description("Pre-downl
|
|
|
1003
1051
|
|
|
1004
1052
|
//#endregion
|
|
1005
1053
|
//#region package.json
|
|
1006
|
-
var version = "0.3.
|
|
1054
|
+
var version = "0.3.3";
|
|
1007
1055
|
|
|
1008
1056
|
//#endregion
|
|
1009
1057
|
//#region src/cli.ts
|
package/dist/cli.mjs
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
#!/usr/bin/env node
|
|
2
|
-
import { a as SkillService, c as ConfigFetcherService, i as createServer, n as SseTransportHandler, o as findConfigFile, r as StdioTransportHandler, s as McpClientManagerService, t as HttpTransportHandler } from "./http-
|
|
2
|
+
import { a as SkillService, c as ConfigFetcherService, i as createServer, n as SseTransportHandler, o as findConfigFile, r as StdioTransportHandler, s as McpClientManagerService, t as HttpTransportHandler } from "./http-DEoeeLtl.mjs";
|
|
3
3
|
import { writeFile } from "node:fs/promises";
|
|
4
4
|
import { resolve } from "node:path";
|
|
5
5
|
import { Liquid } from "liquidjs";
|
|
@@ -148,14 +148,27 @@ const listToolsCommand = new Command("list-tools").description("List all availab
|
|
|
148
148
|
process.exit(1);
|
|
149
149
|
}
|
|
150
150
|
const toolsByServer = {};
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
151
|
+
const toolResults = await Promise.all(clients.map(async (client) => {
|
|
152
|
+
try {
|
|
153
|
+
const tools = await client.listTools();
|
|
154
|
+
const blacklist = new Set(client.toolBlacklist || []);
|
|
155
|
+
const filteredTools = tools.filter((t) => !blacklist.has(t.name));
|
|
156
|
+
return {
|
|
157
|
+
serverName: client.serverName,
|
|
158
|
+
tools: filteredTools,
|
|
159
|
+
error: null
|
|
160
|
+
};
|
|
161
|
+
} catch (error) {
|
|
162
|
+
return {
|
|
163
|
+
serverName: client.serverName,
|
|
164
|
+
tools: [],
|
|
165
|
+
error
|
|
166
|
+
};
|
|
167
|
+
}
|
|
168
|
+
}));
|
|
169
|
+
for (const { serverName, tools, error } of toolResults) {
|
|
170
|
+
if (error && !options.json) console.error(`Failed to list tools from ${serverName}:`, error);
|
|
171
|
+
toolsByServer[serverName] = tools;
|
|
159
172
|
}
|
|
160
173
|
if (options.json) console.log(JSON.stringify(toolsByServer, null, 2));
|
|
161
174
|
else for (const [serverName, tools] of Object.entries(toolsByServer)) {
|
|
@@ -229,43 +242,60 @@ const describeToolsCommand = new Command("describe-tools").description("Describe
|
|
|
229
242
|
const foundTools = [];
|
|
230
243
|
const foundSkills = [];
|
|
231
244
|
const notFoundTools = [...toolNames];
|
|
232
|
-
|
|
233
|
-
|
|
245
|
+
const filteredClients = clients.filter((client) => !options.server || client.serverName === options.server);
|
|
246
|
+
const toolResults = await Promise.all(filteredClients.map(async (client) => {
|
|
234
247
|
try {
|
|
235
|
-
|
|
236
|
-
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
server: client.serverName,
|
|
241
|
-
name: tool.name,
|
|
242
|
-
description: tool.description,
|
|
243
|
-
inputSchema: tool.inputSchema
|
|
244
|
-
});
|
|
245
|
-
const idx = notFoundTools.indexOf(toolName);
|
|
246
|
-
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
247
|
-
}
|
|
248
|
-
}
|
|
248
|
+
return {
|
|
249
|
+
client,
|
|
250
|
+
tools: await client.listTools(),
|
|
251
|
+
error: null
|
|
252
|
+
};
|
|
249
253
|
} catch (error) {
|
|
254
|
+
return {
|
|
255
|
+
client,
|
|
256
|
+
tools: [],
|
|
257
|
+
error
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
}));
|
|
261
|
+
for (const { client, tools, error } of toolResults) {
|
|
262
|
+
if (error) {
|
|
250
263
|
if (!options.json) console.error(`Failed to list tools from ${client.serverName}:`, error);
|
|
264
|
+
continue;
|
|
251
265
|
}
|
|
252
|
-
|
|
253
|
-
|
|
254
|
-
|
|
255
|
-
|
|
256
|
-
|
|
257
|
-
|
|
258
|
-
|
|
259
|
-
|
|
260
|
-
name: skill.name,
|
|
261
|
-
location: skill.basePath,
|
|
262
|
-
instructions: skill.content
|
|
266
|
+
for (const toolName of toolNames) {
|
|
267
|
+
const tool = tools.find((t) => t.name === toolName);
|
|
268
|
+
if (tool) {
|
|
269
|
+
foundTools.push({
|
|
270
|
+
server: client.serverName,
|
|
271
|
+
name: tool.name,
|
|
272
|
+
description: tool.description,
|
|
273
|
+
inputSchema: tool.inputSchema
|
|
263
274
|
});
|
|
264
275
|
const idx = notFoundTools.indexOf(toolName);
|
|
265
276
|
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
266
277
|
}
|
|
267
278
|
}
|
|
268
279
|
}
|
|
280
|
+
if (skillService && notFoundTools.length > 0) {
|
|
281
|
+
const skillsToCheck = [...notFoundTools];
|
|
282
|
+
const skillResults = await Promise.all(skillsToCheck.map(async (toolName) => {
|
|
283
|
+
const skillName = toolName.startsWith("skill__") ? toolName.slice(7) : toolName;
|
|
284
|
+
return {
|
|
285
|
+
toolName,
|
|
286
|
+
skill: await skillService.getSkill(skillName)
|
|
287
|
+
};
|
|
288
|
+
}));
|
|
289
|
+
for (const { toolName, skill } of skillResults) if (skill) {
|
|
290
|
+
foundSkills.push({
|
|
291
|
+
name: skill.name,
|
|
292
|
+
location: skill.basePath,
|
|
293
|
+
instructions: skill.content
|
|
294
|
+
});
|
|
295
|
+
const idx = notFoundTools.indexOf(toolName);
|
|
296
|
+
if (idx > -1) notFoundTools.splice(idx, 1);
|
|
297
|
+
}
|
|
298
|
+
}
|
|
269
299
|
const nextSteps = [];
|
|
270
300
|
if (foundTools.length > 0) nextSteps.push("For MCP tools: Use the use_tool function with toolName and toolArgs based on the inputSchema above.");
|
|
271
301
|
if (foundSkills.length > 0) nextSteps.push(`For skill, just follow skill's description to continue.`);
|
|
@@ -398,11 +428,29 @@ const useToolCommand = new Command("use-tool").description("Execute an MCP tool
|
|
|
398
428
|
process.exit(1);
|
|
399
429
|
}
|
|
400
430
|
}
|
|
431
|
+
const searchResults = await Promise.all(clients.map(async (client$1) => {
|
|
432
|
+
try {
|
|
433
|
+
const hasTool = (await client$1.listTools()).some((t) => t.name === toolName);
|
|
434
|
+
return {
|
|
435
|
+
serverName: client$1.serverName,
|
|
436
|
+
hasTool,
|
|
437
|
+
error: null
|
|
438
|
+
};
|
|
439
|
+
} catch (error) {
|
|
440
|
+
return {
|
|
441
|
+
serverName: client$1.serverName,
|
|
442
|
+
hasTool: false,
|
|
443
|
+
error
|
|
444
|
+
};
|
|
445
|
+
}
|
|
446
|
+
}));
|
|
401
447
|
const matchingServers = [];
|
|
402
|
-
for (const
|
|
403
|
-
if (
|
|
404
|
-
|
|
405
|
-
|
|
448
|
+
for (const { serverName, hasTool, error } of searchResults) {
|
|
449
|
+
if (error) {
|
|
450
|
+
if (!options.json) console.error(`Failed to list tools from ${serverName}:`, error);
|
|
451
|
+
continue;
|
|
452
|
+
}
|
|
453
|
+
if (hasTool) matchingServers.push(serverName);
|
|
406
454
|
}
|
|
407
455
|
if (matchingServers.length === 0) {
|
|
408
456
|
const cwd = process.env.PROJECT_PATH || process.cwd();
|
|
@@ -1003,7 +1051,7 @@ const prefetchCommand = new Command("prefetch").description("Pre-download packag
|
|
|
1003
1051
|
|
|
1004
1052
|
//#endregion
|
|
1005
1053
|
//#region package.json
|
|
1006
|
-
var version = "0.3.
|
|
1054
|
+
var version = "0.3.3";
|
|
1007
1055
|
|
|
1008
1056
|
//#endregion
|
|
1009
1057
|
//#region src/cli.ts
|
|
@@ -528,22 +528,21 @@ var RemoteConfigCacheService = class {
|
|
|
528
528
|
try {
|
|
529
529
|
if (!existsSync(this.cacheDir)) return;
|
|
530
530
|
const now = Date.now();
|
|
531
|
-
const
|
|
532
|
-
|
|
533
|
-
for (const file of files) {
|
|
534
|
-
if (!file.endsWith(".json")) continue;
|
|
531
|
+
const jsonFiles = (await readdir(this.cacheDir)).filter((file) => file.endsWith(".json"));
|
|
532
|
+
const expiredCount = (await Promise.all(jsonFiles.map(async (file) => {
|
|
535
533
|
const filePath = join(this.cacheDir, file);
|
|
536
534
|
try {
|
|
537
535
|
const content = await readFile(filePath, "utf-8");
|
|
538
536
|
if (now > JSON.parse(content).expiresAt) {
|
|
539
537
|
await unlink(filePath);
|
|
540
|
-
|
|
538
|
+
return true;
|
|
541
539
|
}
|
|
540
|
+
return false;
|
|
542
541
|
} catch (error) {
|
|
543
542
|
await unlink(filePath).catch(() => {});
|
|
544
|
-
|
|
543
|
+
return true;
|
|
545
544
|
}
|
|
546
|
-
}
|
|
545
|
+
}))).filter(Boolean).length;
|
|
547
546
|
if (expiredCount > 0) console.error(`Cleaned up ${expiredCount} expired remote config cache entries`);
|
|
548
547
|
} catch (error) {
|
|
549
548
|
console.error("Failed to clean expired remote config cache:", error);
|
|
@@ -559,14 +558,15 @@ var RemoteConfigCacheService = class {
|
|
|
559
558
|
totalSize: 0
|
|
560
559
|
};
|
|
561
560
|
const jsonFiles = (await readdir(this.cacheDir)).filter((file) => file.endsWith(".json"));
|
|
562
|
-
|
|
563
|
-
for (const file of jsonFiles) {
|
|
561
|
+
const totalSize = (await Promise.all(jsonFiles.map(async (file) => {
|
|
564
562
|
const filePath = join(this.cacheDir, file);
|
|
565
563
|
try {
|
|
566
564
|
const content = await readFile(filePath, "utf-8");
|
|
567
|
-
|
|
568
|
-
} catch {
|
|
569
|
-
|
|
565
|
+
return Buffer.byteLength(content, "utf-8");
|
|
566
|
+
} catch {
|
|
567
|
+
return 0;
|
|
568
|
+
}
|
|
569
|
+
}))).reduce((sum, size) => sum + size, 0);
|
|
570
570
|
return {
|
|
571
571
|
totalEntries: jsonFiles.length,
|
|
572
572
|
totalSize
|
|
@@ -967,7 +967,10 @@ var McpClientManagerService = class {
|
|
|
967
967
|
const transport = new StdioClientTransport({
|
|
968
968
|
command: config.command,
|
|
969
969
|
args: config.args,
|
|
970
|
-
env:
|
|
970
|
+
env: {
|
|
971
|
+
...process.env,
|
|
972
|
+
...config.env ?? {}
|
|
973
|
+
}
|
|
971
974
|
});
|
|
972
975
|
await mcpClient["client"].connect(transport);
|
|
973
976
|
const childProcess = transport["_process"];
|
|
@@ -1387,13 +1390,13 @@ var SkillService = class {
|
|
|
1387
1390
|
if (this.cachedSkills !== null) return this.cachedSkills;
|
|
1388
1391
|
const skills = [];
|
|
1389
1392
|
const loadedSkillNames = /* @__PURE__ */ new Set();
|
|
1390
|
-
|
|
1393
|
+
const allDirSkills = await Promise.all(this.skillPaths.map(async (skillPath) => {
|
|
1391
1394
|
const skillsDir = isAbsolute(skillPath) ? skillPath : join(this.cwd, skillPath);
|
|
1392
|
-
|
|
1393
|
-
|
|
1394
|
-
|
|
1395
|
-
|
|
1396
|
-
|
|
1395
|
+
return this.loadSkillsFromDirectory(skillsDir, "project");
|
|
1396
|
+
}));
|
|
1397
|
+
for (const dirSkills of allDirSkills) for (const skill of dirSkills) if (!loadedSkillNames.has(skill.name)) {
|
|
1398
|
+
skills.push(skill);
|
|
1399
|
+
loadedSkillNames.add(skill.name);
|
|
1397
1400
|
}
|
|
1398
1401
|
this.cachedSkills = skills;
|
|
1399
1402
|
this.skillsByName = new Map(skills.map((skill) => [skill.name, skill]));
|
|
@@ -1431,9 +1434,15 @@ var SkillService = class {
|
|
|
1431
1434
|
*/
|
|
1432
1435
|
async startWatching() {
|
|
1433
1436
|
this.stopWatching();
|
|
1434
|
-
|
|
1437
|
+
const existenceChecks = await Promise.all(this.skillPaths.map(async (skillPath) => {
|
|
1435
1438
|
const skillsDir = isAbsolute(skillPath) ? skillPath : join(this.cwd, skillPath);
|
|
1436
|
-
|
|
1439
|
+
return {
|
|
1440
|
+
skillsDir,
|
|
1441
|
+
exists: await pathExists(skillsDir)
|
|
1442
|
+
};
|
|
1443
|
+
}));
|
|
1444
|
+
for (const { skillsDir, exists } of existenceChecks) {
|
|
1445
|
+
if (!exists) continue;
|
|
1437
1446
|
const abortController = new AbortController();
|
|
1438
1447
|
this.watchers.push(abortController);
|
|
1439
1448
|
this.watchDirectory(skillsDir, abortController.signal).catch((error) => {
|
|
@@ -1491,34 +1500,49 @@ var SkillService = class {
|
|
|
1491
1500
|
} catch (error) {
|
|
1492
1501
|
throw new SkillLoadError(`Failed to read skills directory: ${error instanceof Error ? error.message : "Unknown error"}`, dirPath, error instanceof Error ? error : void 0);
|
|
1493
1502
|
}
|
|
1494
|
-
|
|
1503
|
+
const entryStats = await Promise.all(entries.map(async (entry) => {
|
|
1495
1504
|
const entryPath = join(dirPath, entry);
|
|
1496
|
-
let entryStat;
|
|
1497
1505
|
try {
|
|
1498
|
-
|
|
1506
|
+
return {
|
|
1507
|
+
entry,
|
|
1508
|
+
entryPath,
|
|
1509
|
+
stat: await stat(entryPath),
|
|
1510
|
+
error: null
|
|
1511
|
+
};
|
|
1499
1512
|
} catch (error) {
|
|
1500
1513
|
console.warn(`Skipping entry ${entryPath}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1501
|
-
|
|
1514
|
+
return {
|
|
1515
|
+
entry,
|
|
1516
|
+
entryPath,
|
|
1517
|
+
stat: null,
|
|
1518
|
+
error
|
|
1519
|
+
};
|
|
1502
1520
|
}
|
|
1521
|
+
}));
|
|
1522
|
+
const skillFilesToLoad = [];
|
|
1523
|
+
for (const { entry, entryPath, stat: entryStat } of entryStats) {
|
|
1524
|
+
if (!entryStat) continue;
|
|
1503
1525
|
if (entryStat.isDirectory()) {
|
|
1504
1526
|
const skillFilePath = join(entryPath, "SKILL.md");
|
|
1505
|
-
|
|
1506
|
-
|
|
1507
|
-
|
|
1508
|
-
|
|
1509
|
-
|
|
1510
|
-
|
|
1511
|
-
|
|
1512
|
-
|
|
1513
|
-
|
|
1514
|
-
|
|
1515
|
-
|
|
1516
|
-
if (
|
|
1527
|
+
skillFilesToLoad.push({
|
|
1528
|
+
filePath: skillFilePath,
|
|
1529
|
+
isRootLevel: false
|
|
1530
|
+
});
|
|
1531
|
+
} else if (entry === "SKILL.md") skillFilesToLoad.push({
|
|
1532
|
+
filePath: entryPath,
|
|
1533
|
+
isRootLevel: true
|
|
1534
|
+
});
|
|
1535
|
+
}
|
|
1536
|
+
const loadResults = await Promise.all(skillFilesToLoad.map(async ({ filePath, isRootLevel }) => {
|
|
1537
|
+
try {
|
|
1538
|
+
if (!isRootLevel && !await pathExists(filePath)) return null;
|
|
1539
|
+
return await this.loadSkillFile(filePath, location);
|
|
1517
1540
|
} catch (error) {
|
|
1518
|
-
console.warn(`Skipping skill at ${
|
|
1519
|
-
|
|
1541
|
+
console.warn(`Skipping skill at ${filePath}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1542
|
+
return null;
|
|
1520
1543
|
}
|
|
1521
|
-
}
|
|
1544
|
+
}));
|
|
1545
|
+
for (const skill of loadResults) if (skill) skills.push(skill);
|
|
1522
1546
|
return skills;
|
|
1523
1547
|
}
|
|
1524
1548
|
/**
|
|
@@ -1660,44 +1684,42 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
1660
1684
|
async detectSkillsFromPromptFrontMatter() {
|
|
1661
1685
|
if (this.autoDetectedSkillsCache !== null) return this.autoDetectedSkillsCache;
|
|
1662
1686
|
const clients = this.clientManager.getAllClients();
|
|
1663
|
-
const autoDetectedSkills = [];
|
|
1664
1687
|
let listPromptsFailures = 0;
|
|
1665
1688
|
let fetchPromptFailures = 0;
|
|
1666
|
-
const
|
|
1667
|
-
|
|
1689
|
+
const autoDetectedSkills = (await Promise.all(clients.map(async (client) => {
|
|
1690
|
+
const detectedSkills = [];
|
|
1668
1691
|
const configuredPromptNames = new Set(client.prompts ? Object.keys(client.prompts) : []);
|
|
1669
|
-
|
|
1670
|
-
|
|
1671
|
-
|
|
1672
|
-
|
|
1673
|
-
|
|
1674
|
-
|
|
1675
|
-
|
|
1676
|
-
const
|
|
1677
|
-
|
|
1678
|
-
|
|
1679
|
-
|
|
1680
|
-
|
|
1681
|
-
|
|
1682
|
-
|
|
1683
|
-
|
|
1684
|
-
|
|
1685
|
-
|
|
1686
|
-
|
|
1687
|
-
|
|
1688
|
-
|
|
1689
|
-
|
|
1690
|
-
|
|
1691
|
-
}
|
|
1692
|
-
|
|
1693
|
-
|
|
1694
|
-
|
|
1695
|
-
|
|
1696
|
-
}
|
|
1697
|
-
}
|
|
1698
|
-
|
|
1699
|
-
}
|
|
1700
|
-
await Promise.all(fetchPromises);
|
|
1692
|
+
try {
|
|
1693
|
+
const prompts = await client.listPrompts();
|
|
1694
|
+
if (!prompts || prompts.length === 0) return detectedSkills;
|
|
1695
|
+
const promptResults = await Promise.all(prompts.map(async (promptInfo) => {
|
|
1696
|
+
if (configuredPromptNames.has(promptInfo.name)) return null;
|
|
1697
|
+
try {
|
|
1698
|
+
const skillExtraction = extractSkillFrontMatter(((await client.getPrompt(promptInfo.name)).messages || []).map((m) => {
|
|
1699
|
+
const content = m.content;
|
|
1700
|
+
if (typeof content === "string") return content;
|
|
1701
|
+
if (content && typeof content === "object" && "text" in content) return String(content.text);
|
|
1702
|
+
return "";
|
|
1703
|
+
}).join("\n"));
|
|
1704
|
+
if (skillExtraction) return {
|
|
1705
|
+
serverName: client.serverName,
|
|
1706
|
+
promptName: promptInfo.name,
|
|
1707
|
+
skill: skillExtraction.skill
|
|
1708
|
+
};
|
|
1709
|
+
return null;
|
|
1710
|
+
} catch (error) {
|
|
1711
|
+
fetchPromptFailures++;
|
|
1712
|
+
console.error(`${LOG_PREFIX_SKILL_DETECTION} Failed to fetch prompt '${promptInfo.name}' from ${client.serverName}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1713
|
+
return null;
|
|
1714
|
+
}
|
|
1715
|
+
}));
|
|
1716
|
+
for (const result of promptResults) if (result) detectedSkills.push(result);
|
|
1717
|
+
} catch (error) {
|
|
1718
|
+
listPromptsFailures++;
|
|
1719
|
+
console.error(`${LOG_PREFIX_SKILL_DETECTION} Failed to list prompts from ${client.serverName}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1720
|
+
}
|
|
1721
|
+
return detectedSkills;
|
|
1722
|
+
}))).flat();
|
|
1701
1723
|
if (listPromptsFailures > 0 || fetchPromptFailures > 0) console.error(`${LOG_PREFIX_SKILL_DETECTION} Completed with ${listPromptsFailures} server failure(s) and ${fetchPromptFailures} prompt failure(s). Detected ${autoDetectedSkills.length} skill(s).`);
|
|
1702
1724
|
this.autoDetectedSkillsCache = autoDetectedSkills;
|
|
1703
1725
|
return autoDetectedSkills;
|
|
@@ -1948,40 +1970,42 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
1948
1970
|
serverToolsMap.set(client.serverName, []);
|
|
1949
1971
|
}
|
|
1950
1972
|
}));
|
|
1951
|
-
const
|
|
1952
|
-
|
|
1953
|
-
|
|
1954
|
-
|
|
1973
|
+
const lookupResults = await Promise.all(toolNames.map(async (requestedName) => {
|
|
1974
|
+
const result$1 = {
|
|
1975
|
+
tools: [],
|
|
1976
|
+
skills: [],
|
|
1977
|
+
notFound: null
|
|
1978
|
+
};
|
|
1955
1979
|
if (requestedName.startsWith(SKILL_PREFIX)) {
|
|
1956
1980
|
const skillName = requestedName.slice(SKILL_PREFIX.length);
|
|
1957
1981
|
if (this.skillService) {
|
|
1958
1982
|
const skill = await this.skillService.getSkill(skillName);
|
|
1959
1983
|
if (skill) {
|
|
1960
|
-
|
|
1984
|
+
result$1.skills.push({
|
|
1961
1985
|
name: skill.name,
|
|
1962
1986
|
location: skill.basePath,
|
|
1963
1987
|
instructions: formatSkillInstructions(skill.name, skill.content)
|
|
1964
1988
|
});
|
|
1965
|
-
|
|
1989
|
+
return result$1;
|
|
1966
1990
|
}
|
|
1967
1991
|
}
|
|
1968
1992
|
const promptSkillContent = await this.getPromptSkillContent(skillName);
|
|
1969
1993
|
if (promptSkillContent) {
|
|
1970
|
-
|
|
1971
|
-
|
|
1994
|
+
result$1.skills.push(promptSkillContent);
|
|
1995
|
+
return result$1;
|
|
1972
1996
|
}
|
|
1973
|
-
|
|
1974
|
-
|
|
1997
|
+
result$1.notFound = requestedName;
|
|
1998
|
+
return result$1;
|
|
1975
1999
|
}
|
|
1976
2000
|
const { serverName, actualToolName } = parseToolName(requestedName);
|
|
1977
2001
|
if (serverName) {
|
|
1978
2002
|
const serverTools = serverToolsMap.get(serverName);
|
|
1979
2003
|
if (!serverTools) {
|
|
1980
|
-
|
|
1981
|
-
|
|
2004
|
+
result$1.notFound = requestedName;
|
|
2005
|
+
return result$1;
|
|
1982
2006
|
}
|
|
1983
2007
|
const tool = serverTools.find((t) => t.name === actualToolName);
|
|
1984
|
-
if (tool)
|
|
2008
|
+
if (tool) result$1.tools.push({
|
|
1985
2009
|
server: serverName,
|
|
1986
2010
|
tool: {
|
|
1987
2011
|
name: tool.name,
|
|
@@ -1989,52 +2013,61 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
1989
2013
|
inputSchema: tool.inputSchema
|
|
1990
2014
|
}
|
|
1991
2015
|
});
|
|
1992
|
-
else
|
|
1993
|
-
|
|
1994
|
-
|
|
1995
|
-
|
|
1996
|
-
|
|
1997
|
-
|
|
1998
|
-
|
|
1999
|
-
|
|
2000
|
-
|
|
2001
|
-
|
|
2002
|
-
|
|
2003
|
-
|
|
2004
|
-
|
|
2005
|
-
|
|
2006
|
-
}
|
|
2007
|
-
const promptSkillContent = await this.getPromptSkillContent(actualToolName);
|
|
2008
|
-
if (promptSkillContent) {
|
|
2009
|
-
foundSkills.push(promptSkillContent);
|
|
2010
|
-
continue;
|
|
2016
|
+
else result$1.notFound = requestedName;
|
|
2017
|
+
return result$1;
|
|
2018
|
+
}
|
|
2019
|
+
const servers = toolToServers.get(actualToolName);
|
|
2020
|
+
if (!servers || servers.length === 0) {
|
|
2021
|
+
if (this.skillService) {
|
|
2022
|
+
const skill = await this.skillService.getSkill(actualToolName);
|
|
2023
|
+
if (skill) {
|
|
2024
|
+
result$1.skills.push({
|
|
2025
|
+
name: skill.name,
|
|
2026
|
+
location: skill.basePath,
|
|
2027
|
+
instructions: formatSkillInstructions(skill.name, skill.content)
|
|
2028
|
+
});
|
|
2029
|
+
return result$1;
|
|
2011
2030
|
}
|
|
2012
|
-
notFoundItems.push(requestedName);
|
|
2013
|
-
continue;
|
|
2014
2031
|
}
|
|
2015
|
-
|
|
2016
|
-
|
|
2017
|
-
|
|
2018
|
-
|
|
2019
|
-
server,
|
|
2020
|
-
tool: {
|
|
2021
|
-
name: tool.name,
|
|
2022
|
-
description: tool.description,
|
|
2023
|
-
inputSchema: tool.inputSchema
|
|
2024
|
-
}
|
|
2025
|
-
});
|
|
2026
|
-
} else for (const server of servers) {
|
|
2027
|
-
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2028
|
-
foundTools.push({
|
|
2029
|
-
server,
|
|
2030
|
-
tool: {
|
|
2031
|
-
name: tool.name,
|
|
2032
|
-
description: tool.description,
|
|
2033
|
-
inputSchema: tool.inputSchema
|
|
2034
|
-
}
|
|
2035
|
-
});
|
|
2032
|
+
const promptSkillContent = await this.getPromptSkillContent(actualToolName);
|
|
2033
|
+
if (promptSkillContent) {
|
|
2034
|
+
result$1.skills.push(promptSkillContent);
|
|
2035
|
+
return result$1;
|
|
2036
2036
|
}
|
|
2037
|
+
result$1.notFound = requestedName;
|
|
2038
|
+
return result$1;
|
|
2037
2039
|
}
|
|
2040
|
+
if (servers.length === 1) {
|
|
2041
|
+
const server = servers[0];
|
|
2042
|
+
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2043
|
+
result$1.tools.push({
|
|
2044
|
+
server,
|
|
2045
|
+
tool: {
|
|
2046
|
+
name: tool.name,
|
|
2047
|
+
description: tool.description,
|
|
2048
|
+
inputSchema: tool.inputSchema
|
|
2049
|
+
}
|
|
2050
|
+
});
|
|
2051
|
+
} else for (const server of servers) {
|
|
2052
|
+
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2053
|
+
result$1.tools.push({
|
|
2054
|
+
server,
|
|
2055
|
+
tool: {
|
|
2056
|
+
name: tool.name,
|
|
2057
|
+
description: tool.description,
|
|
2058
|
+
inputSchema: tool.inputSchema
|
|
2059
|
+
}
|
|
2060
|
+
});
|
|
2061
|
+
}
|
|
2062
|
+
return result$1;
|
|
2063
|
+
}));
|
|
2064
|
+
const foundTools = [];
|
|
2065
|
+
const foundSkills = [];
|
|
2066
|
+
const notFoundItems = [];
|
|
2067
|
+
for (const result$1 of lookupResults) {
|
|
2068
|
+
foundTools.push(...result$1.tools);
|
|
2069
|
+
foundSkills.push(...result$1.skills);
|
|
2070
|
+
if (result$1.notFound) notFoundItems.push(result$1.notFound);
|
|
2038
2071
|
}
|
|
2039
2072
|
if (foundTools.length === 0 && foundSkills.length === 0) return {
|
|
2040
2073
|
content: [{
|
|
@@ -557,22 +557,21 @@ var RemoteConfigCacheService = class {
|
|
|
557
557
|
try {
|
|
558
558
|
if (!(0, node_fs.existsSync)(this.cacheDir)) return;
|
|
559
559
|
const now = Date.now();
|
|
560
|
-
const
|
|
561
|
-
|
|
562
|
-
for (const file of files) {
|
|
563
|
-
if (!file.endsWith(".json")) continue;
|
|
560
|
+
const jsonFiles = (await (0, node_fs_promises.readdir)(this.cacheDir)).filter((file) => file.endsWith(".json"));
|
|
561
|
+
const expiredCount = (await Promise.all(jsonFiles.map(async (file) => {
|
|
564
562
|
const filePath = (0, node_path.join)(this.cacheDir, file);
|
|
565
563
|
try {
|
|
566
564
|
const content = await (0, node_fs_promises.readFile)(filePath, "utf-8");
|
|
567
565
|
if (now > JSON.parse(content).expiresAt) {
|
|
568
566
|
await (0, node_fs_promises.unlink)(filePath);
|
|
569
|
-
|
|
567
|
+
return true;
|
|
570
568
|
}
|
|
569
|
+
return false;
|
|
571
570
|
} catch (error) {
|
|
572
571
|
await (0, node_fs_promises.unlink)(filePath).catch(() => {});
|
|
573
|
-
|
|
572
|
+
return true;
|
|
574
573
|
}
|
|
575
|
-
}
|
|
574
|
+
}))).filter(Boolean).length;
|
|
576
575
|
if (expiredCount > 0) console.error(`Cleaned up ${expiredCount} expired remote config cache entries`);
|
|
577
576
|
} catch (error) {
|
|
578
577
|
console.error("Failed to clean expired remote config cache:", error);
|
|
@@ -588,14 +587,15 @@ var RemoteConfigCacheService = class {
|
|
|
588
587
|
totalSize: 0
|
|
589
588
|
};
|
|
590
589
|
const jsonFiles = (await (0, node_fs_promises.readdir)(this.cacheDir)).filter((file) => file.endsWith(".json"));
|
|
591
|
-
|
|
592
|
-
for (const file of jsonFiles) {
|
|
590
|
+
const totalSize = (await Promise.all(jsonFiles.map(async (file) => {
|
|
593
591
|
const filePath = (0, node_path.join)(this.cacheDir, file);
|
|
594
592
|
try {
|
|
595
593
|
const content = await (0, node_fs_promises.readFile)(filePath, "utf-8");
|
|
596
|
-
|
|
597
|
-
} catch {
|
|
598
|
-
|
|
594
|
+
return Buffer.byteLength(content, "utf-8");
|
|
595
|
+
} catch {
|
|
596
|
+
return 0;
|
|
597
|
+
}
|
|
598
|
+
}))).reduce((sum, size) => sum + size, 0);
|
|
599
599
|
return {
|
|
600
600
|
totalEntries: jsonFiles.length,
|
|
601
601
|
totalSize
|
|
@@ -996,7 +996,10 @@ var McpClientManagerService = class {
|
|
|
996
996
|
const transport = new __modelcontextprotocol_sdk_client_stdio_js.StdioClientTransport({
|
|
997
997
|
command: config.command,
|
|
998
998
|
args: config.args,
|
|
999
|
-
env:
|
|
999
|
+
env: {
|
|
1000
|
+
...process.env,
|
|
1001
|
+
...config.env ?? {}
|
|
1002
|
+
}
|
|
1000
1003
|
});
|
|
1001
1004
|
await mcpClient["client"].connect(transport);
|
|
1002
1005
|
const childProcess = transport["_process"];
|
|
@@ -1416,13 +1419,13 @@ var SkillService = class {
|
|
|
1416
1419
|
if (this.cachedSkills !== null) return this.cachedSkills;
|
|
1417
1420
|
const skills = [];
|
|
1418
1421
|
const loadedSkillNames = /* @__PURE__ */ new Set();
|
|
1419
|
-
|
|
1422
|
+
const allDirSkills = await Promise.all(this.skillPaths.map(async (skillPath) => {
|
|
1420
1423
|
const skillsDir = (0, node_path.isAbsolute)(skillPath) ? skillPath : (0, node_path.join)(this.cwd, skillPath);
|
|
1421
|
-
|
|
1422
|
-
|
|
1423
|
-
|
|
1424
|
-
|
|
1425
|
-
|
|
1424
|
+
return this.loadSkillsFromDirectory(skillsDir, "project");
|
|
1425
|
+
}));
|
|
1426
|
+
for (const dirSkills of allDirSkills) for (const skill of dirSkills) if (!loadedSkillNames.has(skill.name)) {
|
|
1427
|
+
skills.push(skill);
|
|
1428
|
+
loadedSkillNames.add(skill.name);
|
|
1426
1429
|
}
|
|
1427
1430
|
this.cachedSkills = skills;
|
|
1428
1431
|
this.skillsByName = new Map(skills.map((skill) => [skill.name, skill]));
|
|
@@ -1460,9 +1463,15 @@ var SkillService = class {
|
|
|
1460
1463
|
*/
|
|
1461
1464
|
async startWatching() {
|
|
1462
1465
|
this.stopWatching();
|
|
1463
|
-
|
|
1466
|
+
const existenceChecks = await Promise.all(this.skillPaths.map(async (skillPath) => {
|
|
1464
1467
|
const skillsDir = (0, node_path.isAbsolute)(skillPath) ? skillPath : (0, node_path.join)(this.cwd, skillPath);
|
|
1465
|
-
|
|
1468
|
+
return {
|
|
1469
|
+
skillsDir,
|
|
1470
|
+
exists: await pathExists(skillsDir)
|
|
1471
|
+
};
|
|
1472
|
+
}));
|
|
1473
|
+
for (const { skillsDir, exists } of existenceChecks) {
|
|
1474
|
+
if (!exists) continue;
|
|
1466
1475
|
const abortController = new AbortController();
|
|
1467
1476
|
this.watchers.push(abortController);
|
|
1468
1477
|
this.watchDirectory(skillsDir, abortController.signal).catch((error) => {
|
|
@@ -1520,34 +1529,49 @@ var SkillService = class {
|
|
|
1520
1529
|
} catch (error) {
|
|
1521
1530
|
throw new SkillLoadError(`Failed to read skills directory: ${error instanceof Error ? error.message : "Unknown error"}`, dirPath, error instanceof Error ? error : void 0);
|
|
1522
1531
|
}
|
|
1523
|
-
|
|
1532
|
+
const entryStats = await Promise.all(entries.map(async (entry) => {
|
|
1524
1533
|
const entryPath = (0, node_path.join)(dirPath, entry);
|
|
1525
|
-
let entryStat;
|
|
1526
1534
|
try {
|
|
1527
|
-
|
|
1535
|
+
return {
|
|
1536
|
+
entry,
|
|
1537
|
+
entryPath,
|
|
1538
|
+
stat: await (0, node_fs_promises.stat)(entryPath),
|
|
1539
|
+
error: null
|
|
1540
|
+
};
|
|
1528
1541
|
} catch (error) {
|
|
1529
1542
|
console.warn(`Skipping entry ${entryPath}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1530
|
-
|
|
1543
|
+
return {
|
|
1544
|
+
entry,
|
|
1545
|
+
entryPath,
|
|
1546
|
+
stat: null,
|
|
1547
|
+
error
|
|
1548
|
+
};
|
|
1531
1549
|
}
|
|
1550
|
+
}));
|
|
1551
|
+
const skillFilesToLoad = [];
|
|
1552
|
+
for (const { entry, entryPath, stat: entryStat } of entryStats) {
|
|
1553
|
+
if (!entryStat) continue;
|
|
1532
1554
|
if (entryStat.isDirectory()) {
|
|
1533
1555
|
const skillFilePath = (0, node_path.join)(entryPath, "SKILL.md");
|
|
1534
|
-
|
|
1535
|
-
|
|
1536
|
-
|
|
1537
|
-
|
|
1538
|
-
|
|
1539
|
-
|
|
1540
|
-
|
|
1541
|
-
|
|
1542
|
-
|
|
1543
|
-
|
|
1544
|
-
|
|
1545
|
-
if (
|
|
1556
|
+
skillFilesToLoad.push({
|
|
1557
|
+
filePath: skillFilePath,
|
|
1558
|
+
isRootLevel: false
|
|
1559
|
+
});
|
|
1560
|
+
} else if (entry === "SKILL.md") skillFilesToLoad.push({
|
|
1561
|
+
filePath: entryPath,
|
|
1562
|
+
isRootLevel: true
|
|
1563
|
+
});
|
|
1564
|
+
}
|
|
1565
|
+
const loadResults = await Promise.all(skillFilesToLoad.map(async ({ filePath, isRootLevel }) => {
|
|
1566
|
+
try {
|
|
1567
|
+
if (!isRootLevel && !await pathExists(filePath)) return null;
|
|
1568
|
+
return await this.loadSkillFile(filePath, location);
|
|
1546
1569
|
} catch (error) {
|
|
1547
|
-
console.warn(`Skipping skill at ${
|
|
1548
|
-
|
|
1570
|
+
console.warn(`Skipping skill at ${filePath}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1571
|
+
return null;
|
|
1549
1572
|
}
|
|
1550
|
-
}
|
|
1573
|
+
}));
|
|
1574
|
+
for (const skill of loadResults) if (skill) skills.push(skill);
|
|
1551
1575
|
return skills;
|
|
1552
1576
|
}
|
|
1553
1577
|
/**
|
|
@@ -1689,44 +1713,42 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
1689
1713
|
async detectSkillsFromPromptFrontMatter() {
|
|
1690
1714
|
if (this.autoDetectedSkillsCache !== null) return this.autoDetectedSkillsCache;
|
|
1691
1715
|
const clients = this.clientManager.getAllClients();
|
|
1692
|
-
const autoDetectedSkills = [];
|
|
1693
1716
|
let listPromptsFailures = 0;
|
|
1694
1717
|
let fetchPromptFailures = 0;
|
|
1695
|
-
const
|
|
1696
|
-
|
|
1718
|
+
const autoDetectedSkills = (await Promise.all(clients.map(async (client) => {
|
|
1719
|
+
const detectedSkills = [];
|
|
1697
1720
|
const configuredPromptNames = new Set(client.prompts ? Object.keys(client.prompts) : []);
|
|
1698
|
-
|
|
1699
|
-
|
|
1700
|
-
|
|
1701
|
-
|
|
1702
|
-
|
|
1703
|
-
|
|
1704
|
-
|
|
1705
|
-
const
|
|
1706
|
-
|
|
1707
|
-
|
|
1708
|
-
|
|
1709
|
-
|
|
1710
|
-
|
|
1711
|
-
|
|
1712
|
-
|
|
1713
|
-
|
|
1714
|
-
|
|
1715
|
-
|
|
1716
|
-
|
|
1717
|
-
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
}
|
|
1721
|
-
|
|
1722
|
-
|
|
1723
|
-
|
|
1724
|
-
|
|
1725
|
-
}
|
|
1726
|
-
}
|
|
1727
|
-
|
|
1728
|
-
}
|
|
1729
|
-
await Promise.all(fetchPromises);
|
|
1721
|
+
try {
|
|
1722
|
+
const prompts = await client.listPrompts();
|
|
1723
|
+
if (!prompts || prompts.length === 0) return detectedSkills;
|
|
1724
|
+
const promptResults = await Promise.all(prompts.map(async (promptInfo) => {
|
|
1725
|
+
if (configuredPromptNames.has(promptInfo.name)) return null;
|
|
1726
|
+
try {
|
|
1727
|
+
const skillExtraction = extractSkillFrontMatter(((await client.getPrompt(promptInfo.name)).messages || []).map((m) => {
|
|
1728
|
+
const content = m.content;
|
|
1729
|
+
if (typeof content === "string") return content;
|
|
1730
|
+
if (content && typeof content === "object" && "text" in content) return String(content.text);
|
|
1731
|
+
return "";
|
|
1732
|
+
}).join("\n"));
|
|
1733
|
+
if (skillExtraction) return {
|
|
1734
|
+
serverName: client.serverName,
|
|
1735
|
+
promptName: promptInfo.name,
|
|
1736
|
+
skill: skillExtraction.skill
|
|
1737
|
+
};
|
|
1738
|
+
return null;
|
|
1739
|
+
} catch (error) {
|
|
1740
|
+
fetchPromptFailures++;
|
|
1741
|
+
console.error(`${LOG_PREFIX_SKILL_DETECTION} Failed to fetch prompt '${promptInfo.name}' from ${client.serverName}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1742
|
+
return null;
|
|
1743
|
+
}
|
|
1744
|
+
}));
|
|
1745
|
+
for (const result of promptResults) if (result) detectedSkills.push(result);
|
|
1746
|
+
} catch (error) {
|
|
1747
|
+
listPromptsFailures++;
|
|
1748
|
+
console.error(`${LOG_PREFIX_SKILL_DETECTION} Failed to list prompts from ${client.serverName}: ${error instanceof Error ? error.message : "Unknown error"}`);
|
|
1749
|
+
}
|
|
1750
|
+
return detectedSkills;
|
|
1751
|
+
}))).flat();
|
|
1730
1752
|
if (listPromptsFailures > 0 || fetchPromptFailures > 0) console.error(`${LOG_PREFIX_SKILL_DETECTION} Completed with ${listPromptsFailures} server failure(s) and ${fetchPromptFailures} prompt failure(s). Detected ${autoDetectedSkills.length} skill(s).`);
|
|
1731
1753
|
this.autoDetectedSkillsCache = autoDetectedSkills;
|
|
1732
1754
|
return autoDetectedSkills;
|
|
@@ -1977,40 +1999,42 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
1977
1999
|
serverToolsMap.set(client.serverName, []);
|
|
1978
2000
|
}
|
|
1979
2001
|
}));
|
|
1980
|
-
const
|
|
1981
|
-
|
|
1982
|
-
|
|
1983
|
-
|
|
2002
|
+
const lookupResults = await Promise.all(toolNames.map(async (requestedName) => {
|
|
2003
|
+
const result$1 = {
|
|
2004
|
+
tools: [],
|
|
2005
|
+
skills: [],
|
|
2006
|
+
notFound: null
|
|
2007
|
+
};
|
|
1984
2008
|
if (requestedName.startsWith(SKILL_PREFIX)) {
|
|
1985
2009
|
const skillName = requestedName.slice(SKILL_PREFIX.length);
|
|
1986
2010
|
if (this.skillService) {
|
|
1987
2011
|
const skill = await this.skillService.getSkill(skillName);
|
|
1988
2012
|
if (skill) {
|
|
1989
|
-
|
|
2013
|
+
result$1.skills.push({
|
|
1990
2014
|
name: skill.name,
|
|
1991
2015
|
location: skill.basePath,
|
|
1992
2016
|
instructions: formatSkillInstructions(skill.name, skill.content)
|
|
1993
2017
|
});
|
|
1994
|
-
|
|
2018
|
+
return result$1;
|
|
1995
2019
|
}
|
|
1996
2020
|
}
|
|
1997
2021
|
const promptSkillContent = await this.getPromptSkillContent(skillName);
|
|
1998
2022
|
if (promptSkillContent) {
|
|
1999
|
-
|
|
2000
|
-
|
|
2023
|
+
result$1.skills.push(promptSkillContent);
|
|
2024
|
+
return result$1;
|
|
2001
2025
|
}
|
|
2002
|
-
|
|
2003
|
-
|
|
2026
|
+
result$1.notFound = requestedName;
|
|
2027
|
+
return result$1;
|
|
2004
2028
|
}
|
|
2005
2029
|
const { serverName, actualToolName } = parseToolName(requestedName);
|
|
2006
2030
|
if (serverName) {
|
|
2007
2031
|
const serverTools = serverToolsMap.get(serverName);
|
|
2008
2032
|
if (!serverTools) {
|
|
2009
|
-
|
|
2010
|
-
|
|
2033
|
+
result$1.notFound = requestedName;
|
|
2034
|
+
return result$1;
|
|
2011
2035
|
}
|
|
2012
2036
|
const tool = serverTools.find((t) => t.name === actualToolName);
|
|
2013
|
-
if (tool)
|
|
2037
|
+
if (tool) result$1.tools.push({
|
|
2014
2038
|
server: serverName,
|
|
2015
2039
|
tool: {
|
|
2016
2040
|
name: tool.name,
|
|
@@ -2018,52 +2042,61 @@ var DescribeToolsTool = class DescribeToolsTool {
|
|
|
2018
2042
|
inputSchema: tool.inputSchema
|
|
2019
2043
|
}
|
|
2020
2044
|
});
|
|
2021
|
-
else
|
|
2022
|
-
|
|
2023
|
-
|
|
2024
|
-
|
|
2025
|
-
|
|
2026
|
-
|
|
2027
|
-
|
|
2028
|
-
|
|
2029
|
-
|
|
2030
|
-
|
|
2031
|
-
|
|
2032
|
-
|
|
2033
|
-
|
|
2034
|
-
|
|
2035
|
-
}
|
|
2036
|
-
const promptSkillContent = await this.getPromptSkillContent(actualToolName);
|
|
2037
|
-
if (promptSkillContent) {
|
|
2038
|
-
foundSkills.push(promptSkillContent);
|
|
2039
|
-
continue;
|
|
2045
|
+
else result$1.notFound = requestedName;
|
|
2046
|
+
return result$1;
|
|
2047
|
+
}
|
|
2048
|
+
const servers = toolToServers.get(actualToolName);
|
|
2049
|
+
if (!servers || servers.length === 0) {
|
|
2050
|
+
if (this.skillService) {
|
|
2051
|
+
const skill = await this.skillService.getSkill(actualToolName);
|
|
2052
|
+
if (skill) {
|
|
2053
|
+
result$1.skills.push({
|
|
2054
|
+
name: skill.name,
|
|
2055
|
+
location: skill.basePath,
|
|
2056
|
+
instructions: formatSkillInstructions(skill.name, skill.content)
|
|
2057
|
+
});
|
|
2058
|
+
return result$1;
|
|
2040
2059
|
}
|
|
2041
|
-
notFoundItems.push(requestedName);
|
|
2042
|
-
continue;
|
|
2043
2060
|
}
|
|
2044
|
-
|
|
2045
|
-
|
|
2046
|
-
|
|
2047
|
-
|
|
2048
|
-
server,
|
|
2049
|
-
tool: {
|
|
2050
|
-
name: tool.name,
|
|
2051
|
-
description: tool.description,
|
|
2052
|
-
inputSchema: tool.inputSchema
|
|
2053
|
-
}
|
|
2054
|
-
});
|
|
2055
|
-
} else for (const server of servers) {
|
|
2056
|
-
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2057
|
-
foundTools.push({
|
|
2058
|
-
server,
|
|
2059
|
-
tool: {
|
|
2060
|
-
name: tool.name,
|
|
2061
|
-
description: tool.description,
|
|
2062
|
-
inputSchema: tool.inputSchema
|
|
2063
|
-
}
|
|
2064
|
-
});
|
|
2061
|
+
const promptSkillContent = await this.getPromptSkillContent(actualToolName);
|
|
2062
|
+
if (promptSkillContent) {
|
|
2063
|
+
result$1.skills.push(promptSkillContent);
|
|
2064
|
+
return result$1;
|
|
2065
2065
|
}
|
|
2066
|
+
result$1.notFound = requestedName;
|
|
2067
|
+
return result$1;
|
|
2066
2068
|
}
|
|
2069
|
+
if (servers.length === 1) {
|
|
2070
|
+
const server = servers[0];
|
|
2071
|
+
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2072
|
+
result$1.tools.push({
|
|
2073
|
+
server,
|
|
2074
|
+
tool: {
|
|
2075
|
+
name: tool.name,
|
|
2076
|
+
description: tool.description,
|
|
2077
|
+
inputSchema: tool.inputSchema
|
|
2078
|
+
}
|
|
2079
|
+
});
|
|
2080
|
+
} else for (const server of servers) {
|
|
2081
|
+
const tool = serverToolsMap.get(server).find((t) => t.name === actualToolName);
|
|
2082
|
+
result$1.tools.push({
|
|
2083
|
+
server,
|
|
2084
|
+
tool: {
|
|
2085
|
+
name: tool.name,
|
|
2086
|
+
description: tool.description,
|
|
2087
|
+
inputSchema: tool.inputSchema
|
|
2088
|
+
}
|
|
2089
|
+
});
|
|
2090
|
+
}
|
|
2091
|
+
return result$1;
|
|
2092
|
+
}));
|
|
2093
|
+
const foundTools = [];
|
|
2094
|
+
const foundSkills = [];
|
|
2095
|
+
const notFoundItems = [];
|
|
2096
|
+
for (const result$1 of lookupResults) {
|
|
2097
|
+
foundTools.push(...result$1.tools);
|
|
2098
|
+
foundSkills.push(...result$1.skills);
|
|
2099
|
+
if (result$1.notFound) notFoundItems.push(result$1.notFound);
|
|
2067
2100
|
}
|
|
2068
2101
|
if (foundTools.length === 0 && foundSkills.length === 0) return {
|
|
2069
2102
|
content: [{
|
package/dist/index.cjs
CHANGED
package/dist/index.mjs
CHANGED
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { i as createServer, n as SseTransportHandler, r as StdioTransportHandler, t as HttpTransportHandler } from "./http-
|
|
1
|
+
import { i as createServer, n as SseTransportHandler, r as StdioTransportHandler, t as HttpTransportHandler } from "./http-DEoeeLtl.mjs";
|
|
2
2
|
|
|
3
3
|
export { HttpTransportHandler, SseTransportHandler, StdioTransportHandler, createServer };
|