@wundr.io/mcp-registry 1.0.3
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/README.md +890 -0
- package/dist/aggregator.d.ts +330 -0
- package/dist/aggregator.d.ts.map +1 -0
- package/dist/aggregator.js +708 -0
- package/dist/aggregator.js.map +1 -0
- package/dist/discovery.d.ts +274 -0
- package/dist/discovery.d.ts.map +1 -0
- package/dist/discovery.js +536 -0
- package/dist/discovery.js.map +1 -0
- package/dist/health-monitor.d.ts +304 -0
- package/dist/health-monitor.d.ts.map +1 -0
- package/dist/health-monitor.js +626 -0
- package/dist/health-monitor.js.map +1 -0
- package/dist/index.d.ts +109 -0
- package/dist/index.d.ts.map +1 -0
- package/dist/index.js +185 -0
- package/dist/index.js.map +1 -0
- package/dist/registry.d.ts +323 -0
- package/dist/registry.d.ts.map +1 -0
- package/dist/registry.js +647 -0
- package/dist/registry.js.map +1 -0
- package/dist/types.d.ts +663 -0
- package/dist/types.d.ts.map +1 -0
- package/dist/types.js +120 -0
- package/dist/types.js.map +1 -0
- package/package.json +71 -0
|
@@ -0,0 +1,536 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
/**
|
|
3
|
+
* @wundr.io/mcp-registry - Dynamic Server Discovery
|
|
4
|
+
*
|
|
5
|
+
* Provides capability-based server discovery, query building,
|
|
6
|
+
* and intelligent server selection algorithms.
|
|
7
|
+
*
|
|
8
|
+
* @packageDocumentation
|
|
9
|
+
*/
|
|
10
|
+
Object.defineProperty(exports, "__esModule", { value: true });
|
|
11
|
+
exports.ServerDiscoveryService = exports.CapabilityQueryBuilder = exports.InvalidQueryError = exports.NoServersFoundError = void 0;
|
|
12
|
+
exports.createServerDiscoveryService = createServerDiscoveryService;
|
|
13
|
+
const types_1 = require("./types");
|
|
14
|
+
// =============================================================================
|
|
15
|
+
// Discovery Error Types
|
|
16
|
+
// =============================================================================
|
|
17
|
+
/**
|
|
18
|
+
* Error thrown when no servers match a discovery query
|
|
19
|
+
*/
|
|
20
|
+
class NoServersFoundError extends Error {
|
|
21
|
+
query;
|
|
22
|
+
constructor(query, message) {
|
|
23
|
+
super(message ?? 'No servers found matching the query');
|
|
24
|
+
this.query = query;
|
|
25
|
+
this.name = 'NoServersFoundError';
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
exports.NoServersFoundError = NoServersFoundError;
|
|
29
|
+
/**
|
|
30
|
+
* Error thrown when a discovery query is invalid
|
|
31
|
+
*/
|
|
32
|
+
class InvalidQueryError extends Error {
|
|
33
|
+
validationErrors;
|
|
34
|
+
constructor(validationErrors, message) {
|
|
35
|
+
super(message ?? `Invalid query: ${validationErrors.join(', ')}`);
|
|
36
|
+
this.validationErrors = validationErrors;
|
|
37
|
+
this.name = 'InvalidQueryError';
|
|
38
|
+
}
|
|
39
|
+
}
|
|
40
|
+
exports.InvalidQueryError = InvalidQueryError;
|
|
41
|
+
// =============================================================================
|
|
42
|
+
// Query Builder
|
|
43
|
+
// =============================================================================
|
|
44
|
+
/**
|
|
45
|
+
* Fluent builder for creating capability queries
|
|
46
|
+
*
|
|
47
|
+
* @example
|
|
48
|
+
* ```typescript
|
|
49
|
+
* const query = new CapabilityQueryBuilder()
|
|
50
|
+
* .withCategory('tools')
|
|
51
|
+
* .withTools(['drift_detection', 'governance_report'])
|
|
52
|
+
* .withMinPriority(5)
|
|
53
|
+
* .withHealthStatus('healthy')
|
|
54
|
+
* .build();
|
|
55
|
+
* ```
|
|
56
|
+
*/
|
|
57
|
+
class CapabilityQueryBuilder {
|
|
58
|
+
category;
|
|
59
|
+
capabilities = [];
|
|
60
|
+
tools = [];
|
|
61
|
+
tags = [];
|
|
62
|
+
minPriority;
|
|
63
|
+
healthStatus;
|
|
64
|
+
/**
|
|
65
|
+
* Set the capability category filter
|
|
66
|
+
*
|
|
67
|
+
* @param category - Capability category
|
|
68
|
+
* @returns This builder for chaining
|
|
69
|
+
*/
|
|
70
|
+
withCategory(category) {
|
|
71
|
+
this.category = category;
|
|
72
|
+
return this;
|
|
73
|
+
}
|
|
74
|
+
/**
|
|
75
|
+
* Add required capabilities
|
|
76
|
+
*
|
|
77
|
+
* @param capabilities - Capability names
|
|
78
|
+
* @returns This builder for chaining
|
|
79
|
+
*/
|
|
80
|
+
withCapabilities(capabilities) {
|
|
81
|
+
this.capabilities.push(...capabilities);
|
|
82
|
+
return this;
|
|
83
|
+
}
|
|
84
|
+
/**
|
|
85
|
+
* Add a single required capability
|
|
86
|
+
*
|
|
87
|
+
* @param capability - Capability name
|
|
88
|
+
* @returns This builder for chaining
|
|
89
|
+
*/
|
|
90
|
+
withCapability(capability) {
|
|
91
|
+
this.capabilities.push(capability);
|
|
92
|
+
return this;
|
|
93
|
+
}
|
|
94
|
+
/**
|
|
95
|
+
* Add required tools
|
|
96
|
+
*
|
|
97
|
+
* @param tools - Tool names
|
|
98
|
+
* @returns This builder for chaining
|
|
99
|
+
*/
|
|
100
|
+
withTools(tools) {
|
|
101
|
+
this.tools.push(...tools);
|
|
102
|
+
return this;
|
|
103
|
+
}
|
|
104
|
+
/**
|
|
105
|
+
* Add a single required tool
|
|
106
|
+
*
|
|
107
|
+
* @param tool - Tool name
|
|
108
|
+
* @returns This builder for chaining
|
|
109
|
+
*/
|
|
110
|
+
withTool(tool) {
|
|
111
|
+
this.tools.push(tool);
|
|
112
|
+
return this;
|
|
113
|
+
}
|
|
114
|
+
/**
|
|
115
|
+
* Add required tags
|
|
116
|
+
*
|
|
117
|
+
* @param tags - Tag names
|
|
118
|
+
* @returns This builder for chaining
|
|
119
|
+
*/
|
|
120
|
+
withTags(tags) {
|
|
121
|
+
this.tags.push(...tags);
|
|
122
|
+
return this;
|
|
123
|
+
}
|
|
124
|
+
/**
|
|
125
|
+
* Add a single required tag
|
|
126
|
+
*
|
|
127
|
+
* @param tag - Tag name
|
|
128
|
+
* @returns This builder for chaining
|
|
129
|
+
*/
|
|
130
|
+
withTag(tag) {
|
|
131
|
+
this.tags.push(tag);
|
|
132
|
+
return this;
|
|
133
|
+
}
|
|
134
|
+
/**
|
|
135
|
+
* Set minimum priority filter
|
|
136
|
+
*
|
|
137
|
+
* @param priority - Minimum priority value
|
|
138
|
+
* @returns This builder for chaining
|
|
139
|
+
*/
|
|
140
|
+
withMinPriority(priority) {
|
|
141
|
+
this.minPriority = priority;
|
|
142
|
+
return this;
|
|
143
|
+
}
|
|
144
|
+
/**
|
|
145
|
+
* Set health status filter
|
|
146
|
+
*
|
|
147
|
+
* @param status - Required health status(es)
|
|
148
|
+
* @returns This builder for chaining
|
|
149
|
+
*/
|
|
150
|
+
withHealthStatus(status) {
|
|
151
|
+
this.healthStatus = status;
|
|
152
|
+
return this;
|
|
153
|
+
}
|
|
154
|
+
/**
|
|
155
|
+
* Build the query
|
|
156
|
+
*
|
|
157
|
+
* @returns The constructed capability query
|
|
158
|
+
* @throws {InvalidQueryError} If the query is invalid
|
|
159
|
+
*/
|
|
160
|
+
build() {
|
|
161
|
+
const query = {
|
|
162
|
+
category: this.category,
|
|
163
|
+
capabilities: this.capabilities.length > 0 ? this.capabilities : undefined,
|
|
164
|
+
tools: this.tools.length > 0 ? this.tools : undefined,
|
|
165
|
+
tags: this.tags.length > 0 ? this.tags : undefined,
|
|
166
|
+
minPriority: this.minPriority,
|
|
167
|
+
healthStatus: this.healthStatus,
|
|
168
|
+
};
|
|
169
|
+
// Validate the query
|
|
170
|
+
const validation = types_1.CapabilityQuerySchema.safeParse(query);
|
|
171
|
+
if (!validation.success) {
|
|
172
|
+
const errors = validation.error.errors.map(e => `${e.path.join('.')}: ${e.message}`);
|
|
173
|
+
throw new InvalidQueryError(errors);
|
|
174
|
+
}
|
|
175
|
+
return query;
|
|
176
|
+
}
|
|
177
|
+
/**
|
|
178
|
+
* Reset the builder
|
|
179
|
+
*
|
|
180
|
+
* @returns This builder for chaining
|
|
181
|
+
*/
|
|
182
|
+
reset() {
|
|
183
|
+
this.category = undefined;
|
|
184
|
+
this.capabilities = [];
|
|
185
|
+
this.tools = [];
|
|
186
|
+
this.tags = [];
|
|
187
|
+
this.minPriority = undefined;
|
|
188
|
+
this.healthStatus = undefined;
|
|
189
|
+
return this;
|
|
190
|
+
}
|
|
191
|
+
}
|
|
192
|
+
exports.CapabilityQueryBuilder = CapabilityQueryBuilder;
|
|
193
|
+
/**
|
|
194
|
+
* Server Discovery Service
|
|
195
|
+
*
|
|
196
|
+
* Provides dynamic server discovery based on capabilities,
|
|
197
|
+
* tools, tags, and health status.
|
|
198
|
+
*
|
|
199
|
+
* @example
|
|
200
|
+
* ```typescript
|
|
201
|
+
* const discovery = new ServerDiscoveryService(registry);
|
|
202
|
+
*
|
|
203
|
+
* // Find servers with specific tools
|
|
204
|
+
* const result = await discovery.discover({
|
|
205
|
+
* tools: ['drift_detection'],
|
|
206
|
+
* healthStatus: 'healthy',
|
|
207
|
+
* });
|
|
208
|
+
*
|
|
209
|
+
* // Use query builder
|
|
210
|
+
* const query = discovery.queryBuilder()
|
|
211
|
+
* .withCategory('tools')
|
|
212
|
+
* .withMinPriority(5)
|
|
213
|
+
* .build();
|
|
214
|
+
*
|
|
215
|
+
* const servers = await discovery.discover(query);
|
|
216
|
+
* ```
|
|
217
|
+
*/
|
|
218
|
+
class ServerDiscoveryService {
|
|
219
|
+
registry;
|
|
220
|
+
/**
|
|
221
|
+
* Creates a new ServerDiscoveryService
|
|
222
|
+
*
|
|
223
|
+
* @param registry - The server registry to search
|
|
224
|
+
*/
|
|
225
|
+
constructor(registry) {
|
|
226
|
+
this.registry = registry;
|
|
227
|
+
}
|
|
228
|
+
/**
|
|
229
|
+
* Create a new query builder
|
|
230
|
+
*
|
|
231
|
+
* @returns A new CapabilityQueryBuilder instance
|
|
232
|
+
*/
|
|
233
|
+
queryBuilder() {
|
|
234
|
+
return new CapabilityQueryBuilder();
|
|
235
|
+
}
|
|
236
|
+
/**
|
|
237
|
+
* Discover servers matching a query
|
|
238
|
+
*
|
|
239
|
+
* @param query - The capability query
|
|
240
|
+
* @param options - Discovery options
|
|
241
|
+
* @returns Discovery result with matching servers
|
|
242
|
+
*/
|
|
243
|
+
async discover(query, options = {}) {
|
|
244
|
+
const allServers = this.registry.getAll();
|
|
245
|
+
let matchingServers = this.filterServers(allServers, query, options);
|
|
246
|
+
// Sort results
|
|
247
|
+
matchingServers = this.sortServers(matchingServers, options);
|
|
248
|
+
// Apply limit
|
|
249
|
+
if (options.limit !== undefined && options.limit > 0) {
|
|
250
|
+
matchingServers = matchingServers.slice(0, options.limit);
|
|
251
|
+
}
|
|
252
|
+
return {
|
|
253
|
+
servers: matchingServers,
|
|
254
|
+
query,
|
|
255
|
+
timestamp: new Date(),
|
|
256
|
+
totalSearched: allServers.length,
|
|
257
|
+
matchCount: matchingServers.length,
|
|
258
|
+
};
|
|
259
|
+
}
|
|
260
|
+
/**
|
|
261
|
+
* Find the best server for a specific tool
|
|
262
|
+
*
|
|
263
|
+
* @param toolName - The tool name to find
|
|
264
|
+
* @returns The best server for the tool, or undefined
|
|
265
|
+
*/
|
|
266
|
+
async findBestServerForTool(toolName) {
|
|
267
|
+
const servers = this.registry.findByTool(toolName);
|
|
268
|
+
if (servers.length === 0) {
|
|
269
|
+
return undefined;
|
|
270
|
+
}
|
|
271
|
+
// Filter to healthy servers first
|
|
272
|
+
let candidates = servers.filter(server => {
|
|
273
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
274
|
+
return health?.status === 'healthy';
|
|
275
|
+
});
|
|
276
|
+
// Fall back to degraded servers if no healthy ones
|
|
277
|
+
if (candidates.length === 0) {
|
|
278
|
+
candidates = servers.filter(server => {
|
|
279
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
280
|
+
return health?.status === 'degraded';
|
|
281
|
+
});
|
|
282
|
+
}
|
|
283
|
+
// Fall back to all servers if none healthy/degraded
|
|
284
|
+
if (candidates.length === 0) {
|
|
285
|
+
candidates = [...servers];
|
|
286
|
+
}
|
|
287
|
+
// Sort by priority (descending) then by latency (ascending)
|
|
288
|
+
return this.sortServers(candidates, {
|
|
289
|
+
sortBy: 'priority',
|
|
290
|
+
sortOrder: 'desc',
|
|
291
|
+
})[0];
|
|
292
|
+
}
|
|
293
|
+
/**
|
|
294
|
+
* Find all servers that can handle a set of tools
|
|
295
|
+
*
|
|
296
|
+
* @param toolNames - Tool names to find
|
|
297
|
+
* @returns Servers that provide all specified tools
|
|
298
|
+
*/
|
|
299
|
+
async findServersForTools(toolNames) {
|
|
300
|
+
if (toolNames.length === 0) {
|
|
301
|
+
return [];
|
|
302
|
+
}
|
|
303
|
+
// Get servers for each tool
|
|
304
|
+
const serverSets = toolNames.map(name => new Set(this.registry.findByTool(name).map(s => s.id)));
|
|
305
|
+
// Find intersection of all sets
|
|
306
|
+
const intersection = serverSets.reduce((acc, set) => {
|
|
307
|
+
return new Set([...acc].filter(id => set.has(id)));
|
|
308
|
+
});
|
|
309
|
+
// Get server registrations
|
|
310
|
+
return Array.from(intersection)
|
|
311
|
+
.map(id => this.registry.get(id))
|
|
312
|
+
.filter((server) => server !== undefined);
|
|
313
|
+
}
|
|
314
|
+
/**
|
|
315
|
+
* Get server recommendations based on current usage patterns
|
|
316
|
+
*
|
|
317
|
+
* @param context - Usage context for recommendations
|
|
318
|
+
* @returns Recommended servers sorted by relevance
|
|
319
|
+
*/
|
|
320
|
+
async getRecommendations(context) {
|
|
321
|
+
const allServers = this.registry.getAll();
|
|
322
|
+
const recommendations = [];
|
|
323
|
+
for (const server of allServers) {
|
|
324
|
+
const score = this.calculateRecommendationScore(server, context);
|
|
325
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
326
|
+
recommendations.push({
|
|
327
|
+
server,
|
|
328
|
+
score,
|
|
329
|
+
reasons: this.getRecommendationReasons(server, context, score),
|
|
330
|
+
healthStatus: health?.status ?? 'unknown',
|
|
331
|
+
});
|
|
332
|
+
}
|
|
333
|
+
// Sort by score descending
|
|
334
|
+
return recommendations.sort((a, b) => b.score - a.score);
|
|
335
|
+
}
|
|
336
|
+
// ===========================================================================
|
|
337
|
+
// Private Helper Methods
|
|
338
|
+
// ===========================================================================
|
|
339
|
+
/**
|
|
340
|
+
* Filter servers based on query criteria
|
|
341
|
+
*/
|
|
342
|
+
filterServers(servers, query, options) {
|
|
343
|
+
return servers.filter(server => {
|
|
344
|
+
// Filter by capability category
|
|
345
|
+
if (query.category !== undefined) {
|
|
346
|
+
const hasCategory = server.capabilities.some(cap => cap.category === query.category && cap.enabled);
|
|
347
|
+
if (!hasCategory) {
|
|
348
|
+
return false;
|
|
349
|
+
}
|
|
350
|
+
}
|
|
351
|
+
// Filter by capability names
|
|
352
|
+
if (query.capabilities !== undefined && query.capabilities.length > 0) {
|
|
353
|
+
const serverCapNames = new Set(server.capabilities.filter(c => c.enabled).map(c => c.name));
|
|
354
|
+
const hasAllCaps = query.capabilities.every(cap => serverCapNames.has(cap));
|
|
355
|
+
if (!hasAllCaps) {
|
|
356
|
+
return false;
|
|
357
|
+
}
|
|
358
|
+
}
|
|
359
|
+
// Filter by tools
|
|
360
|
+
if (query.tools !== undefined && query.tools.length > 0) {
|
|
361
|
+
const serverToolNames = new Set(server.tools.map(t => t.name));
|
|
362
|
+
const hasAllTools = query.tools.every(tool => serverToolNames.has(tool));
|
|
363
|
+
if (!hasAllTools) {
|
|
364
|
+
return false;
|
|
365
|
+
}
|
|
366
|
+
}
|
|
367
|
+
// Filter by tags
|
|
368
|
+
if (query.tags !== undefined && query.tags.length > 0) {
|
|
369
|
+
const serverTags = new Set(server.tags);
|
|
370
|
+
const hasAllTags = query.tags.every(tag => serverTags.has(tag));
|
|
371
|
+
if (!hasAllTags) {
|
|
372
|
+
return false;
|
|
373
|
+
}
|
|
374
|
+
}
|
|
375
|
+
// Filter by minimum priority
|
|
376
|
+
if (query.minPriority !== undefined) {
|
|
377
|
+
if ((server.priority ?? 0) < query.minPriority) {
|
|
378
|
+
return false;
|
|
379
|
+
}
|
|
380
|
+
}
|
|
381
|
+
// Filter by health status
|
|
382
|
+
if (query.healthStatus !== undefined) {
|
|
383
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
384
|
+
const serverHealth = health?.status ?? 'unknown';
|
|
385
|
+
// Handle unknown health if option is set
|
|
386
|
+
if (serverHealth === 'unknown' && !options.includeUnknownHealth) {
|
|
387
|
+
return false;
|
|
388
|
+
}
|
|
389
|
+
const allowedStatuses = Array.isArray(query.healthStatus)
|
|
390
|
+
? query.healthStatus
|
|
391
|
+
: [query.healthStatus];
|
|
392
|
+
if (!allowedStatuses.includes(serverHealth)) {
|
|
393
|
+
return false;
|
|
394
|
+
}
|
|
395
|
+
}
|
|
396
|
+
return true;
|
|
397
|
+
});
|
|
398
|
+
}
|
|
399
|
+
/**
|
|
400
|
+
* Sort servers based on options
|
|
401
|
+
*/
|
|
402
|
+
sortServers(servers, options) {
|
|
403
|
+
const sorted = [...servers];
|
|
404
|
+
const sortBy = options.sortBy ?? 'priority';
|
|
405
|
+
const sortOrder = options.sortOrder ?? 'desc';
|
|
406
|
+
sorted.sort((a, b) => {
|
|
407
|
+
let comparison = 0;
|
|
408
|
+
switch (sortBy) {
|
|
409
|
+
case 'priority':
|
|
410
|
+
comparison = (a.priority ?? 0) - (b.priority ?? 0);
|
|
411
|
+
break;
|
|
412
|
+
case 'name':
|
|
413
|
+
comparison = a.name.localeCompare(b.name);
|
|
414
|
+
break;
|
|
415
|
+
case 'registeredAt':
|
|
416
|
+
comparison = a.registeredAt.getTime() - b.registeredAt.getTime();
|
|
417
|
+
break;
|
|
418
|
+
case 'latency': {
|
|
419
|
+
const aHealth = this.registry.getHealthStatus(a.id);
|
|
420
|
+
const bHealth = this.registry.getHealthStatus(b.id);
|
|
421
|
+
const aLatency = aHealth?.latencyMs ?? Number.MAX_VALUE;
|
|
422
|
+
const bLatency = bHealth?.latencyMs ?? Number.MAX_VALUE;
|
|
423
|
+
comparison = aLatency - bLatency;
|
|
424
|
+
break;
|
|
425
|
+
}
|
|
426
|
+
}
|
|
427
|
+
return sortOrder === 'asc' ? comparison : -comparison;
|
|
428
|
+
});
|
|
429
|
+
return sorted;
|
|
430
|
+
}
|
|
431
|
+
/**
|
|
432
|
+
* Calculate recommendation score for a server
|
|
433
|
+
*/
|
|
434
|
+
calculateRecommendationScore(server, context) {
|
|
435
|
+
let score = 0;
|
|
436
|
+
// Base score from priority
|
|
437
|
+
score += (server.priority ?? 0) * 10;
|
|
438
|
+
// Health score
|
|
439
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
440
|
+
switch (health?.status) {
|
|
441
|
+
case 'healthy':
|
|
442
|
+
score += 50;
|
|
443
|
+
break;
|
|
444
|
+
case 'degraded':
|
|
445
|
+
score += 20;
|
|
446
|
+
break;
|
|
447
|
+
case 'unhealthy':
|
|
448
|
+
score -= 50;
|
|
449
|
+
break;
|
|
450
|
+
default:
|
|
451
|
+
score += 0;
|
|
452
|
+
}
|
|
453
|
+
// Latency score (lower is better)
|
|
454
|
+
if (health?.avgLatencyMs !== undefined) {
|
|
455
|
+
if (health.avgLatencyMs < 100) {
|
|
456
|
+
score += 30;
|
|
457
|
+
}
|
|
458
|
+
else if (health.avgLatencyMs < 500) {
|
|
459
|
+
score += 15;
|
|
460
|
+
}
|
|
461
|
+
else if (health.avgLatencyMs > 1000) {
|
|
462
|
+
score -= 10;
|
|
463
|
+
}
|
|
464
|
+
}
|
|
465
|
+
// Tool match score
|
|
466
|
+
if (context.preferredTools !== undefined) {
|
|
467
|
+
const serverToolNames = new Set(server.tools.map(t => t.name));
|
|
468
|
+
const matchingTools = context.preferredTools.filter(t => serverToolNames.has(t));
|
|
469
|
+
score += matchingTools.length * 15;
|
|
470
|
+
}
|
|
471
|
+
// Tag match score
|
|
472
|
+
if (context.preferredTags !== undefined) {
|
|
473
|
+
const serverTags = new Set(server.tags);
|
|
474
|
+
const matchingTags = context.preferredTags.filter(t => serverTags.has(t));
|
|
475
|
+
score += matchingTags.length * 10;
|
|
476
|
+
}
|
|
477
|
+
// Capability match score
|
|
478
|
+
if (context.requiredCapabilities !== undefined) {
|
|
479
|
+
const serverCapNames = new Set(server.capabilities.filter(c => c.enabled).map(c => c.name));
|
|
480
|
+
const matchingCaps = context.requiredCapabilities.filter(c => serverCapNames.has(c));
|
|
481
|
+
score += matchingCaps.length * 20;
|
|
482
|
+
}
|
|
483
|
+
// Error rate penalty
|
|
484
|
+
if (health?.errorRate !== undefined && health.errorRate > 0) {
|
|
485
|
+
score -= health.errorRate * 100;
|
|
486
|
+
}
|
|
487
|
+
return Math.max(0, score);
|
|
488
|
+
}
|
|
489
|
+
/**
|
|
490
|
+
* Get recommendation reasons for a server
|
|
491
|
+
*/
|
|
492
|
+
getRecommendationReasons(server, context, score) {
|
|
493
|
+
const reasons = [];
|
|
494
|
+
const health = this.registry.getHealthStatus(server.id);
|
|
495
|
+
if (health?.status === 'healthy') {
|
|
496
|
+
reasons.push('Server is healthy');
|
|
497
|
+
}
|
|
498
|
+
if ((server.priority ?? 0) >= 5) {
|
|
499
|
+
reasons.push('High priority server');
|
|
500
|
+
}
|
|
501
|
+
if (health?.avgLatencyMs !== undefined && health.avgLatencyMs < 100) {
|
|
502
|
+
reasons.push('Low latency');
|
|
503
|
+
}
|
|
504
|
+
if (context.preferredTools !== undefined) {
|
|
505
|
+
const serverToolNames = new Set(server.tools.map(t => t.name));
|
|
506
|
+
const matchingTools = context.preferredTools.filter(t => serverToolNames.has(t));
|
|
507
|
+
if (matchingTools.length > 0) {
|
|
508
|
+
reasons.push(`Provides ${matchingTools.length} preferred tool(s)`);
|
|
509
|
+
}
|
|
510
|
+
}
|
|
511
|
+
if (score >= 100) {
|
|
512
|
+
reasons.push('Highly recommended');
|
|
513
|
+
}
|
|
514
|
+
return reasons;
|
|
515
|
+
}
|
|
516
|
+
}
|
|
517
|
+
exports.ServerDiscoveryService = ServerDiscoveryService;
|
|
518
|
+
// =============================================================================
|
|
519
|
+
// Factory Function
|
|
520
|
+
// =============================================================================
|
|
521
|
+
/**
|
|
522
|
+
* Create a new ServerDiscoveryService
|
|
523
|
+
*
|
|
524
|
+
* @param registry - The server registry to search
|
|
525
|
+
* @returns New discovery service instance
|
|
526
|
+
*
|
|
527
|
+
* @example
|
|
528
|
+
* ```typescript
|
|
529
|
+
* const discovery = createServerDiscoveryService(registry);
|
|
530
|
+
* const result = await discovery.discover({ tools: ['my-tool'] });
|
|
531
|
+
* ```
|
|
532
|
+
*/
|
|
533
|
+
function createServerDiscoveryService(registry) {
|
|
534
|
+
return new ServerDiscoveryService(registry);
|
|
535
|
+
}
|
|
536
|
+
//# sourceMappingURL=discovery.js.map
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
{"version":3,"file":"discovery.js","sourceRoot":"","sources":["../src/discovery.ts"],"names":[],"mappings":"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"}
|