fastmcp 4.13.1 → 4.14.0
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 +46 -0
- package/dist/FastMCP.cjs +2 -2
- package/dist/FastMCP.d.cts +32 -1
- package/dist/FastMCP.d.ts +32 -1
- package/dist/FastMCP.js +1 -1
- package/dist/{chunk-3BMGHXXY.js → chunk-LMDMFMPI.js} +196 -142
- package/dist/chunk-LMDMFMPI.js.map +1 -0
- package/dist/{chunk-O72VCMGV.cjs → chunk-XK5NJ5W2.cjs} +226 -172
- package/dist/chunk-XK5NJ5W2.cjs.map +1 -0
- package/dist/examples/custom-routes.cjs +2 -2
- package/dist/examples/custom-routes.js +1 -1
- package/package.json +1 -1
- package/dist/chunk-3BMGHXXY.js.map +0 -1
- package/dist/chunk-O72VCMGV.cjs.map +0 -1
|
@@ -355,6 +355,8 @@ function assertToolSchemas(tool) {
|
|
|
355
355
|
assertStandardSchema(tool.name, "outputSchema", tool.outputSchema);
|
|
356
356
|
}
|
|
357
357
|
}
|
|
358
|
+
var STREAM_KEEPALIVE_LOGGER = "fastmcp-keepalive";
|
|
359
|
+
var STREAM_KEEPALIVE_DEFAULT_INTERVAL_MS = 2e4;
|
|
358
360
|
var TextContentZodSchema = _zod.z.object({
|
|
359
361
|
/**
|
|
360
362
|
* The text content of the message.
|
|
@@ -483,6 +485,7 @@ var FastMCPSession = class extends FastMCPSessionEventEmitter {
|
|
|
483
485
|
* instance — so capabilities can never be inferred here.
|
|
484
486
|
*/
|
|
485
487
|
#stateless;
|
|
488
|
+
#streamKeepaliveConfig;
|
|
486
489
|
/**
|
|
487
490
|
* Resource URIs the connected client has subscribed to via
|
|
488
491
|
* `resources/subscribe`. Used to scope `notifications/resources/updated`
|
|
@@ -503,6 +506,7 @@ var FastMCPSession = class extends FastMCPSessionEventEmitter {
|
|
|
503
506
|
roots,
|
|
504
507
|
sessionId,
|
|
505
508
|
stateless = false,
|
|
509
|
+
streamKeepalive,
|
|
506
510
|
tools,
|
|
507
511
|
transportType,
|
|
508
512
|
utils,
|
|
@@ -516,6 +520,7 @@ var FastMCPSession = class extends FastMCPSessionEventEmitter {
|
|
|
516
520
|
this.#rootsConfig = roots;
|
|
517
521
|
this.#sessionId = sessionId;
|
|
518
522
|
this.#stateless = stateless;
|
|
523
|
+
this.#streamKeepaliveConfig = streamKeepalive;
|
|
519
524
|
this.#needsEventLoopFlush = transportType === "httpStream";
|
|
520
525
|
if (tools.length) {
|
|
521
526
|
this.#capabilities.tools = {};
|
|
@@ -843,6 +848,44 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
843
848
|
logLevel: pingConfig.logLevel || "debug"
|
|
844
849
|
};
|
|
845
850
|
}
|
|
851
|
+
/**
|
|
852
|
+
* Periodically writes to the response stream of an in-flight tool call, so an
|
|
853
|
+
* idle-connection timeout (proxy, load balancer) does not close it while a
|
|
854
|
+
* long-running tool produces no output of its own.
|
|
855
|
+
*
|
|
856
|
+
* The notification is related to the tool call, so it travels on that
|
|
857
|
+
* request's own stream, which is the only server-to-client route that exists
|
|
858
|
+
* when running stateless.
|
|
859
|
+
*
|
|
860
|
+
* @returns a function that stops the keepalive.
|
|
861
|
+
*/
|
|
862
|
+
#startStreamKeepalive(extra, toolName) {
|
|
863
|
+
const config = this.#streamKeepaliveConfig;
|
|
864
|
+
if (!_optionalChain([config, 'optionalAccess', _21 => _21.enabled])) {
|
|
865
|
+
return () => {
|
|
866
|
+
};
|
|
867
|
+
}
|
|
868
|
+
const intervalMs = config.intervalMs && config.intervalMs > 0 ? config.intervalMs : STREAM_KEEPALIVE_DEFAULT_INTERVAL_MS;
|
|
869
|
+
const timer = setInterval(() => {
|
|
870
|
+
extra.sendNotification({
|
|
871
|
+
method: "notifications/message",
|
|
872
|
+
params: {
|
|
873
|
+
data: { message: `keepalive while '${toolName}' is running` },
|
|
874
|
+
level: _nullishCoalesce(config.logLevel, () => ( "debug")),
|
|
875
|
+
logger: STREAM_KEEPALIVE_LOGGER
|
|
876
|
+
}
|
|
877
|
+
}).catch((error) => {
|
|
878
|
+
this.#logger.debug(
|
|
879
|
+
`[FastMCP debug] stream keepalive for '${toolName}' failed:`,
|
|
880
|
+
error instanceof Error ? error.message : String(error)
|
|
881
|
+
);
|
|
882
|
+
});
|
|
883
|
+
}, intervalMs);
|
|
884
|
+
_optionalChain([timer, 'access', _22 => _22.unref, 'optionalCall', _23 => _23()]);
|
|
885
|
+
const stop = () => clearInterval(timer);
|
|
886
|
+
_optionalChain([extra, 'access', _24 => _24.signal, 'optionalAccess', _25 => _25.addEventListener, 'call', _26 => _26("abort", stop, { once: true })]);
|
|
887
|
+
return stop;
|
|
888
|
+
}
|
|
846
889
|
async #validateStructuredContent(tool, value, toolName) {
|
|
847
890
|
if (!tool.outputSchema) {
|
|
848
891
|
return value;
|
|
@@ -1037,7 +1080,7 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
1037
1080
|
result = await prompt.load(
|
|
1038
1081
|
args,
|
|
1039
1082
|
this.#auth,
|
|
1040
|
-
this.#createLoadContext(_optionalChain([request, 'access',
|
|
1083
|
+
this.#createLoadContext(_optionalChain([request, 'access', _27 => _27.params, 'optionalAccess', _28 => _28._meta]))
|
|
1041
1084
|
);
|
|
1042
1085
|
} catch (error) {
|
|
1043
1086
|
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
@@ -1102,7 +1145,7 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
1102
1145
|
const result = await resourceTemplate.load(
|
|
1103
1146
|
match,
|
|
1104
1147
|
this.#auth,
|
|
1105
|
-
this.#createLoadContext(_optionalChain([request, 'access',
|
|
1148
|
+
this.#createLoadContext(_optionalChain([request, 'access', _29 => _29.params, 'optionalAccess', _30 => _30._meta]))
|
|
1106
1149
|
);
|
|
1107
1150
|
const resources = Array.isArray(result) ? result : [result];
|
|
1108
1151
|
return {
|
|
@@ -1127,7 +1170,7 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
1127
1170
|
try {
|
|
1128
1171
|
maybeArrayResult = await resource.load(
|
|
1129
1172
|
this.#auth,
|
|
1130
|
-
this.#createLoadContext(_optionalChain([request, 'access',
|
|
1173
|
+
this.#createLoadContext(_optionalChain([request, 'access', _31 => _31.params, 'optionalAccess', _32 => _32._meta]))
|
|
1131
1174
|
);
|
|
1132
1175
|
} catch (error) {
|
|
1133
1176
|
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
@@ -1190,7 +1233,7 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
1190
1233
|
);
|
|
1191
1234
|
}
|
|
1192
1235
|
setupRootsHandlers() {
|
|
1193
|
-
if (_optionalChain([this, 'access',
|
|
1236
|
+
if (_optionalChain([this, 'access', _33 => _33.#rootsConfig, 'optionalAccess', _34 => _34.enabled]) === false) {
|
|
1194
1237
|
this.#logger.debug(
|
|
1195
1238
|
"[FastMCP debug] roots capability explicitly disabled via config"
|
|
1196
1239
|
);
|
|
@@ -1260,169 +1303,178 @@ ${error instanceof Error ? error.stack : JSON.stringify(error)}`
|
|
|
1260
1303
|
tools: cachedToolsList
|
|
1261
1304
|
};
|
|
1262
1305
|
});
|
|
1263
|
-
this.#server.setRequestHandler(
|
|
1264
|
-
|
|
1265
|
-
|
|
1266
|
-
|
|
1267
|
-
|
|
1268
|
-
`Unknown tool: ${request.params.name}`
|
|
1269
|
-
);
|
|
1270
|
-
}
|
|
1271
|
-
let args = void 0;
|
|
1272
|
-
if (tool.parameters) {
|
|
1273
|
-
const parsed = await tool.parameters["~standard"].validate(
|
|
1274
|
-
request.params.arguments
|
|
1275
|
-
);
|
|
1276
|
-
if (parsed.issues) {
|
|
1277
|
-
const friendlyErrors = this.#formatSchemaIssues(parsed.issues);
|
|
1306
|
+
this.#server.setRequestHandler(
|
|
1307
|
+
_typesjs.CallToolRequestSchema,
|
|
1308
|
+
async (request, extra) => {
|
|
1309
|
+
const tool = toolsMap.get(request.params.name);
|
|
1310
|
+
if (!tool) {
|
|
1278
1311
|
throw new (0, _typesjs.McpError)(
|
|
1279
|
-
_typesjs.ErrorCode.
|
|
1280
|
-
`
|
|
1312
|
+
_typesjs.ErrorCode.MethodNotFound,
|
|
1313
|
+
`Unknown tool: ${request.params.name}`
|
|
1281
1314
|
);
|
|
1282
1315
|
}
|
|
1283
|
-
args =
|
|
1284
|
-
|
|
1285
|
-
|
|
1286
|
-
|
|
1287
|
-
|
|
1288
|
-
|
|
1289
|
-
|
|
1290
|
-
|
|
1316
|
+
let args = void 0;
|
|
1317
|
+
if (tool.parameters) {
|
|
1318
|
+
const parsed = await tool.parameters["~standard"].validate(
|
|
1319
|
+
request.params.arguments
|
|
1320
|
+
);
|
|
1321
|
+
if (parsed.issues) {
|
|
1322
|
+
const friendlyErrors = this.#formatSchemaIssues(parsed.issues);
|
|
1323
|
+
throw new (0, _typesjs.McpError)(
|
|
1324
|
+
_typesjs.ErrorCode.InvalidParams,
|
|
1325
|
+
`Tool '${request.params.name}' parameter validation failed: ${friendlyErrors}. Please check the parameter types and values according to the tool's schema.`
|
|
1326
|
+
);
|
|
1291
1327
|
}
|
|
1292
|
-
|
|
1293
|
-
|
|
1294
|
-
|
|
1295
|
-
|
|
1296
|
-
|
|
1297
|
-
|
|
1328
|
+
args = parsed.value;
|
|
1329
|
+
}
|
|
1330
|
+
const progressToken = _optionalChain([request, 'access', _35 => _35.params, 'optionalAccess', _36 => _36._meta, 'optionalAccess', _37 => _37.progressToken]);
|
|
1331
|
+
let result;
|
|
1332
|
+
try {
|
|
1333
|
+
const reportProgress = async (progress) => {
|
|
1334
|
+
if (progressToken === void 0) {
|
|
1335
|
+
return;
|
|
1336
|
+
}
|
|
1337
|
+
try {
|
|
1338
|
+
await this.#server.notification({
|
|
1339
|
+
method: "notifications/progress",
|
|
1340
|
+
params: {
|
|
1341
|
+
...progress,
|
|
1342
|
+
progressToken
|
|
1343
|
+
}
|
|
1344
|
+
});
|
|
1345
|
+
if (this.#needsEventLoopFlush) {
|
|
1346
|
+
await new Promise((resolve) => setImmediate(resolve));
|
|
1298
1347
|
}
|
|
1299
|
-
})
|
|
1300
|
-
|
|
1301
|
-
|
|
1348
|
+
} catch (progressError) {
|
|
1349
|
+
this.#logger.warn(
|
|
1350
|
+
`[FastMCP warning] Failed to report progress for tool '${request.params.name}':`,
|
|
1351
|
+
progressError instanceof Error ? progressError.message : String(progressError)
|
|
1352
|
+
);
|
|
1302
1353
|
}
|
|
1303
|
-
}
|
|
1304
|
-
|
|
1305
|
-
|
|
1306
|
-
|
|
1307
|
-
|
|
1308
|
-
|
|
1309
|
-
|
|
1310
|
-
|
|
1311
|
-
|
|
1312
|
-
|
|
1313
|
-
|
|
1314
|
-
|
|
1315
|
-
|
|
1316
|
-
|
|
1317
|
-
content: contentArray,
|
|
1318
|
-
toolName: request.params.name
|
|
1354
|
+
};
|
|
1355
|
+
const log = this.#createLog();
|
|
1356
|
+
const streamContent = async (content) => {
|
|
1357
|
+
const contentArray = Array.isArray(content) ? content : [content];
|
|
1358
|
+
try {
|
|
1359
|
+
await this.#server.notification({
|
|
1360
|
+
method: "notifications/tool/streamContent",
|
|
1361
|
+
params: {
|
|
1362
|
+
content: contentArray,
|
|
1363
|
+
toolName: request.params.name
|
|
1364
|
+
}
|
|
1365
|
+
});
|
|
1366
|
+
if (this.#needsEventLoopFlush) {
|
|
1367
|
+
await new Promise((resolve) => setImmediate(resolve));
|
|
1319
1368
|
}
|
|
1320
|
-
})
|
|
1321
|
-
|
|
1322
|
-
|
|
1369
|
+
} catch (streamError) {
|
|
1370
|
+
this.#logger.warn(
|
|
1371
|
+
`[FastMCP warning] Failed to stream content for tool '${request.params.name}':`,
|
|
1372
|
+
streamError instanceof Error ? streamError.message : String(streamError)
|
|
1373
|
+
);
|
|
1323
1374
|
}
|
|
1324
|
-
}
|
|
1325
|
-
|
|
1326
|
-
|
|
1327
|
-
|
|
1328
|
-
|
|
1375
|
+
};
|
|
1376
|
+
if (this.#onToolCall) {
|
|
1377
|
+
await this.#onToolCall({
|
|
1378
|
+
arguments: _nullishCoalesce(args, () => ( {})),
|
|
1379
|
+
toolName: request.params.name
|
|
1380
|
+
});
|
|
1329
1381
|
}
|
|
1330
|
-
|
|
1331
|
-
|
|
1332
|
-
|
|
1333
|
-
|
|
1334
|
-
|
|
1335
|
-
|
|
1336
|
-
|
|
1337
|
-
|
|
1338
|
-
|
|
1339
|
-
|
|
1340
|
-
|
|
1341
|
-
|
|
1342
|
-
|
|
1343
|
-
|
|
1344
|
-
|
|
1345
|
-
|
|
1346
|
-
|
|
1347
|
-
|
|
1348
|
-
|
|
1349
|
-
|
|
1350
|
-
|
|
1351
|
-
|
|
1352
|
-
|
|
1353
|
-
|
|
1354
|
-
|
|
1355
|
-
|
|
1356
|
-
)
|
|
1382
|
+
const executeToolPromise = Promise.resolve(
|
|
1383
|
+
tool.execute(args, {
|
|
1384
|
+
client: {
|
|
1385
|
+
version: this.#server.getClientVersion()
|
|
1386
|
+
},
|
|
1387
|
+
elicit: (params, options) => this.#server.elicitInput(params, options),
|
|
1388
|
+
log,
|
|
1389
|
+
reportProgress,
|
|
1390
|
+
requestId: typeof _optionalChain([request, 'access', _38 => _38.params, 'optionalAccess', _39 => _39._meta, 'optionalAccess', _40 => _40.requestId]) === "string" ? request.params._meta.requestId : void 0,
|
|
1391
|
+
session: this.#auth,
|
|
1392
|
+
sessionId: this.#sessionId,
|
|
1393
|
+
streamContent
|
|
1394
|
+
})
|
|
1395
|
+
);
|
|
1396
|
+
const stopStreamKeepalive = this.#startStreamKeepalive(
|
|
1397
|
+
extra,
|
|
1398
|
+
request.params.name
|
|
1399
|
+
);
|
|
1400
|
+
const maybeStringResult = await (tool.timeoutMs ? Promise.race([
|
|
1401
|
+
executeToolPromise,
|
|
1402
|
+
new Promise((_, reject) => {
|
|
1403
|
+
const timeoutId = setTimeout(() => {
|
|
1404
|
+
reject(
|
|
1405
|
+
new UserError(
|
|
1406
|
+
`Tool '${request.params.name}' timed out after ${tool.timeoutMs}ms. Consider increasing timeoutMs or optimizing the tool implementation.`
|
|
1407
|
+
)
|
|
1408
|
+
);
|
|
1409
|
+
}, tool.timeoutMs);
|
|
1410
|
+
executeToolPromise.then(
|
|
1411
|
+
() => clearTimeout(timeoutId),
|
|
1412
|
+
() => clearTimeout(timeoutId)
|
|
1357
1413
|
);
|
|
1358
|
-
}
|
|
1359
|
-
|
|
1360
|
-
|
|
1361
|
-
|
|
1362
|
-
|
|
1363
|
-
|
|
1364
|
-
|
|
1365
|
-
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
|
|
1369
|
-
})
|
|
1370
|
-
|
|
1371
|
-
|
|
1372
|
-
|
|
1373
|
-
})
|
|
1374
|
-
|
|
1375
|
-
|
|
1376
|
-
|
|
1377
|
-
|
|
1378
|
-
|
|
1379
|
-
|
|
1380
|
-
|
|
1381
|
-
|
|
1414
|
+
})
|
|
1415
|
+
]) : executeToolPromise).finally(stopStreamKeepalive);
|
|
1416
|
+
await _promises3.setTimeout.call(void 0, 1);
|
|
1417
|
+
if (maybeStringResult === void 0 || maybeStringResult === null) {
|
|
1418
|
+
result = ContentResultZodSchema.parse({
|
|
1419
|
+
content: []
|
|
1420
|
+
});
|
|
1421
|
+
} else if (typeof maybeStringResult === "string") {
|
|
1422
|
+
result = ContentResultZodSchema.parse({
|
|
1423
|
+
content: [{ text: maybeStringResult, type: "text" }]
|
|
1424
|
+
});
|
|
1425
|
+
} else if ("type" in maybeStringResult) {
|
|
1426
|
+
result = ContentResultZodSchema.parse({
|
|
1427
|
+
content: [maybeStringResult]
|
|
1428
|
+
});
|
|
1429
|
+
} else if ("content" in maybeStringResult) {
|
|
1430
|
+
result = ContentResultZodSchema.parse(maybeStringResult);
|
|
1431
|
+
if (result.structuredContent !== void 0 && tool.outputSchema) {
|
|
1432
|
+
result.structuredContent = await this.#validateStructuredContent(
|
|
1433
|
+
tool,
|
|
1434
|
+
result.structuredContent,
|
|
1435
|
+
request.params.name
|
|
1436
|
+
);
|
|
1437
|
+
}
|
|
1438
|
+
} else if (tool.outputSchema) {
|
|
1439
|
+
const structuredContent = await this.#validateStructuredContent(
|
|
1382
1440
|
tool,
|
|
1383
|
-
|
|
1441
|
+
maybeStringResult,
|
|
1384
1442
|
request.params.name
|
|
1385
1443
|
);
|
|
1444
|
+
result = ContentResultZodSchema.parse({
|
|
1445
|
+
content: [
|
|
1446
|
+
{
|
|
1447
|
+
text: JSON.stringify(structuredContent),
|
|
1448
|
+
type: "text"
|
|
1449
|
+
}
|
|
1450
|
+
],
|
|
1451
|
+
structuredContent
|
|
1452
|
+
});
|
|
1453
|
+
} else {
|
|
1454
|
+
result = ContentResultZodSchema.parse(maybeStringResult);
|
|
1386
1455
|
}
|
|
1387
|
-
}
|
|
1388
|
-
|
|
1389
|
-
|
|
1390
|
-
|
|
1391
|
-
|
|
1392
|
-
|
|
1393
|
-
|
|
1456
|
+
} catch (error) {
|
|
1457
|
+
if (error instanceof UserError) {
|
|
1458
|
+
return {
|
|
1459
|
+
content: [{ text: error.message, type: "text" }],
|
|
1460
|
+
isError: true,
|
|
1461
|
+
...error.extras ? { structuredContent: error.extras } : {}
|
|
1462
|
+
};
|
|
1463
|
+
}
|
|
1464
|
+
const errorMessage = error instanceof Error ? error.message : String(error);
|
|
1465
|
+
return {
|
|
1394
1466
|
content: [
|
|
1395
1467
|
{
|
|
1396
|
-
text:
|
|
1468
|
+
text: `Tool '${request.params.name}' execution failed: ${errorMessage}`,
|
|
1397
1469
|
type: "text"
|
|
1398
1470
|
}
|
|
1399
1471
|
],
|
|
1400
|
-
|
|
1401
|
-
});
|
|
1402
|
-
} else {
|
|
1403
|
-
result = ContentResultZodSchema.parse(maybeStringResult);
|
|
1404
|
-
}
|
|
1405
|
-
} catch (error) {
|
|
1406
|
-
if (error instanceof UserError) {
|
|
1407
|
-
return {
|
|
1408
|
-
content: [{ text: error.message, type: "text" }],
|
|
1409
|
-
isError: true,
|
|
1410
|
-
...error.extras ? { structuredContent: error.extras } : {}
|
|
1472
|
+
isError: true
|
|
1411
1473
|
};
|
|
1412
1474
|
}
|
|
1413
|
-
|
|
1414
|
-
return {
|
|
1415
|
-
content: [
|
|
1416
|
-
{
|
|
1417
|
-
text: `Tool '${request.params.name}' execution failed: ${errorMessage}`,
|
|
1418
|
-
type: "text"
|
|
1419
|
-
}
|
|
1420
|
-
],
|
|
1421
|
-
isError: true
|
|
1422
|
-
};
|
|
1475
|
+
return result;
|
|
1423
1476
|
}
|
|
1424
|
-
|
|
1425
|
-
});
|
|
1477
|
+
);
|
|
1426
1478
|
}
|
|
1427
1479
|
};
|
|
1428
1480
|
function camelToSnakeCase(str) {
|
|
@@ -1451,7 +1503,7 @@ function normalizePath(path) {
|
|
|
1451
1503
|
return path.startsWith("/") ? path : `/${path}`;
|
|
1452
1504
|
}
|
|
1453
1505
|
function parseBasicAuthHeader(authHeader) {
|
|
1454
|
-
const basicMatch = _optionalChain([authHeader, 'optionalAccess',
|
|
1506
|
+
const basicMatch = _optionalChain([authHeader, 'optionalAccess', _41 => _41.match, 'call', _42 => _42(/^Basic\s+(.+)$/)]);
|
|
1455
1507
|
if (!basicMatch) return null;
|
|
1456
1508
|
try {
|
|
1457
1509
|
const credentials = Buffer.from(basicMatch[1], "base64").toString("utf-8");
|
|
@@ -1863,6 +1915,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
1863
1915
|
resources: this.#resources,
|
|
1864
1916
|
resourcesTemplates: this.#resourcesTemplates,
|
|
1865
1917
|
roots: this.#options.roots,
|
|
1918
|
+
streamKeepalive: this.#options.streamKeepalive,
|
|
1866
1919
|
tools: this.#tools,
|
|
1867
1920
|
transportType: "stdio",
|
|
1868
1921
|
utils: this.#options.utils,
|
|
@@ -1932,7 +1985,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
1932
1985
|
enableJsonResponse: httpConfig.enableJsonResponse,
|
|
1933
1986
|
eventStore: httpConfig.eventStore,
|
|
1934
1987
|
host: httpConfig.host,
|
|
1935
|
-
..._optionalChain([this, 'access',
|
|
1988
|
+
..._optionalChain([this, 'access', _43 => _43.#options, 'access', _44 => _44.oauth, 'optionalAccess', _45 => _45.enabled]) && _optionalChain([this, 'access', _46 => _46.#options, 'access', _47 => _47.oauth, 'access', _48 => _48.protectedResource, 'optionalAccess', _49 => _49.resource]) ? {
|
|
1936
1989
|
oauth: {
|
|
1937
1990
|
protectedResource: {
|
|
1938
1991
|
resource: this.#options.oauth.protectedResource.resource
|
|
@@ -1981,7 +2034,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
1981
2034
|
enableJsonResponse: httpConfig.enableJsonResponse,
|
|
1982
2035
|
eventStore: httpConfig.eventStore,
|
|
1983
2036
|
host: httpConfig.host,
|
|
1984
|
-
..._optionalChain([this, 'access',
|
|
2037
|
+
..._optionalChain([this, 'access', _50 => _50.#options, 'access', _51 => _51.oauth, 'optionalAccess', _52 => _52.enabled]) && _optionalChain([this, 'access', _53 => _53.#options, 'access', _54 => _54.oauth, 'access', _55 => _55.protectedResource, 'optionalAccess', _56 => _56.resource]) ? {
|
|
1985
2038
|
oauth: {
|
|
1986
2039
|
protectedResource: {
|
|
1987
2040
|
resource: this.#options.oauth.protectedResource.resource
|
|
@@ -2062,6 +2115,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2062
2115
|
roots: this.#options.roots,
|
|
2063
2116
|
sessionId,
|
|
2064
2117
|
stateless,
|
|
2118
|
+
streamKeepalive: this.#options.streamKeepalive,
|
|
2065
2119
|
tools: allowedTools,
|
|
2066
2120
|
transportType: "httpStream",
|
|
2067
2121
|
utils: this.#options.utils,
|
|
@@ -2083,7 +2137,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2083
2137
|
*/
|
|
2084
2138
|
#createUnauthorizedResponse(message) {
|
|
2085
2139
|
const oauth = this.#options.oauth;
|
|
2086
|
-
const resource = _optionalChain([oauth, 'optionalAccess',
|
|
2140
|
+
const resource = _optionalChain([oauth, 'optionalAccess', _57 => _57.enabled]) ? _optionalChain([oauth, 'access', _58 => _58.protectedResource, 'optionalAccess', _59 => _59.resource]) : void 0;
|
|
2087
2141
|
const wwwAuthenticateParts = [
|
|
2088
2142
|
'error="invalid_token"',
|
|
2089
2143
|
`error_description="${message.replace(/"/g, '\\"')}"`
|
|
@@ -2195,7 +2249,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2195
2249
|
}
|
|
2196
2250
|
}
|
|
2197
2251
|
const oauthConfig = this.#options.oauth;
|
|
2198
|
-
if (_optionalChain([oauthConfig, 'optionalAccess',
|
|
2252
|
+
if (_optionalChain([oauthConfig, 'optionalAccess', _60 => _60.enabled]) && req.method === "GET") {
|
|
2199
2253
|
const url2 = new URL(req.url || "", `http://${host}`);
|
|
2200
2254
|
const authorizationServerMetadataPath = joinPaths(
|
|
2201
2255
|
"",
|
|
@@ -2229,8 +2283,8 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2229
2283
|
}
|
|
2230
2284
|
}
|
|
2231
2285
|
}
|
|
2232
|
-
const oauthProxy = _optionalChain([oauthConfig, 'optionalAccess',
|
|
2233
|
-
if (oauthProxy && _optionalChain([oauthConfig, 'optionalAccess',
|
|
2286
|
+
const oauthProxy = _optionalChain([oauthConfig, 'optionalAccess', _61 => _61.proxy]);
|
|
2287
|
+
if (oauthProxy && _optionalChain([oauthConfig, 'optionalAccess', _62 => _62.enabled])) {
|
|
2234
2288
|
const url2 = new URL(req.url || "", `http://${host}`);
|
|
2235
2289
|
const oauthPath = basePathRelativePath;
|
|
2236
2290
|
try {
|
|
@@ -2283,7 +2337,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2283
2337
|
const statusCode = error.statusCode || 400;
|
|
2284
2338
|
res.writeHead(statusCode, { "Content-Type": "application/json" }).end(
|
|
2285
2339
|
JSON.stringify(
|
|
2286
|
-
_optionalChain([error, 'access',
|
|
2340
|
+
_optionalChain([error, 'access', _63 => _63.toJSON, 'optionalCall', _64 => _64()]) || {
|
|
2287
2341
|
error: "invalid_request"
|
|
2288
2342
|
}
|
|
2289
2343
|
)
|
|
@@ -2310,7 +2364,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2310
2364
|
} catch (error) {
|
|
2311
2365
|
res.writeHead(400, { "Content-Type": "application/json" }).end(
|
|
2312
2366
|
JSON.stringify(
|
|
2313
|
-
_optionalChain([error, 'access',
|
|
2367
|
+
_optionalChain([error, 'access', _65 => _65.toJSON, 'optionalCall', _66 => _66()]) || {
|
|
2314
2368
|
error: "invalid_request"
|
|
2315
2369
|
}
|
|
2316
2370
|
)
|
|
@@ -2332,7 +2386,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2332
2386
|
} catch (error) {
|
|
2333
2387
|
res.writeHead(400, { "Content-Type": "application/json" }).end(
|
|
2334
2388
|
JSON.stringify(
|
|
2335
|
-
_optionalChain([error, 'access',
|
|
2389
|
+
_optionalChain([error, 'access', _67 => _67.toJSON, 'optionalCall', _68 => _68()]) || {
|
|
2336
2390
|
error: "server_error"
|
|
2337
2391
|
}
|
|
2338
2392
|
)
|
|
@@ -2401,7 +2455,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2401
2455
|
} catch (error) {
|
|
2402
2456
|
res.writeHead(400, { "Content-Type": "application/json" }).end(
|
|
2403
2457
|
JSON.stringify(
|
|
2404
|
-
_optionalChain([error, 'access',
|
|
2458
|
+
_optionalChain([error, 'access', _69 => _69.toJSON, 'optionalCall', _70 => _70()]) || {
|
|
2405
2459
|
error: "server_error"
|
|
2406
2460
|
}
|
|
2407
2461
|
)
|
|
@@ -2459,8 +2513,8 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2459
2513
|
const basicAuth = parseBasicAuthHeader(
|
|
2460
2514
|
req.headers.authorization
|
|
2461
2515
|
);
|
|
2462
|
-
const clientId = _optionalChain([basicAuth, 'optionalAccess',
|
|
2463
|
-
const clientSecret = _nullishCoalesce(_nullishCoalesce(_optionalChain([basicAuth, 'optionalAccess',
|
|
2516
|
+
const clientId = _optionalChain([basicAuth, 'optionalAccess', _71 => _71.clientId]) || params.get("client_id") || "";
|
|
2517
|
+
const clientSecret = _nullishCoalesce(_nullishCoalesce(_optionalChain([basicAuth, 'optionalAccess', _72 => _72.clientSecret]), () => ( params.get("client_secret"))), () => ( void 0));
|
|
2464
2518
|
let response;
|
|
2465
2519
|
if (grantType === "authorization_code") {
|
|
2466
2520
|
response = await oauthProxy.exchangeAuthorizationCode({
|
|
@@ -2490,7 +2544,7 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2490
2544
|
const statusCode = error.statusCode || 400;
|
|
2491
2545
|
res.writeHead(statusCode, { "Content-Type": "application/json" }).end(
|
|
2492
2546
|
JSON.stringify(
|
|
2493
|
-
_optionalChain([error, 'access',
|
|
2547
|
+
_optionalChain([error, 'access', _73 => _73.toJSON, 'optionalCall', _74 => _74()]) || {
|
|
2494
2548
|
error: "invalid_request"
|
|
2495
2549
|
}
|
|
2496
2550
|
)
|
|
@@ -2561,23 +2615,23 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2561
2615
|
const envBasePath = process.env.FASTMCP_BASE_PATH;
|
|
2562
2616
|
const envStateless = process.env.FASTMCP_STATELESS;
|
|
2563
2617
|
const envHost = process.env.FASTMCP_HOST;
|
|
2564
|
-
const transportType = _optionalChain([overrides, 'optionalAccess',
|
|
2618
|
+
const transportType = _optionalChain([overrides, 'optionalAccess', _75 => _75.transportType]) || (transportArg === "http-stream" ? "httpStream" : transportArg) || envTransport || "stdio";
|
|
2565
2619
|
if (transportType === "httpStream") {
|
|
2566
2620
|
const port = parseInt(
|
|
2567
|
-
_optionalChain([overrides, 'optionalAccess',
|
|
2621
|
+
_optionalChain([overrides, 'optionalAccess', _76 => _76.httpStream, 'optionalAccess', _77 => _77.port, 'optionalAccess', _78 => _78.toString, 'call', _79 => _79()]) || portArg || envPort || "8080"
|
|
2568
2622
|
);
|
|
2569
|
-
const host = _optionalChain([overrides, 'optionalAccess',
|
|
2570
|
-
const endpoint = _optionalChain([overrides, 'optionalAccess',
|
|
2623
|
+
const host = _optionalChain([overrides, 'optionalAccess', _80 => _80.httpStream, 'optionalAccess', _81 => _81.host]) || hostArg || envHost || "localhost";
|
|
2624
|
+
const endpoint = _optionalChain([overrides, 'optionalAccess', _82 => _82.httpStream, 'optionalAccess', _83 => _83.endpoint]) || endpointArg || envEndpoint || "/mcp";
|
|
2571
2625
|
const basePath = normalizeBasePath(
|
|
2572
|
-
_optionalChain([overrides, 'optionalAccess',
|
|
2626
|
+
_optionalChain([overrides, 'optionalAccess', _84 => _84.httpStream, 'optionalAccess', _85 => _85.basePath]) || basePathArg || envBasePath
|
|
2573
2627
|
);
|
|
2574
|
-
const enableJsonResponse = _optionalChain([overrides, 'optionalAccess',
|
|
2575
|
-
const stateless = _optionalChain([overrides, 'optionalAccess',
|
|
2576
|
-
const cors = _optionalChain([overrides, 'optionalAccess',
|
|
2577
|
-
const eventStore = _optionalChain([overrides, 'optionalAccess',
|
|
2578
|
-
const sslCa = _optionalChain([overrides, 'optionalAccess',
|
|
2579
|
-
const sslCert = _optionalChain([overrides, 'optionalAccess',
|
|
2580
|
-
const sslKey = _optionalChain([overrides, 'optionalAccess',
|
|
2628
|
+
const enableJsonResponse = _optionalChain([overrides, 'optionalAccess', _86 => _86.httpStream, 'optionalAccess', _87 => _87.enableJsonResponse]) || false;
|
|
2629
|
+
const stateless = _optionalChain([overrides, 'optionalAccess', _88 => _88.httpStream, 'optionalAccess', _89 => _89.stateless]) || statelessArg === "true" || envStateless === "true" || false;
|
|
2630
|
+
const cors = _optionalChain([overrides, 'optionalAccess', _90 => _90.httpStream, 'optionalAccess', _91 => _91.cors]);
|
|
2631
|
+
const eventStore = _optionalChain([overrides, 'optionalAccess', _92 => _92.httpStream, 'optionalAccess', _93 => _93.eventStore]);
|
|
2632
|
+
const sslCa = _optionalChain([overrides, 'optionalAccess', _94 => _94.httpStream, 'optionalAccess', _95 => _95.sslCa]);
|
|
2633
|
+
const sslCert = _optionalChain([overrides, 'optionalAccess', _96 => _96.httpStream, 'optionalAccess', _97 => _97.sslCert]);
|
|
2634
|
+
const sslKey = _optionalChain([overrides, 'optionalAccess', _98 => _98.httpStream, 'optionalAccess', _99 => _99.sslKey]);
|
|
2581
2635
|
return {
|
|
2582
2636
|
httpStream: {
|
|
2583
2637
|
basePath,
|
|
@@ -2676,4 +2730,4 @@ var FastMCP = class extends FastMCPEventEmitter {
|
|
|
2676
2730
|
|
|
2677
2731
|
|
|
2678
2732
|
exports.DiscoveryDocumentCache = DiscoveryDocumentCache; exports.jsonSchemaAdapter = jsonSchemaAdapter; exports.MEDIA_FETCH_TIMEOUT_MS = MEDIA_FETCH_TIMEOUT_MS; exports.imageContent = imageContent; exports.audioContent = audioContent; exports.FastMCPError = FastMCPError; exports.SessionError = SessionError; exports.UnexpectedStateError = UnexpectedStateError; exports.UserError = UserError; exports.ServerState = ServerState; exports.FastMCPSession = FastMCPSession; exports.FastMCP = FastMCP;
|
|
2679
|
-
//# sourceMappingURL=chunk-
|
|
2733
|
+
//# sourceMappingURL=chunk-XK5NJ5W2.cjs.map
|