@agentconnect.md/daemon 1.0.0-rc.221 → 1.0.0-rc.222

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (29) hide show
  1. package/dist/{acp-host-zyZ_j0yY.js → acp-host-DE2r7uCO.js} +64 -11
  2. package/dist/acp-host-DE2r7uCO.js.map +1 -0
  3. package/dist/{agent-list-Vx-p1X3q.js → agent-list-BwgY3Xqv.js} +2 -2
  4. package/dist/{agent-list-Vx-p1X3q.js.map → agent-list-BwgY3Xqv.js.map} +1 -1
  5. package/dist/bridge-DXIVgEzf.js +726 -0
  6. package/dist/bridge-DXIVgEzf.js.map +1 -0
  7. package/dist/{chat-CqfkPkqK.js → chat--hmAp3lB.js} +3 -3
  8. package/dist/{chat-CqfkPkqK.js.map → chat--hmAp3lB.js.map} +1 -1
  9. package/dist/index.js +5 -5
  10. package/dist/{load-agents-C1m5Y9n_.js → load-agents-hq5NXMmx.js} +33 -6
  11. package/dist/load-agents-hq5NXMmx.js.map +1 -0
  12. package/dist/{login-DUhkVhAr.js → login-EVa3UJRh.js} +4 -4
  13. package/dist/{login-DUhkVhAr.js.map → login-EVa3UJRh.js.map} +1 -1
  14. package/dist/{run-foreground-mvTzCScX.js → run-foreground-B05rDr1z.js} +3454 -37
  15. package/dist/run-foreground-B05rDr1z.js.map +1 -0
  16. package/dist/run-foreground-Bcg0RA3e.js +2 -0
  17. package/dist/{schemas-DujcoO0q.js → schemas-CQkO9hC5.js} +27 -2
  18. package/dist/schemas-CQkO9hC5.js.map +1 -0
  19. package/dist/{bridge-DoUrmBw9.js → stdio-CwrB9yrX.js} +41 -727
  20. package/dist/stdio-CwrB9yrX.js.map +1 -0
  21. package/package.json +1 -1
  22. package/dist/acp-host-zyZ_j0yY.js.map +0 -1
  23. package/dist/bridge-DoUrmBw9.js.map +0 -1
  24. package/dist/ipc-2Xbxe7uu.js +0 -35
  25. package/dist/ipc-2Xbxe7uu.js.map +0 -1
  26. package/dist/load-agents-C1m5Y9n_.js.map +0 -1
  27. package/dist/run-foreground-PSOzCSP8.js +0 -2
  28. package/dist/run-foreground-mvTzCScX.js.map +0 -1
  29. package/dist/schemas-DujcoO0q.js.map +0 -1
@@ -1,11 +1,12 @@
1
1
  import { i as __require, o as __toESM, t as __commonJSMin } from "./rolldown-runtime-CE-6LUnI.js";
2
2
  import { n as require_ms, t as require_src$2 } from "./src-DDtlVutj.js";
3
3
  import { t as DAEMON_VERSION } from "./version-DGaRXjBK.js";
4
- import { a as agentChildEnv, i as selectAgent, n as findAgentFiles, o as loadConfig, r as loadAgents, s as persistDaemonId } from "./load-agents-C1m5Y9n_.js";
4
+ import { C as _coercedNumber, T as NEVER, a as array, d as literal, f as looseObject, i as any, m as object, o as boolean, p as number$1, t as ZodNumber, v as string, x as url$4 } from "./schemas-CQkO9hC5.js";
5
+ import { a as agentChildEnv, i as selectAgent, n as findAgentFiles, o as loadConfig, r as loadAgents, s as persistDaemonId } from "./load-agents-hq5NXMmx.js";
5
6
  import { l as resolveRoot, o as mcpSocketPath, u as statePath } from "./paths-DEcUO8lC.js";
6
- import { _ as cachedRuntimeVersions, a as initGitInjection, c as simpleGit, d as MAX_FRAME_BYTES, f as buildEnvelope, g as cachedRuntimeNames, h as MEMORY_INDEX, i as prepareWorkspace, m as encode, n as installedRuntimes, o as probeGitVersion, p as decodeEnvelope, r as prefetchWorkspace, s as sessionGitEnv, t as AcpHost, u as normalizeGitUrl, v as resolveRuntimes } from "./acp-host-zyZ_j0yY.js";
7
+ import { _ as cachedRuntimeNames, a as initGitInjection, c as simpleGit, d as MAX_FRAME_BYTES, f as buildEnvelope, g as RESERVED_MCP_SERVER_NAME, h as MEMORY_INDEX, i as prepareWorkspace, m as encode, n as installedRuntimes, o as probeGitVersion, p as decodeEnvelope, r as prefetchWorkspace, s as sessionGitEnv, t as AcpHost, u as normalizeGitUrl, v as cachedRuntimeVersions, y as resolveRuntimes } from "./acp-host-DE2r7uCO.js";
7
8
  import { i as GitCredentialCache, n as gitcredSocketPath, r as writeGitcredShim, t as GitCredServer } from "./gitcred-server-Dcsq6QJe.js";
8
- import { n as encodeFrame, t as decodeFrames } from "./ipc-2Xbxe7uu.js";
9
+ import { B as isInitializedNotification, C as JSONRPCMessageSchema, D as ListResourceTemplatesResultSchema, E as ListPromptsResultSchema, F as ReadResourceResultSchema, G as safeParse, H as isJSONRPCResultResponse, I as ResourceListChangedNotificationSchema, K as decodeFrames, L as SUPPORTED_PROTOCOL_VERSIONS, N as McpError, O as ListResourcesResultSchema, P as PromptListChangedNotificationSchema, T as ListChangedOptionsBaseSchema, U as getObjectShape, V as isJSONRPCRequest, W as isZ4Schema, _ as EmptyResultSchema, a as AjvJsonSchemaValidator, d as CreateMessageRequestSchema, f as CreateMessageResultSchema, g as ElicitResultSchema, h as ElicitRequestSchema, i as assertToolsCallTaskCapability, j as ListToolsResultSchema, l as CallToolResultSchema, m as CreateTaskResultSchema, n as serializeMessage, o as Protocol, p as CreateMessageResultWithToolsSchema, q as encodeFrame, r as assertClientRequestTaskCapability, s as mergeCapabilities, t as ReadBuffer, u as CompleteResultSchema, v as ErrorCode, w as LATEST_PROTOCOL_VERSION, x as InitializeResultSchema, y as GetPromptResultSchema, z as ToolListChangedNotificationSchema } from "./stdio-CwrB9yrX.js";
9
10
  import { URL as URL$1 } from "url";
10
11
  import * as tls from "tls";
11
12
  import * as net$2 from "net";
@@ -15,13 +16,38 @@ import * as http$6 from "http";
15
16
  import { Agent } from "https";
16
17
  import { chmodSync, existsSync, mkdirSync, mkdtempSync, promises, readFileSync, rmSync, stat, unwatchFile, watch, watchFile, writeFileSync } from "node:fs";
17
18
  import { EventEmitter } from "node:events";
19
+ import process$1 from "node:process";
18
20
  import { hostname, tmpdir, type } from "node:os";
19
21
  import { randomBytes, randomUUID } from "node:crypto";
20
- import { Readable } from "node:stream";
22
+ import { PassThrough, Readable } from "node:stream";
21
23
  import net from "node:net";
22
24
  import { lstat, open, readdir, realpath, stat as stat$1 } from "node:fs/promises";
23
25
  import { DatabaseSync } from "node:sqlite";
24
26
  import assert from "assert";
27
+ //#region ../../node_modules/.pnpm/zod@4.4.3/node_modules/zod/v4/classic/compat.js
28
+ /** @deprecated Use the raw string literal codes instead, e.g. "invalid_type". */
29
+ const ZodIssueCode = {
30
+ invalid_type: "invalid_type",
31
+ too_big: "too_big",
32
+ too_small: "too_small",
33
+ invalid_format: "invalid_format",
34
+ not_multiple_of: "not_multiple_of",
35
+ unrecognized_keys: "unrecognized_keys",
36
+ invalid_union: "invalid_union",
37
+ invalid_key: "invalid_key",
38
+ invalid_element: "invalid_element",
39
+ invalid_value: "invalid_value",
40
+ custom: "custom"
41
+ };
42
+ /** @deprecated Do not use. Stub definition, only included for zod-to-json-schema compatibility. */
43
+ var ZodFirstPartyTypeKind;
44
+ ZodFirstPartyTypeKind || (ZodFirstPartyTypeKind = {});
45
+ //#endregion
46
+ //#region ../../node_modules/.pnpm/zod@4.4.3/node_modules/zod/v4/classic/coerce.js
47
+ function number(params) {
48
+ return _coercedNumber(ZodNumber, params);
49
+ }
50
+ //#endregion
25
51
  //#region ../../node_modules/.pnpm/ws@8.21.0/node_modules/ws/lib/constants.js
26
52
  var require_constants$1 = /* @__PURE__ */ __commonJSMin(((exports, module) => {
27
53
  const BINARY_TYPES = [
@@ -6031,20 +6057,20 @@ var SessionManager = class {
6031
6057
  this.deps.store.upsertSession(rec);
6032
6058
  } else if (host.hasSession?.(rec.acpSessionId) === false) {
6033
6059
  const cwd = await prepareWorkspace(agent);
6060
+ const mcpServers = this.deps.mcpServersFor?.({
6061
+ agent,
6062
+ channel: msg.channel,
6063
+ thread
6064
+ }) ?? [];
6034
6065
  let resumed = false;
6035
6066
  if (host.loadSupported?.()) {
6036
6067
  this.deps.store.setSessionState(key, "resuming", Date.now());
6037
6068
  try {
6038
- await host.loadSession(rec.acpSessionId, cwd, effortOverride);
6069
+ await host.loadSession(rec.acpSessionId, cwd, mcpServers, effortOverride);
6039
6070
  resumed = true;
6040
6071
  } catch {}
6041
6072
  }
6042
6073
  if (!resumed) {
6043
- const mcpServers = this.deps.mcpServersFor?.({
6044
- agent,
6045
- channel: msg.channel,
6046
- thread
6047
- }) ?? [];
6048
6074
  const acpSessionId = await host.newSession(cwd, mcpServers, effortOverride);
6049
6075
  created = true;
6050
6076
  rec = {
@@ -6486,7 +6512,7 @@ var McpControlServer = class {
6486
6512
  */
6487
6513
  function buildMcpServers(opts) {
6488
6514
  return [{
6489
- name: "agentconnect",
6515
+ name: RESERVED_MCP_SERVER_NAME,
6490
6516
  command: process.execPath,
6491
6517
  args: [
6492
6518
  ...process.execArgv,
@@ -6503,6 +6529,3363 @@ function buildMcpServers(opts) {
6503
6529
  }];
6504
6530
  }
6505
6531
  //#endregion
6532
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/experimental/tasks/client.js
6533
+ /**
6534
+ * Experimental client task features for MCP SDK.
6535
+ * WARNING: These APIs are experimental and may change without notice.
6536
+ *
6537
+ * @experimental
6538
+ */
6539
+ /**
6540
+ * Experimental task features for MCP clients.
6541
+ *
6542
+ * Access via `client.experimental.tasks`:
6543
+ * ```typescript
6544
+ * const stream = client.experimental.tasks.callToolStream({ name: 'tool', arguments: {} });
6545
+ * const task = await client.experimental.tasks.getTask(taskId);
6546
+ * ```
6547
+ *
6548
+ * @experimental
6549
+ */
6550
+ var ExperimentalClientTasks = class {
6551
+ constructor(_client) {
6552
+ this._client = _client;
6553
+ }
6554
+ /**
6555
+ * Calls a tool and returns an AsyncGenerator that yields response messages.
6556
+ * The generator is guaranteed to end with either a 'result' or 'error' message.
6557
+ *
6558
+ * This method provides streaming access to tool execution, allowing you to
6559
+ * observe intermediate task status updates for long-running tool calls.
6560
+ * Automatically validates structured output if the tool has an outputSchema.
6561
+ *
6562
+ * @example
6563
+ * ```typescript
6564
+ * const stream = client.experimental.tasks.callToolStream({ name: 'myTool', arguments: {} });
6565
+ * for await (const message of stream) {
6566
+ * switch (message.type) {
6567
+ * case 'taskCreated':
6568
+ * console.log('Tool execution started:', message.task.taskId);
6569
+ * break;
6570
+ * case 'taskStatus':
6571
+ * console.log('Tool status:', message.task.status);
6572
+ * break;
6573
+ * case 'result':
6574
+ * console.log('Tool result:', message.result);
6575
+ * break;
6576
+ * case 'error':
6577
+ * console.error('Tool error:', message.error);
6578
+ * break;
6579
+ * }
6580
+ * }
6581
+ * ```
6582
+ *
6583
+ * @param params - Tool call parameters (name and arguments)
6584
+ * @param resultSchema - Zod schema for validating the result (defaults to CallToolResultSchema)
6585
+ * @param options - Optional request options (timeout, signal, task creation params, etc.)
6586
+ * @returns AsyncGenerator that yields ResponseMessage objects
6587
+ *
6588
+ * @experimental
6589
+ */
6590
+ async *callToolStream(params, resultSchema = CallToolResultSchema, options) {
6591
+ const clientInternal = this._client;
6592
+ const optionsWithTask = {
6593
+ ...options,
6594
+ task: options?.task ?? (clientInternal.isToolTask(params.name) ? {} : void 0)
6595
+ };
6596
+ const stream = clientInternal.requestStream({
6597
+ method: "tools/call",
6598
+ params
6599
+ }, resultSchema, optionsWithTask);
6600
+ const validator = clientInternal.getToolOutputValidator(params.name);
6601
+ for await (const message of stream) {
6602
+ if (message.type === "result" && validator) {
6603
+ const result = message.result;
6604
+ if (!result.structuredContent && !result.isError) {
6605
+ yield {
6606
+ type: "error",
6607
+ error: new McpError(ErrorCode.InvalidRequest, `Tool ${params.name} has an output schema but did not return structured content`)
6608
+ };
6609
+ return;
6610
+ }
6611
+ if (result.structuredContent) try {
6612
+ const validationResult = validator(result.structuredContent);
6613
+ if (!validationResult.valid) {
6614
+ yield {
6615
+ type: "error",
6616
+ error: new McpError(ErrorCode.InvalidParams, `Structured content does not match the tool's output schema: ${validationResult.errorMessage}`)
6617
+ };
6618
+ return;
6619
+ }
6620
+ } catch (error) {
6621
+ if (error instanceof McpError) {
6622
+ yield {
6623
+ type: "error",
6624
+ error
6625
+ };
6626
+ return;
6627
+ }
6628
+ yield {
6629
+ type: "error",
6630
+ error: new McpError(ErrorCode.InvalidParams, `Failed to validate structured content: ${error instanceof Error ? error.message : String(error)}`)
6631
+ };
6632
+ return;
6633
+ }
6634
+ }
6635
+ yield message;
6636
+ }
6637
+ }
6638
+ /**
6639
+ * Gets the current status of a task.
6640
+ *
6641
+ * @param taskId - The task identifier
6642
+ * @param options - Optional request options
6643
+ * @returns The task status
6644
+ *
6645
+ * @experimental
6646
+ */
6647
+ async getTask(taskId, options) {
6648
+ return this._client.getTask({ taskId }, options);
6649
+ }
6650
+ /**
6651
+ * Retrieves the result of a completed task.
6652
+ *
6653
+ * @param taskId - The task identifier
6654
+ * @param resultSchema - Zod schema for validating the result
6655
+ * @param options - Optional request options
6656
+ * @returns The task result
6657
+ *
6658
+ * @experimental
6659
+ */
6660
+ async getTaskResult(taskId, resultSchema, options) {
6661
+ return this._client.getTaskResult({ taskId }, resultSchema, options);
6662
+ }
6663
+ /**
6664
+ * Lists tasks with optional pagination.
6665
+ *
6666
+ * @param cursor - Optional pagination cursor
6667
+ * @param options - Optional request options
6668
+ * @returns List of tasks with optional next cursor
6669
+ *
6670
+ * @experimental
6671
+ */
6672
+ async listTasks(cursor, options) {
6673
+ return this._client.listTasks(cursor ? { cursor } : void 0, options);
6674
+ }
6675
+ /**
6676
+ * Cancels a running task.
6677
+ *
6678
+ * @param taskId - The task identifier
6679
+ * @param options - Optional request options
6680
+ *
6681
+ * @experimental
6682
+ */
6683
+ async cancelTask(taskId, options) {
6684
+ return this._client.cancelTask({ taskId }, options);
6685
+ }
6686
+ /**
6687
+ * Sends a request and returns an AsyncGenerator that yields response messages.
6688
+ * The generator is guaranteed to end with either a 'result' or 'error' message.
6689
+ *
6690
+ * This method provides streaming access to request processing, allowing you to
6691
+ * observe intermediate task status updates for task-augmented requests.
6692
+ *
6693
+ * @param request - The request to send
6694
+ * @param resultSchema - Zod schema for validating the result
6695
+ * @param options - Optional request options (timeout, signal, task creation params, etc.)
6696
+ * @returns AsyncGenerator that yields ResponseMessage objects
6697
+ *
6698
+ * @experimental
6699
+ */
6700
+ requestStream(request, resultSchema, options) {
6701
+ return this._client.requestStream(request, resultSchema, options);
6702
+ }
6703
+ };
6704
+ //#endregion
6705
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/client/index.js
6706
+ /**
6707
+ * Elicitation default application helper. Applies defaults to the data based on the schema.
6708
+ *
6709
+ * @param schema - The schema to apply defaults to.
6710
+ * @param data - The data to apply defaults to.
6711
+ */
6712
+ function applyElicitationDefaults(schema, data) {
6713
+ if (!schema || data === null || typeof data !== "object") return;
6714
+ if (schema.type === "object" && schema.properties && typeof schema.properties === "object") {
6715
+ const obj = data;
6716
+ const props = schema.properties;
6717
+ for (const key of Object.keys(props)) {
6718
+ const propSchema = props[key];
6719
+ if (obj[key] === void 0 && Object.prototype.hasOwnProperty.call(propSchema, "default")) obj[key] = propSchema.default;
6720
+ if (obj[key] !== void 0) applyElicitationDefaults(propSchema, obj[key]);
6721
+ }
6722
+ }
6723
+ if (Array.isArray(schema.anyOf)) {
6724
+ for (const sub of schema.anyOf) if (typeof sub !== "boolean") applyElicitationDefaults(sub, data);
6725
+ }
6726
+ if (Array.isArray(schema.oneOf)) {
6727
+ for (const sub of schema.oneOf) if (typeof sub !== "boolean") applyElicitationDefaults(sub, data);
6728
+ }
6729
+ }
6730
+ /**
6731
+ * Determines which elicitation modes are supported based on declared client capabilities.
6732
+ *
6733
+ * According to the spec:
6734
+ * - An empty elicitation capability object defaults to form mode support (backwards compatibility)
6735
+ * - URL mode is only supported if explicitly declared
6736
+ *
6737
+ * @param capabilities - The client's elicitation capabilities
6738
+ * @returns An object indicating which modes are supported
6739
+ */
6740
+ function getSupportedElicitationModes(capabilities) {
6741
+ if (!capabilities) return {
6742
+ supportsFormMode: false,
6743
+ supportsUrlMode: false
6744
+ };
6745
+ const hasFormCapability = capabilities.form !== void 0;
6746
+ const hasUrlCapability = capabilities.url !== void 0;
6747
+ return {
6748
+ supportsFormMode: hasFormCapability || !hasFormCapability && !hasUrlCapability,
6749
+ supportsUrlMode: hasUrlCapability
6750
+ };
6751
+ }
6752
+ /**
6753
+ * An MCP client on top of a pluggable transport.
6754
+ *
6755
+ * The client will automatically begin the initialization flow with the server when connect() is called.
6756
+ *
6757
+ * To use with custom types, extend the base Request/Notification/Result types and pass them as type parameters:
6758
+ *
6759
+ * ```typescript
6760
+ * // Custom schemas
6761
+ * const CustomRequestSchema = RequestSchema.extend({...})
6762
+ * const CustomNotificationSchema = NotificationSchema.extend({...})
6763
+ * const CustomResultSchema = ResultSchema.extend({...})
6764
+ *
6765
+ * // Type aliases
6766
+ * type CustomRequest = z.infer<typeof CustomRequestSchema>
6767
+ * type CustomNotification = z.infer<typeof CustomNotificationSchema>
6768
+ * type CustomResult = z.infer<typeof CustomResultSchema>
6769
+ *
6770
+ * // Create typed client
6771
+ * const client = new Client<CustomRequest, CustomNotification, CustomResult>({
6772
+ * name: "CustomClient",
6773
+ * version: "1.0.0"
6774
+ * })
6775
+ * ```
6776
+ */
6777
+ var Client = class extends Protocol {
6778
+ /**
6779
+ * Initializes this client with the given name and version information.
6780
+ */
6781
+ constructor(_clientInfo, options) {
6782
+ super(options);
6783
+ this._clientInfo = _clientInfo;
6784
+ this._cachedToolOutputValidators = /* @__PURE__ */ new Map();
6785
+ this._cachedKnownTaskTools = /* @__PURE__ */ new Set();
6786
+ this._cachedRequiredTaskTools = /* @__PURE__ */ new Set();
6787
+ this._listChangedDebounceTimers = /* @__PURE__ */ new Map();
6788
+ this._capabilities = options?.capabilities ?? {};
6789
+ this._jsonSchemaValidator = options?.jsonSchemaValidator ?? new AjvJsonSchemaValidator();
6790
+ if (options?.listChanged) this._pendingListChangedConfig = options.listChanged;
6791
+ }
6792
+ /**
6793
+ * Set up handlers for list changed notifications based on config and server capabilities.
6794
+ * This should only be called after initialization when server capabilities are known.
6795
+ * Handlers are silently skipped if the server doesn't advertise the corresponding listChanged capability.
6796
+ * @internal
6797
+ */
6798
+ _setupListChangedHandlers(config) {
6799
+ if (config.tools && this._serverCapabilities?.tools?.listChanged) this._setupListChangedHandler("tools", ToolListChangedNotificationSchema, config.tools, async () => {
6800
+ return (await this.listTools()).tools;
6801
+ });
6802
+ if (config.prompts && this._serverCapabilities?.prompts?.listChanged) this._setupListChangedHandler("prompts", PromptListChangedNotificationSchema, config.prompts, async () => {
6803
+ return (await this.listPrompts()).prompts;
6804
+ });
6805
+ if (config.resources && this._serverCapabilities?.resources?.listChanged) this._setupListChangedHandler("resources", ResourceListChangedNotificationSchema, config.resources, async () => {
6806
+ return (await this.listResources()).resources;
6807
+ });
6808
+ }
6809
+ /**
6810
+ * Access experimental features.
6811
+ *
6812
+ * WARNING: These APIs are experimental and may change without notice.
6813
+ *
6814
+ * @experimental
6815
+ */
6816
+ get experimental() {
6817
+ if (!this._experimental) this._experimental = { tasks: new ExperimentalClientTasks(this) };
6818
+ return this._experimental;
6819
+ }
6820
+ /**
6821
+ * Registers new capabilities. This can only be called before connecting to a transport.
6822
+ *
6823
+ * The new capabilities will be merged with any existing capabilities previously given (e.g., at initialization).
6824
+ */
6825
+ registerCapabilities(capabilities) {
6826
+ if (this.transport) throw new Error("Cannot register capabilities after connecting to transport");
6827
+ this._capabilities = mergeCapabilities(this._capabilities, capabilities);
6828
+ }
6829
+ /**
6830
+ * Override request handler registration to enforce client-side validation for elicitation.
6831
+ */
6832
+ setRequestHandler(requestSchema, handler) {
6833
+ const methodSchema = getObjectShape(requestSchema)?.method;
6834
+ if (!methodSchema) throw new Error("Schema is missing a method literal");
6835
+ let methodValue;
6836
+ if (isZ4Schema(methodSchema)) {
6837
+ const v4Schema = methodSchema;
6838
+ methodValue = (v4Schema._zod?.def)?.value ?? v4Schema.value;
6839
+ } else {
6840
+ const v3Schema = methodSchema;
6841
+ methodValue = v3Schema._def?.value ?? v3Schema.value;
6842
+ }
6843
+ if (typeof methodValue !== "string") throw new Error("Schema method literal must be a string");
6844
+ const method = methodValue;
6845
+ if (method === "elicitation/create") {
6846
+ const wrappedHandler = async (request, extra) => {
6847
+ const validatedRequest = safeParse(ElicitRequestSchema, request);
6848
+ if (!validatedRequest.success) {
6849
+ const errorMessage = validatedRequest.error instanceof Error ? validatedRequest.error.message : String(validatedRequest.error);
6850
+ throw new McpError(ErrorCode.InvalidParams, `Invalid elicitation request: ${errorMessage}`);
6851
+ }
6852
+ const { params } = validatedRequest.data;
6853
+ params.mode = params.mode ?? "form";
6854
+ const { supportsFormMode, supportsUrlMode } = getSupportedElicitationModes(this._capabilities.elicitation);
6855
+ if (params.mode === "form" && !supportsFormMode) throw new McpError(ErrorCode.InvalidParams, "Client does not support form-mode elicitation requests");
6856
+ if (params.mode === "url" && !supportsUrlMode) throw new McpError(ErrorCode.InvalidParams, "Client does not support URL-mode elicitation requests");
6857
+ const result = await Promise.resolve(handler(request, extra));
6858
+ if (params.task) {
6859
+ const taskValidationResult = safeParse(CreateTaskResultSchema, result);
6860
+ if (!taskValidationResult.success) {
6861
+ const errorMessage = taskValidationResult.error instanceof Error ? taskValidationResult.error.message : String(taskValidationResult.error);
6862
+ throw new McpError(ErrorCode.InvalidParams, `Invalid task creation result: ${errorMessage}`);
6863
+ }
6864
+ return taskValidationResult.data;
6865
+ }
6866
+ const validationResult = safeParse(ElicitResultSchema, result);
6867
+ if (!validationResult.success) {
6868
+ const errorMessage = validationResult.error instanceof Error ? validationResult.error.message : String(validationResult.error);
6869
+ throw new McpError(ErrorCode.InvalidParams, `Invalid elicitation result: ${errorMessage}`);
6870
+ }
6871
+ const validatedResult = validationResult.data;
6872
+ const requestedSchema = params.mode === "form" ? params.requestedSchema : void 0;
6873
+ if (params.mode === "form" && validatedResult.action === "accept" && validatedResult.content && requestedSchema) {
6874
+ if (this._capabilities.elicitation?.form?.applyDefaults) try {
6875
+ applyElicitationDefaults(requestedSchema, validatedResult.content);
6876
+ } catch {}
6877
+ }
6878
+ return validatedResult;
6879
+ };
6880
+ return super.setRequestHandler(requestSchema, wrappedHandler);
6881
+ }
6882
+ if (method === "sampling/createMessage") {
6883
+ const wrappedHandler = async (request, extra) => {
6884
+ const validatedRequest = safeParse(CreateMessageRequestSchema, request);
6885
+ if (!validatedRequest.success) {
6886
+ const errorMessage = validatedRequest.error instanceof Error ? validatedRequest.error.message : String(validatedRequest.error);
6887
+ throw new McpError(ErrorCode.InvalidParams, `Invalid sampling request: ${errorMessage}`);
6888
+ }
6889
+ const { params } = validatedRequest.data;
6890
+ const result = await Promise.resolve(handler(request, extra));
6891
+ if (params.task) {
6892
+ const taskValidationResult = safeParse(CreateTaskResultSchema, result);
6893
+ if (!taskValidationResult.success) {
6894
+ const errorMessage = taskValidationResult.error instanceof Error ? taskValidationResult.error.message : String(taskValidationResult.error);
6895
+ throw new McpError(ErrorCode.InvalidParams, `Invalid task creation result: ${errorMessage}`);
6896
+ }
6897
+ return taskValidationResult.data;
6898
+ }
6899
+ const validationResult = safeParse(params.tools || params.toolChoice ? CreateMessageResultWithToolsSchema : CreateMessageResultSchema, result);
6900
+ if (!validationResult.success) {
6901
+ const errorMessage = validationResult.error instanceof Error ? validationResult.error.message : String(validationResult.error);
6902
+ throw new McpError(ErrorCode.InvalidParams, `Invalid sampling result: ${errorMessage}`);
6903
+ }
6904
+ return validationResult.data;
6905
+ };
6906
+ return super.setRequestHandler(requestSchema, wrappedHandler);
6907
+ }
6908
+ return super.setRequestHandler(requestSchema, handler);
6909
+ }
6910
+ assertCapability(capability, method) {
6911
+ if (!this._serverCapabilities?.[capability]) throw new Error(`Server does not support ${capability} (required for ${method})`);
6912
+ }
6913
+ async connect(transport, options) {
6914
+ await super.connect(transport);
6915
+ if (transport.sessionId !== void 0) return;
6916
+ try {
6917
+ const result = await this.request({
6918
+ method: "initialize",
6919
+ params: {
6920
+ protocolVersion: LATEST_PROTOCOL_VERSION,
6921
+ capabilities: this._capabilities,
6922
+ clientInfo: this._clientInfo
6923
+ }
6924
+ }, InitializeResultSchema, options);
6925
+ if (result === void 0) throw new Error(`Server sent invalid initialize result: ${result}`);
6926
+ if (!SUPPORTED_PROTOCOL_VERSIONS.includes(result.protocolVersion)) throw new Error(`Server's protocol version is not supported: ${result.protocolVersion}`);
6927
+ this._serverCapabilities = result.capabilities;
6928
+ this._serverVersion = result.serverInfo;
6929
+ if (transport.setProtocolVersion) transport.setProtocolVersion(result.protocolVersion);
6930
+ this._instructions = result.instructions;
6931
+ await this.notification({ method: "notifications/initialized" });
6932
+ if (this._pendingListChangedConfig) {
6933
+ this._setupListChangedHandlers(this._pendingListChangedConfig);
6934
+ this._pendingListChangedConfig = void 0;
6935
+ }
6936
+ } catch (error) {
6937
+ this.close();
6938
+ throw error;
6939
+ }
6940
+ }
6941
+ /**
6942
+ * After initialization has completed, this will be populated with the server's reported capabilities.
6943
+ */
6944
+ getServerCapabilities() {
6945
+ return this._serverCapabilities;
6946
+ }
6947
+ /**
6948
+ * After initialization has completed, this will be populated with information about the server's name and version.
6949
+ */
6950
+ getServerVersion() {
6951
+ return this._serverVersion;
6952
+ }
6953
+ /**
6954
+ * After initialization has completed, this may be populated with information about the server's instructions.
6955
+ */
6956
+ getInstructions() {
6957
+ return this._instructions;
6958
+ }
6959
+ assertCapabilityForMethod(method) {
6960
+ switch (method) {
6961
+ case "logging/setLevel":
6962
+ if (!this._serverCapabilities?.logging) throw new Error(`Server does not support logging (required for ${method})`);
6963
+ break;
6964
+ case "prompts/get":
6965
+ case "prompts/list":
6966
+ if (!this._serverCapabilities?.prompts) throw new Error(`Server does not support prompts (required for ${method})`);
6967
+ break;
6968
+ case "resources/list":
6969
+ case "resources/templates/list":
6970
+ case "resources/read":
6971
+ case "resources/subscribe":
6972
+ case "resources/unsubscribe":
6973
+ if (!this._serverCapabilities?.resources) throw new Error(`Server does not support resources (required for ${method})`);
6974
+ if (method === "resources/subscribe" && !this._serverCapabilities.resources.subscribe) throw new Error(`Server does not support resource subscriptions (required for ${method})`);
6975
+ break;
6976
+ case "tools/call":
6977
+ case "tools/list":
6978
+ if (!this._serverCapabilities?.tools) throw new Error(`Server does not support tools (required for ${method})`);
6979
+ break;
6980
+ case "completion/complete":
6981
+ if (!this._serverCapabilities?.completions) throw new Error(`Server does not support completions (required for ${method})`);
6982
+ break;
6983
+ case "initialize": break;
6984
+ case "ping": break;
6985
+ }
6986
+ }
6987
+ assertNotificationCapability(method) {
6988
+ switch (method) {
6989
+ case "notifications/roots/list_changed":
6990
+ if (!this._capabilities.roots?.listChanged) throw new Error(`Client does not support roots list changed notifications (required for ${method})`);
6991
+ break;
6992
+ case "notifications/initialized": break;
6993
+ case "notifications/cancelled": break;
6994
+ case "notifications/progress": break;
6995
+ }
6996
+ }
6997
+ assertRequestHandlerCapability(method) {
6998
+ if (!this._capabilities) return;
6999
+ switch (method) {
7000
+ case "sampling/createMessage":
7001
+ if (!this._capabilities.sampling) throw new Error(`Client does not support sampling capability (required for ${method})`);
7002
+ break;
7003
+ case "elicitation/create":
7004
+ if (!this._capabilities.elicitation) throw new Error(`Client does not support elicitation capability (required for ${method})`);
7005
+ break;
7006
+ case "roots/list":
7007
+ if (!this._capabilities.roots) throw new Error(`Client does not support roots capability (required for ${method})`);
7008
+ break;
7009
+ case "tasks/get":
7010
+ case "tasks/list":
7011
+ case "tasks/result":
7012
+ case "tasks/cancel":
7013
+ if (!this._capabilities.tasks) throw new Error(`Client does not support tasks capability (required for ${method})`);
7014
+ break;
7015
+ case "ping": break;
7016
+ }
7017
+ }
7018
+ assertTaskCapability(method) {
7019
+ assertToolsCallTaskCapability(this._serverCapabilities?.tasks?.requests, method, "Server");
7020
+ }
7021
+ assertTaskHandlerCapability(method) {
7022
+ if (!this._capabilities) return;
7023
+ assertClientRequestTaskCapability(this._capabilities.tasks?.requests, method, "Client");
7024
+ }
7025
+ async ping(options) {
7026
+ return this.request({ method: "ping" }, EmptyResultSchema, options);
7027
+ }
7028
+ async complete(params, options) {
7029
+ return this.request({
7030
+ method: "completion/complete",
7031
+ params
7032
+ }, CompleteResultSchema, options);
7033
+ }
7034
+ async setLoggingLevel(level, options) {
7035
+ return this.request({
7036
+ method: "logging/setLevel",
7037
+ params: { level }
7038
+ }, EmptyResultSchema, options);
7039
+ }
7040
+ async getPrompt(params, options) {
7041
+ return this.request({
7042
+ method: "prompts/get",
7043
+ params
7044
+ }, GetPromptResultSchema, options);
7045
+ }
7046
+ async listPrompts(params, options) {
7047
+ return this.request({
7048
+ method: "prompts/list",
7049
+ params
7050
+ }, ListPromptsResultSchema, options);
7051
+ }
7052
+ async listResources(params, options) {
7053
+ return this.request({
7054
+ method: "resources/list",
7055
+ params
7056
+ }, ListResourcesResultSchema, options);
7057
+ }
7058
+ async listResourceTemplates(params, options) {
7059
+ return this.request({
7060
+ method: "resources/templates/list",
7061
+ params
7062
+ }, ListResourceTemplatesResultSchema, options);
7063
+ }
7064
+ async readResource(params, options) {
7065
+ return this.request({
7066
+ method: "resources/read",
7067
+ params
7068
+ }, ReadResourceResultSchema, options);
7069
+ }
7070
+ async subscribeResource(params, options) {
7071
+ return this.request({
7072
+ method: "resources/subscribe",
7073
+ params
7074
+ }, EmptyResultSchema, options);
7075
+ }
7076
+ async unsubscribeResource(params, options) {
7077
+ return this.request({
7078
+ method: "resources/unsubscribe",
7079
+ params
7080
+ }, EmptyResultSchema, options);
7081
+ }
7082
+ /**
7083
+ * Calls a tool and waits for the result. Automatically validates structured output if the tool has an outputSchema.
7084
+ *
7085
+ * For task-based execution with streaming behavior, use client.experimental.tasks.callToolStream() instead.
7086
+ */
7087
+ async callTool(params, resultSchema = CallToolResultSchema, options) {
7088
+ if (this.isToolTaskRequired(params.name)) throw new McpError(ErrorCode.InvalidRequest, `Tool "${params.name}" requires task-based execution. Use client.experimental.tasks.callToolStream() instead.`);
7089
+ const result = await this.request({
7090
+ method: "tools/call",
7091
+ params
7092
+ }, resultSchema, options);
7093
+ const validator = this.getToolOutputValidator(params.name);
7094
+ if (validator) {
7095
+ if (!result.structuredContent && !result.isError) throw new McpError(ErrorCode.InvalidRequest, `Tool ${params.name} has an output schema but did not return structured content`);
7096
+ if (result.structuredContent) try {
7097
+ const validationResult = validator(result.structuredContent);
7098
+ if (!validationResult.valid) throw new McpError(ErrorCode.InvalidParams, `Structured content does not match the tool's output schema: ${validationResult.errorMessage}`);
7099
+ } catch (error) {
7100
+ if (error instanceof McpError) throw error;
7101
+ throw new McpError(ErrorCode.InvalidParams, `Failed to validate structured content: ${error instanceof Error ? error.message : String(error)}`);
7102
+ }
7103
+ }
7104
+ return result;
7105
+ }
7106
+ isToolTask(toolName) {
7107
+ if (!this._serverCapabilities?.tasks?.requests?.tools?.call) return false;
7108
+ return this._cachedKnownTaskTools.has(toolName);
7109
+ }
7110
+ /**
7111
+ * Check if a tool requires task-based execution.
7112
+ * Unlike isToolTask which includes 'optional' tools, this only checks for 'required'.
7113
+ */
7114
+ isToolTaskRequired(toolName) {
7115
+ return this._cachedRequiredTaskTools.has(toolName);
7116
+ }
7117
+ /**
7118
+ * Cache validators for tool output schemas.
7119
+ * Called after listTools() to pre-compile validators for better performance.
7120
+ */
7121
+ cacheToolMetadata(tools) {
7122
+ this._cachedToolOutputValidators.clear();
7123
+ this._cachedKnownTaskTools.clear();
7124
+ this._cachedRequiredTaskTools.clear();
7125
+ for (const tool of tools) {
7126
+ if (tool.outputSchema) {
7127
+ const toolValidator = this._jsonSchemaValidator.getValidator(tool.outputSchema);
7128
+ this._cachedToolOutputValidators.set(tool.name, toolValidator);
7129
+ }
7130
+ const taskSupport = tool.execution?.taskSupport;
7131
+ if (taskSupport === "required" || taskSupport === "optional") this._cachedKnownTaskTools.add(tool.name);
7132
+ if (taskSupport === "required") this._cachedRequiredTaskTools.add(tool.name);
7133
+ }
7134
+ }
7135
+ /**
7136
+ * Get cached validator for a tool
7137
+ */
7138
+ getToolOutputValidator(toolName) {
7139
+ return this._cachedToolOutputValidators.get(toolName);
7140
+ }
7141
+ async listTools(params, options) {
7142
+ const result = await this.request({
7143
+ method: "tools/list",
7144
+ params
7145
+ }, ListToolsResultSchema, options);
7146
+ this.cacheToolMetadata(result.tools);
7147
+ return result;
7148
+ }
7149
+ /**
7150
+ * Set up a single list changed handler.
7151
+ * @internal
7152
+ */
7153
+ _setupListChangedHandler(listType, notificationSchema, options, fetcher) {
7154
+ const parseResult = ListChangedOptionsBaseSchema.safeParse(options);
7155
+ if (!parseResult.success) throw new Error(`Invalid ${listType} listChanged options: ${parseResult.error.message}`);
7156
+ if (typeof options.onChanged !== "function") throw new Error(`Invalid ${listType} listChanged options: onChanged must be a function`);
7157
+ const { autoRefresh, debounceMs } = parseResult.data;
7158
+ const { onChanged } = options;
7159
+ const refresh = async () => {
7160
+ if (!autoRefresh) {
7161
+ onChanged(null, null);
7162
+ return;
7163
+ }
7164
+ try {
7165
+ const items = await fetcher();
7166
+ onChanged(null, items);
7167
+ } catch (e) {
7168
+ const error = e instanceof Error ? e : new Error(String(e));
7169
+ onChanged(error, null);
7170
+ }
7171
+ };
7172
+ const handler = () => {
7173
+ if (debounceMs) {
7174
+ const existingTimer = this._listChangedDebounceTimers.get(listType);
7175
+ if (existingTimer) clearTimeout(existingTimer);
7176
+ const timer = setTimeout(refresh, debounceMs);
7177
+ this._listChangedDebounceTimers.set(listType, timer);
7178
+ } else refresh();
7179
+ };
7180
+ this.setNotificationHandler(notificationSchema, handler);
7181
+ }
7182
+ async sendRootsListChanged() {
7183
+ return this.notification({ method: "notifications/roots/list_changed" });
7184
+ }
7185
+ };
7186
+ //#endregion
7187
+ //#region ../../node_modules/.pnpm/isexe@2.0.0/node_modules/isexe/windows.js
7188
+ var require_windows = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7189
+ module.exports = isexe;
7190
+ isexe.sync = sync;
7191
+ var fs$17 = __require("fs");
7192
+ function checkPathExt(path, options) {
7193
+ var pathext = options.pathExt !== void 0 ? options.pathExt : process.env.PATHEXT;
7194
+ if (!pathext) return true;
7195
+ pathext = pathext.split(";");
7196
+ if (pathext.indexOf("") !== -1) return true;
7197
+ for (var i = 0; i < pathext.length; i++) {
7198
+ var p = pathext[i].toLowerCase();
7199
+ if (p && path.substr(-p.length).toLowerCase() === p) return true;
7200
+ }
7201
+ return false;
7202
+ }
7203
+ function checkStat(stat, path, options) {
7204
+ if (!stat.isSymbolicLink() && !stat.isFile()) return false;
7205
+ return checkPathExt(path, options);
7206
+ }
7207
+ function isexe(path, options, cb) {
7208
+ fs$17.stat(path, function(er, stat) {
7209
+ cb(er, er ? false : checkStat(stat, path, options));
7210
+ });
7211
+ }
7212
+ function sync(path, options) {
7213
+ return checkStat(fs$17.statSync(path), path, options);
7214
+ }
7215
+ }));
7216
+ //#endregion
7217
+ //#region ../../node_modules/.pnpm/isexe@2.0.0/node_modules/isexe/mode.js
7218
+ var require_mode = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7219
+ module.exports = isexe;
7220
+ isexe.sync = sync;
7221
+ var fs$16 = __require("fs");
7222
+ function isexe(path, options, cb) {
7223
+ fs$16.stat(path, function(er, stat) {
7224
+ cb(er, er ? false : checkStat(stat, options));
7225
+ });
7226
+ }
7227
+ function sync(path, options) {
7228
+ return checkStat(fs$16.statSync(path), options);
7229
+ }
7230
+ function checkStat(stat, options) {
7231
+ return stat.isFile() && checkMode(stat, options);
7232
+ }
7233
+ function checkMode(stat, options) {
7234
+ var mod = stat.mode;
7235
+ var uid = stat.uid;
7236
+ var gid = stat.gid;
7237
+ var myUid = options.uid !== void 0 ? options.uid : process.getuid && process.getuid();
7238
+ var myGid = options.gid !== void 0 ? options.gid : process.getgid && process.getgid();
7239
+ var u = parseInt("100", 8);
7240
+ var g = parseInt("010", 8);
7241
+ var o = parseInt("001", 8);
7242
+ var ug = u | g;
7243
+ return mod & o || mod & g && gid === myGid || mod & u && uid === myUid || mod & ug && myUid === 0;
7244
+ }
7245
+ }));
7246
+ //#endregion
7247
+ //#region ../../node_modules/.pnpm/isexe@2.0.0/node_modules/isexe/index.js
7248
+ var require_isexe = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7249
+ __require("fs");
7250
+ var core;
7251
+ if (process.platform === "win32" || global.TESTING_WINDOWS) core = require_windows();
7252
+ else core = require_mode();
7253
+ module.exports = isexe;
7254
+ isexe.sync = sync;
7255
+ function isexe(path, options, cb) {
7256
+ if (typeof options === "function") {
7257
+ cb = options;
7258
+ options = {};
7259
+ }
7260
+ if (!cb) {
7261
+ if (typeof Promise !== "function") throw new TypeError("callback not provided");
7262
+ return new Promise(function(resolve, reject) {
7263
+ isexe(path, options || {}, function(er, is) {
7264
+ if (er) reject(er);
7265
+ else resolve(is);
7266
+ });
7267
+ });
7268
+ }
7269
+ core(path, options || {}, function(er, is) {
7270
+ if (er) {
7271
+ if (er.code === "EACCES" || options && options.ignoreErrors) {
7272
+ er = null;
7273
+ is = false;
7274
+ }
7275
+ }
7276
+ cb(er, is);
7277
+ });
7278
+ }
7279
+ function sync(path, options) {
7280
+ try {
7281
+ return core.sync(path, options || {});
7282
+ } catch (er) {
7283
+ if (options && options.ignoreErrors || er.code === "EACCES") return false;
7284
+ else throw er;
7285
+ }
7286
+ }
7287
+ }));
7288
+ //#endregion
7289
+ //#region ../../node_modules/.pnpm/which@2.0.2/node_modules/which/which.js
7290
+ var require_which = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7291
+ const isWindows = process.platform === "win32" || process.env.OSTYPE === "cygwin" || process.env.OSTYPE === "msys";
7292
+ const path$12 = __require("path");
7293
+ const COLON = isWindows ? ";" : ":";
7294
+ const isexe = require_isexe();
7295
+ const getNotFoundError = (cmd) => Object.assign(/* @__PURE__ */ new Error(`not found: ${cmd}`), { code: "ENOENT" });
7296
+ const getPathInfo = (cmd, opt) => {
7297
+ const colon = opt.colon || COLON;
7298
+ const pathEnv = cmd.match(/\//) || isWindows && cmd.match(/\\/) ? [""] : [...isWindows ? [process.cwd()] : [], ...(opt.path || process.env.PATH || "").split(colon)];
7299
+ const pathExtExe = isWindows ? opt.pathExt || process.env.PATHEXT || ".EXE;.CMD;.BAT;.COM" : "";
7300
+ const pathExt = isWindows ? pathExtExe.split(colon) : [""];
7301
+ if (isWindows) {
7302
+ if (cmd.indexOf(".") !== -1 && pathExt[0] !== "") pathExt.unshift("");
7303
+ }
7304
+ return {
7305
+ pathEnv,
7306
+ pathExt,
7307
+ pathExtExe
7308
+ };
7309
+ };
7310
+ const which = (cmd, opt, cb) => {
7311
+ if (typeof opt === "function") {
7312
+ cb = opt;
7313
+ opt = {};
7314
+ }
7315
+ if (!opt) opt = {};
7316
+ const { pathEnv, pathExt, pathExtExe } = getPathInfo(cmd, opt);
7317
+ const found = [];
7318
+ const step = (i) => new Promise((resolve, reject) => {
7319
+ if (i === pathEnv.length) return opt.all && found.length ? resolve(found) : reject(getNotFoundError(cmd));
7320
+ const ppRaw = pathEnv[i];
7321
+ const pathPart = /^".*"$/.test(ppRaw) ? ppRaw.slice(1, -1) : ppRaw;
7322
+ const pCmd = path$12.join(pathPart, cmd);
7323
+ const p = !pathPart && /^\.[\\\/]/.test(cmd) ? cmd.slice(0, 2) + pCmd : pCmd;
7324
+ resolve(subStep(p, i, 0));
7325
+ });
7326
+ const subStep = (p, i, ii) => new Promise((resolve, reject) => {
7327
+ if (ii === pathExt.length) return resolve(step(i + 1));
7328
+ const ext = pathExt[ii];
7329
+ isexe(p + ext, { pathExt: pathExtExe }, (er, is) => {
7330
+ if (!er && is) if (opt.all) found.push(p + ext);
7331
+ else return resolve(p + ext);
7332
+ return resolve(subStep(p, i, ii + 1));
7333
+ });
7334
+ });
7335
+ return cb ? step(0).then((res) => cb(null, res), cb) : step(0);
7336
+ };
7337
+ const whichSync = (cmd, opt) => {
7338
+ opt = opt || {};
7339
+ const { pathEnv, pathExt, pathExtExe } = getPathInfo(cmd, opt);
7340
+ const found = [];
7341
+ for (let i = 0; i < pathEnv.length; i++) {
7342
+ const ppRaw = pathEnv[i];
7343
+ const pathPart = /^".*"$/.test(ppRaw) ? ppRaw.slice(1, -1) : ppRaw;
7344
+ const pCmd = path$12.join(pathPart, cmd);
7345
+ const p = !pathPart && /^\.[\\\/]/.test(cmd) ? cmd.slice(0, 2) + pCmd : pCmd;
7346
+ for (let j = 0; j < pathExt.length; j++) {
7347
+ const cur = p + pathExt[j];
7348
+ try {
7349
+ if (isexe.sync(cur, { pathExt: pathExtExe })) if (opt.all) found.push(cur);
7350
+ else return cur;
7351
+ } catch (ex) {}
7352
+ }
7353
+ }
7354
+ if (opt.all && found.length) return found;
7355
+ if (opt.nothrow) return null;
7356
+ throw getNotFoundError(cmd);
7357
+ };
7358
+ module.exports = which;
7359
+ which.sync = whichSync;
7360
+ }));
7361
+ //#endregion
7362
+ //#region ../../node_modules/.pnpm/path-key@3.1.1/node_modules/path-key/index.js
7363
+ var require_path_key = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7364
+ const pathKey = (options = {}) => {
7365
+ const environment = options.env || process.env;
7366
+ if ((options.platform || process.platform) !== "win32") return "PATH";
7367
+ return Object.keys(environment).reverse().find((key) => key.toUpperCase() === "PATH") || "Path";
7368
+ };
7369
+ module.exports = pathKey;
7370
+ module.exports.default = pathKey;
7371
+ }));
7372
+ //#endregion
7373
+ //#region ../../node_modules/.pnpm/cross-spawn@7.0.6/node_modules/cross-spawn/lib/util/resolveCommand.js
7374
+ var require_resolveCommand = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7375
+ const path$11 = __require("path");
7376
+ const which = require_which();
7377
+ const getPathKey = require_path_key();
7378
+ function resolveCommandAttempt(parsed, withoutPathExt) {
7379
+ const env = parsed.options.env || process.env;
7380
+ const cwd = process.cwd();
7381
+ const hasCustomCwd = parsed.options.cwd != null;
7382
+ const shouldSwitchCwd = hasCustomCwd && process.chdir !== void 0 && !process.chdir.disabled;
7383
+ if (shouldSwitchCwd) try {
7384
+ process.chdir(parsed.options.cwd);
7385
+ } catch (err) {}
7386
+ let resolved;
7387
+ try {
7388
+ resolved = which.sync(parsed.command, {
7389
+ path: env[getPathKey({ env })],
7390
+ pathExt: withoutPathExt ? path$11.delimiter : void 0
7391
+ });
7392
+ } catch (e) {} finally {
7393
+ if (shouldSwitchCwd) process.chdir(cwd);
7394
+ }
7395
+ if (resolved) resolved = path$11.resolve(hasCustomCwd ? parsed.options.cwd : "", resolved);
7396
+ return resolved;
7397
+ }
7398
+ function resolveCommand(parsed) {
7399
+ return resolveCommandAttempt(parsed) || resolveCommandAttempt(parsed, true);
7400
+ }
7401
+ module.exports = resolveCommand;
7402
+ }));
7403
+ //#endregion
7404
+ //#region ../../node_modules/.pnpm/cross-spawn@7.0.6/node_modules/cross-spawn/lib/util/escape.js
7405
+ var require_escape = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7406
+ const metaCharsRegExp = /([()\][%!^"`<>&|;, *?])/g;
7407
+ function escapeCommand(arg) {
7408
+ arg = arg.replace(metaCharsRegExp, "^$1");
7409
+ return arg;
7410
+ }
7411
+ function escapeArgument(arg, doubleEscapeMetaChars) {
7412
+ arg = `${arg}`;
7413
+ arg = arg.replace(/(?=(\\+?)?)\1"/g, "$1$1\\\"");
7414
+ arg = arg.replace(/(?=(\\+?)?)\1$/, "$1$1");
7415
+ arg = `"${arg}"`;
7416
+ arg = arg.replace(metaCharsRegExp, "^$1");
7417
+ if (doubleEscapeMetaChars) arg = arg.replace(metaCharsRegExp, "^$1");
7418
+ return arg;
7419
+ }
7420
+ module.exports.command = escapeCommand;
7421
+ module.exports.argument = escapeArgument;
7422
+ }));
7423
+ //#endregion
7424
+ //#region ../../node_modules/.pnpm/shebang-regex@3.0.0/node_modules/shebang-regex/index.js
7425
+ var require_shebang_regex = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7426
+ module.exports = /^#!(.*)/;
7427
+ }));
7428
+ //#endregion
7429
+ //#region ../../node_modules/.pnpm/shebang-command@2.0.0/node_modules/shebang-command/index.js
7430
+ var require_shebang_command = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7431
+ const shebangRegex = require_shebang_regex();
7432
+ module.exports = (string = "") => {
7433
+ const match = string.match(shebangRegex);
7434
+ if (!match) return null;
7435
+ const [path, argument] = match[0].replace(/#! ?/, "").split(" ");
7436
+ const binary = path.split("/").pop();
7437
+ if (binary === "env") return argument;
7438
+ return argument ? `${binary} ${argument}` : binary;
7439
+ };
7440
+ }));
7441
+ //#endregion
7442
+ //#region ../../node_modules/.pnpm/cross-spawn@7.0.6/node_modules/cross-spawn/lib/util/readShebang.js
7443
+ var require_readShebang = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7444
+ const fs$15 = __require("fs");
7445
+ const shebangCommand = require_shebang_command();
7446
+ function readShebang(command) {
7447
+ const size = 150;
7448
+ const buffer = Buffer.alloc(size);
7449
+ let fd;
7450
+ try {
7451
+ fd = fs$15.openSync(command, "r");
7452
+ fs$15.readSync(fd, buffer, 0, size, 0);
7453
+ fs$15.closeSync(fd);
7454
+ } catch (e) {}
7455
+ return shebangCommand(buffer.toString());
7456
+ }
7457
+ module.exports = readShebang;
7458
+ }));
7459
+ //#endregion
7460
+ //#region ../../node_modules/.pnpm/cross-spawn@7.0.6/node_modules/cross-spawn/lib/parse.js
7461
+ var require_parse$2 = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7462
+ const path$10 = __require("path");
7463
+ const resolveCommand = require_resolveCommand();
7464
+ const escape = require_escape();
7465
+ const readShebang = require_readShebang();
7466
+ const isWin = process.platform === "win32";
7467
+ const isExecutableRegExp = /\.(?:com|exe)$/i;
7468
+ const isCmdShimRegExp = /node_modules[\\/].bin[\\/][^\\/]+\.cmd$/i;
7469
+ function detectShebang(parsed) {
7470
+ parsed.file = resolveCommand(parsed);
7471
+ const shebang = parsed.file && readShebang(parsed.file);
7472
+ if (shebang) {
7473
+ parsed.args.unshift(parsed.file);
7474
+ parsed.command = shebang;
7475
+ return resolveCommand(parsed);
7476
+ }
7477
+ return parsed.file;
7478
+ }
7479
+ function parseNonShell(parsed) {
7480
+ if (!isWin) return parsed;
7481
+ const commandFile = detectShebang(parsed);
7482
+ const needsShell = !isExecutableRegExp.test(commandFile);
7483
+ if (parsed.options.forceShell || needsShell) {
7484
+ const needsDoubleEscapeMetaChars = isCmdShimRegExp.test(commandFile);
7485
+ parsed.command = path$10.normalize(parsed.command);
7486
+ parsed.command = escape.command(parsed.command);
7487
+ parsed.args = parsed.args.map((arg) => escape.argument(arg, needsDoubleEscapeMetaChars));
7488
+ parsed.args = [
7489
+ "/d",
7490
+ "/s",
7491
+ "/c",
7492
+ `"${[parsed.command].concat(parsed.args).join(" ")}"`
7493
+ ];
7494
+ parsed.command = process.env.comspec || "cmd.exe";
7495
+ parsed.options.windowsVerbatimArguments = true;
7496
+ }
7497
+ return parsed;
7498
+ }
7499
+ function parse(command, args, options) {
7500
+ if (args && !Array.isArray(args)) {
7501
+ options = args;
7502
+ args = null;
7503
+ }
7504
+ args = args ? args.slice(0) : [];
7505
+ options = Object.assign({}, options);
7506
+ const parsed = {
7507
+ command,
7508
+ args,
7509
+ options,
7510
+ file: void 0,
7511
+ original: {
7512
+ command,
7513
+ args
7514
+ }
7515
+ };
7516
+ return options.shell ? parsed : parseNonShell(parsed);
7517
+ }
7518
+ module.exports = parse;
7519
+ }));
7520
+ //#endregion
7521
+ //#region ../../node_modules/.pnpm/cross-spawn@7.0.6/node_modules/cross-spawn/lib/enoent.js
7522
+ var require_enoent = /* @__PURE__ */ __commonJSMin(((exports, module) => {
7523
+ const isWin = process.platform === "win32";
7524
+ function notFoundError(original, syscall) {
7525
+ return Object.assign(/* @__PURE__ */ new Error(`${syscall} ${original.command} ENOENT`), {
7526
+ code: "ENOENT",
7527
+ errno: "ENOENT",
7528
+ syscall: `${syscall} ${original.command}`,
7529
+ path: original.command,
7530
+ spawnargs: original.args
7531
+ });
7532
+ }
7533
+ function hookChildProcess(cp, parsed) {
7534
+ if (!isWin) return;
7535
+ const originalEmit = cp.emit;
7536
+ cp.emit = function(name, arg1) {
7537
+ if (name === "exit") {
7538
+ const err = verifyENOENT(arg1, parsed);
7539
+ if (err) return originalEmit.call(cp, "error", err);
7540
+ }
7541
+ return originalEmit.apply(cp, arguments);
7542
+ };
7543
+ }
7544
+ function verifyENOENT(status, parsed) {
7545
+ if (isWin && status === 1 && !parsed.file) return notFoundError(parsed.original, "spawn");
7546
+ return null;
7547
+ }
7548
+ function verifyENOENTSync(status, parsed) {
7549
+ if (isWin && status === 1 && !parsed.file) return notFoundError(parsed.original, "spawnSync");
7550
+ return null;
7551
+ }
7552
+ module.exports = {
7553
+ hookChildProcess,
7554
+ verifyENOENT,
7555
+ verifyENOENTSync,
7556
+ notFoundError
7557
+ };
7558
+ }));
7559
+ //#endregion
7560
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/client/stdio.js
7561
+ var import_cross_spawn = /* @__PURE__ */ __toESM((/* @__PURE__ */ __commonJSMin(((exports, module) => {
7562
+ const cp = __require("child_process");
7563
+ const parse = require_parse$2();
7564
+ const enoent = require_enoent();
7565
+ function spawn(command, args, options) {
7566
+ const parsed = parse(command, args, options);
7567
+ const spawned = cp.spawn(parsed.command, parsed.args, parsed.options);
7568
+ enoent.hookChildProcess(spawned, parsed);
7569
+ return spawned;
7570
+ }
7571
+ function spawnSync(command, args, options) {
7572
+ const parsed = parse(command, args, options);
7573
+ const result = cp.spawnSync(parsed.command, parsed.args, parsed.options);
7574
+ result.error = result.error || enoent.verifyENOENTSync(result.status, parsed);
7575
+ return result;
7576
+ }
7577
+ module.exports = spawn;
7578
+ module.exports.spawn = spawn;
7579
+ module.exports.sync = spawnSync;
7580
+ module.exports._parse = parse;
7581
+ module.exports._enoent = enoent;
7582
+ })))(), 1);
7583
+ /**
7584
+ * Environment variables to inherit by default, if an environment is not explicitly given.
7585
+ */
7586
+ const DEFAULT_INHERITED_ENV_VARS = process$1.platform === "win32" ? [
7587
+ "APPDATA",
7588
+ "HOMEDRIVE",
7589
+ "HOMEPATH",
7590
+ "LOCALAPPDATA",
7591
+ "PATH",
7592
+ "PROCESSOR_ARCHITECTURE",
7593
+ "SYSTEMDRIVE",
7594
+ "SYSTEMROOT",
7595
+ "TEMP",
7596
+ "USERNAME",
7597
+ "USERPROFILE",
7598
+ "PROGRAMFILES"
7599
+ ] : [
7600
+ "HOME",
7601
+ "LOGNAME",
7602
+ "PATH",
7603
+ "SHELL",
7604
+ "TERM",
7605
+ "USER"
7606
+ ];
7607
+ /**
7608
+ * Returns a default environment object including only environment variables deemed safe to inherit.
7609
+ */
7610
+ function getDefaultEnvironment() {
7611
+ const env = {};
7612
+ for (const key of DEFAULT_INHERITED_ENV_VARS) {
7613
+ const value = process$1.env[key];
7614
+ if (value === void 0) continue;
7615
+ if (value.startsWith("()")) continue;
7616
+ env[key] = value;
7617
+ }
7618
+ return env;
7619
+ }
7620
+ /**
7621
+ * Client transport for stdio: this will connect to a server by spawning a process and communicating with it over stdin/stdout.
7622
+ *
7623
+ * This transport is only available in Node.js environments.
7624
+ */
7625
+ var StdioClientTransport = class {
7626
+ constructor(server) {
7627
+ this._readBuffer = new ReadBuffer();
7628
+ this._stderrStream = null;
7629
+ this._serverParams = server;
7630
+ if (server.stderr === "pipe" || server.stderr === "overlapped") this._stderrStream = new PassThrough();
7631
+ }
7632
+ /**
7633
+ * Starts the server process and prepares to communicate with it.
7634
+ */
7635
+ async start() {
7636
+ if (this._process) throw new Error("StdioClientTransport already started! If using Client class, note that connect() calls start() automatically.");
7637
+ return new Promise((resolve, reject) => {
7638
+ this._process = (0, import_cross_spawn.default)(this._serverParams.command, this._serverParams.args ?? [], {
7639
+ env: {
7640
+ ...getDefaultEnvironment(),
7641
+ ...this._serverParams.env
7642
+ },
7643
+ stdio: [
7644
+ "pipe",
7645
+ "pipe",
7646
+ this._serverParams.stderr ?? "inherit"
7647
+ ],
7648
+ shell: false,
7649
+ windowsHide: process$1.platform === "win32",
7650
+ cwd: this._serverParams.cwd
7651
+ });
7652
+ this._process.on("error", (error) => {
7653
+ reject(error);
7654
+ this.onerror?.(error);
7655
+ });
7656
+ this._process.on("spawn", () => {
7657
+ resolve();
7658
+ });
7659
+ this._process.on("close", (_code) => {
7660
+ this._process = void 0;
7661
+ this.onclose?.();
7662
+ });
7663
+ this._process.stdin?.on("error", (error) => {
7664
+ this.onerror?.(error);
7665
+ });
7666
+ this._process.stdout?.on("data", (chunk) => {
7667
+ this._readBuffer.append(chunk);
7668
+ this.processReadBuffer();
7669
+ });
7670
+ this._process.stdout?.on("error", (error) => {
7671
+ this.onerror?.(error);
7672
+ });
7673
+ if (this._stderrStream && this._process.stderr) this._process.stderr.pipe(this._stderrStream);
7674
+ });
7675
+ }
7676
+ /**
7677
+ * The stderr stream of the child process, if `StdioServerParameters.stderr` was set to "pipe" or "overlapped".
7678
+ *
7679
+ * If stderr piping was requested, a PassThrough stream is returned _immediately_, allowing callers to
7680
+ * attach listeners before the start method is invoked. This prevents loss of any early
7681
+ * error output emitted by the child process.
7682
+ */
7683
+ get stderr() {
7684
+ if (this._stderrStream) return this._stderrStream;
7685
+ return this._process?.stderr ?? null;
7686
+ }
7687
+ /**
7688
+ * The child process pid spawned by this transport.
7689
+ *
7690
+ * This is only available after the transport has been started.
7691
+ */
7692
+ get pid() {
7693
+ return this._process?.pid ?? null;
7694
+ }
7695
+ processReadBuffer() {
7696
+ while (true) try {
7697
+ const message = this._readBuffer.readMessage();
7698
+ if (message === null) break;
7699
+ this.onmessage?.(message);
7700
+ } catch (error) {
7701
+ this.onerror?.(error);
7702
+ }
7703
+ }
7704
+ async close() {
7705
+ if (this._process) {
7706
+ const processToClose = this._process;
7707
+ this._process = void 0;
7708
+ const closePromise = new Promise((resolve) => {
7709
+ processToClose.once("close", () => {
7710
+ resolve();
7711
+ });
7712
+ });
7713
+ try {
7714
+ processToClose.stdin?.end();
7715
+ } catch {}
7716
+ await Promise.race([closePromise, new Promise((resolve) => setTimeout(resolve, 2e3).unref())]);
7717
+ if (processToClose.exitCode === null) {
7718
+ try {
7719
+ processToClose.kill("SIGTERM");
7720
+ } catch {}
7721
+ await Promise.race([closePromise, new Promise((resolve) => setTimeout(resolve, 2e3).unref())]);
7722
+ }
7723
+ if (processToClose.exitCode === null) try {
7724
+ processToClose.kill("SIGKILL");
7725
+ } catch {}
7726
+ }
7727
+ this._readBuffer.clear();
7728
+ }
7729
+ send(message) {
7730
+ return new Promise((resolve) => {
7731
+ if (!this._process?.stdin) throw new Error("Not connected");
7732
+ const json = serializeMessage(message);
7733
+ if (this._process.stdin.write(json)) resolve();
7734
+ else this._process.stdin.once("drain", resolve);
7735
+ });
7736
+ }
7737
+ };
7738
+ //#endregion
7739
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/shared/transport.js
7740
+ /**
7741
+ * Normalizes HeadersInit to a plain Record<string, string> for manipulation.
7742
+ * Handles Headers objects, arrays of tuples, and plain objects.
7743
+ */
7744
+ function normalizeHeaders(headers) {
7745
+ if (!headers) return {};
7746
+ if (headers instanceof Headers) return Object.fromEntries(headers.entries());
7747
+ if (Array.isArray(headers)) return Object.fromEntries(headers);
7748
+ return { ...headers };
7749
+ }
7750
+ /**
7751
+ * Creates a fetch function that includes base RequestInit options.
7752
+ * This ensures requests inherit settings like credentials, mode, headers, etc. from the base init.
7753
+ *
7754
+ * @param baseFetch - The base fetch function to wrap (defaults to global fetch)
7755
+ * @param baseInit - The base RequestInit to merge with each request
7756
+ * @returns A wrapped fetch function that merges base options with call-specific options
7757
+ */
7758
+ function createFetchWithInit(baseFetch = fetch, baseInit) {
7759
+ if (!baseInit) return baseFetch;
7760
+ return async (url, init) => {
7761
+ return baseFetch(url, {
7762
+ ...baseInit,
7763
+ ...init,
7764
+ headers: init?.headers ? {
7765
+ ...normalizeHeaders(baseInit.headers),
7766
+ ...normalizeHeaders(init.headers)
7767
+ } : baseInit.headers
7768
+ });
7769
+ };
7770
+ }
7771
+ //#endregion
7772
+ //#region ../../node_modules/.pnpm/pkce-challenge@5.0.1/node_modules/pkce-challenge/dist/index.node.js
7773
+ let crypto$6;
7774
+ crypto$6 = globalThis.crypto?.webcrypto ?? globalThis.crypto ?? import("node:crypto").then((m) => m.webcrypto);
7775
+ /**
7776
+ * Creates an array of length `size` of random bytes
7777
+ * @param size
7778
+ * @returns Array of random ints (0 to 255)
7779
+ */
7780
+ async function getRandomValues(size) {
7781
+ return (await crypto$6).getRandomValues(new Uint8Array(size));
7782
+ }
7783
+ /** Generate cryptographically strong random string
7784
+ * @param size The desired length of the string
7785
+ * @returns The random string
7786
+ */
7787
+ async function random(size) {
7788
+ const mask = "abcdefghijklmnopqrstuvwxyzABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-._~";
7789
+ const evenDistCutoff = Math.pow(2, 8) - Math.pow(2, 8) % 66;
7790
+ let result = "";
7791
+ while (result.length < size) {
7792
+ const randomBytes = await getRandomValues(size - result.length);
7793
+ for (const randomByte of randomBytes) if (randomByte < evenDistCutoff) result += mask[randomByte % 66];
7794
+ }
7795
+ return result;
7796
+ }
7797
+ /** Generate a PKCE challenge verifier
7798
+ * @param length Length of the verifier
7799
+ * @returns A random verifier `length` characters long
7800
+ */
7801
+ async function generateVerifier(length) {
7802
+ return await random(length);
7803
+ }
7804
+ /** Generate a PKCE code challenge from a code verifier
7805
+ * @param code_verifier
7806
+ * @returns The base64 url encoded code challenge
7807
+ */
7808
+ async function generateChallenge(code_verifier) {
7809
+ const buffer = await (await crypto$6).subtle.digest("SHA-256", new TextEncoder().encode(code_verifier));
7810
+ return btoa(String.fromCharCode(...new Uint8Array(buffer))).replace(/\//g, "_").replace(/\+/g, "-").replace(/=/g, "");
7811
+ }
7812
+ /** Generate a PKCE challenge pair
7813
+ * @param length Length of the verifer (between 43-128). Defaults to 43.
7814
+ * @returns PKCE challenge pair
7815
+ */
7816
+ async function pkceChallenge(length) {
7817
+ if (!length) length = 43;
7818
+ if (length < 43 || length > 128) throw `Expected a length between 43 and 128. Received ${length}.`;
7819
+ const verifier = await generateVerifier(length);
7820
+ return {
7821
+ code_verifier: verifier,
7822
+ code_challenge: await generateChallenge(verifier)
7823
+ };
7824
+ }
7825
+ //#endregion
7826
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/shared/auth.js
7827
+ /**
7828
+ * Reusable URL validation that disallows javascript: scheme
7829
+ */
7830
+ const SafeUrlSchema = url$4().superRefine((val, ctx) => {
7831
+ if (!URL.canParse(val)) {
7832
+ ctx.addIssue({
7833
+ code: ZodIssueCode.custom,
7834
+ message: "URL must be parseable",
7835
+ fatal: true
7836
+ });
7837
+ return NEVER;
7838
+ }
7839
+ }).refine((url) => {
7840
+ const u = new URL(url);
7841
+ return u.protocol !== "javascript:" && u.protocol !== "data:" && u.protocol !== "vbscript:";
7842
+ }, { message: "URL cannot use javascript:, data:, or vbscript: scheme" });
7843
+ /**
7844
+ * RFC 9728 OAuth Protected Resource Metadata
7845
+ */
7846
+ const OAuthProtectedResourceMetadataSchema = looseObject({
7847
+ resource: string().url(),
7848
+ authorization_servers: array(SafeUrlSchema).optional(),
7849
+ jwks_uri: string().url().optional(),
7850
+ scopes_supported: array(string()).optional(),
7851
+ bearer_methods_supported: array(string()).optional(),
7852
+ resource_signing_alg_values_supported: array(string()).optional(),
7853
+ resource_name: string().optional(),
7854
+ resource_documentation: string().optional(),
7855
+ resource_policy_uri: string().url().optional(),
7856
+ resource_tos_uri: string().url().optional(),
7857
+ tls_client_certificate_bound_access_tokens: boolean().optional(),
7858
+ authorization_details_types_supported: array(string()).optional(),
7859
+ dpop_signing_alg_values_supported: array(string()).optional(),
7860
+ dpop_bound_access_tokens_required: boolean().optional()
7861
+ });
7862
+ /**
7863
+ * RFC 8414 OAuth 2.0 Authorization Server Metadata
7864
+ */
7865
+ const OAuthMetadataSchema = looseObject({
7866
+ issuer: string(),
7867
+ authorization_endpoint: SafeUrlSchema,
7868
+ token_endpoint: SafeUrlSchema,
7869
+ registration_endpoint: SafeUrlSchema.optional(),
7870
+ scopes_supported: array(string()).optional(),
7871
+ response_types_supported: array(string()),
7872
+ response_modes_supported: array(string()).optional(),
7873
+ grant_types_supported: array(string()).optional(),
7874
+ token_endpoint_auth_methods_supported: array(string()).optional(),
7875
+ token_endpoint_auth_signing_alg_values_supported: array(string()).optional(),
7876
+ service_documentation: SafeUrlSchema.optional(),
7877
+ revocation_endpoint: SafeUrlSchema.optional(),
7878
+ revocation_endpoint_auth_methods_supported: array(string()).optional(),
7879
+ revocation_endpoint_auth_signing_alg_values_supported: array(string()).optional(),
7880
+ introspection_endpoint: string().optional(),
7881
+ introspection_endpoint_auth_methods_supported: array(string()).optional(),
7882
+ introspection_endpoint_auth_signing_alg_values_supported: array(string()).optional(),
7883
+ code_challenge_methods_supported: array(string()).optional(),
7884
+ client_id_metadata_document_supported: boolean().optional()
7885
+ });
7886
+ /**
7887
+ * OpenID Connect Discovery metadata that may include OAuth 2.0 fields
7888
+ * This schema represents the real-world scenario where OIDC providers
7889
+ * return a mix of OpenID Connect and OAuth 2.0 metadata fields
7890
+ */
7891
+ const OpenIdProviderDiscoveryMetadataSchema = object({
7892
+ ...looseObject({
7893
+ issuer: string(),
7894
+ authorization_endpoint: SafeUrlSchema,
7895
+ token_endpoint: SafeUrlSchema,
7896
+ userinfo_endpoint: SafeUrlSchema.optional(),
7897
+ jwks_uri: SafeUrlSchema,
7898
+ registration_endpoint: SafeUrlSchema.optional(),
7899
+ scopes_supported: array(string()).optional(),
7900
+ response_types_supported: array(string()),
7901
+ response_modes_supported: array(string()).optional(),
7902
+ grant_types_supported: array(string()).optional(),
7903
+ acr_values_supported: array(string()).optional(),
7904
+ subject_types_supported: array(string()),
7905
+ id_token_signing_alg_values_supported: array(string()),
7906
+ id_token_encryption_alg_values_supported: array(string()).optional(),
7907
+ id_token_encryption_enc_values_supported: array(string()).optional(),
7908
+ userinfo_signing_alg_values_supported: array(string()).optional(),
7909
+ userinfo_encryption_alg_values_supported: array(string()).optional(),
7910
+ userinfo_encryption_enc_values_supported: array(string()).optional(),
7911
+ request_object_signing_alg_values_supported: array(string()).optional(),
7912
+ request_object_encryption_alg_values_supported: array(string()).optional(),
7913
+ request_object_encryption_enc_values_supported: array(string()).optional(),
7914
+ token_endpoint_auth_methods_supported: array(string()).optional(),
7915
+ token_endpoint_auth_signing_alg_values_supported: array(string()).optional(),
7916
+ display_values_supported: array(string()).optional(),
7917
+ claim_types_supported: array(string()).optional(),
7918
+ claims_supported: array(string()).optional(),
7919
+ service_documentation: string().optional(),
7920
+ claims_locales_supported: array(string()).optional(),
7921
+ ui_locales_supported: array(string()).optional(),
7922
+ claims_parameter_supported: boolean().optional(),
7923
+ request_parameter_supported: boolean().optional(),
7924
+ request_uri_parameter_supported: boolean().optional(),
7925
+ require_request_uri_registration: boolean().optional(),
7926
+ op_policy_uri: SafeUrlSchema.optional(),
7927
+ op_tos_uri: SafeUrlSchema.optional(),
7928
+ client_id_metadata_document_supported: boolean().optional()
7929
+ }).shape,
7930
+ ...OAuthMetadataSchema.pick({ code_challenge_methods_supported: true }).shape
7931
+ });
7932
+ /**
7933
+ * OAuth 2.1 token response
7934
+ */
7935
+ const OAuthTokensSchema = object({
7936
+ access_token: string(),
7937
+ id_token: string().optional(),
7938
+ token_type: string(),
7939
+ expires_in: number().optional(),
7940
+ scope: string().optional(),
7941
+ refresh_token: string().optional()
7942
+ }).strip();
7943
+ /**
7944
+ * OAuth 2.1 error response
7945
+ */
7946
+ const OAuthErrorResponseSchema = object({
7947
+ error: string(),
7948
+ error_description: string().optional(),
7949
+ error_uri: string().optional()
7950
+ });
7951
+ /**
7952
+ * Optional version of SafeUrlSchema that allows empty string for retrocompatibility on tos_uri and logo_uri
7953
+ */
7954
+ const OptionalSafeUrlSchema = SafeUrlSchema.optional().or(literal("").transform(() => void 0));
7955
+ /**
7956
+ * RFC 7591 OAuth 2.0 Dynamic Client Registration metadata
7957
+ */
7958
+ const OAuthClientMetadataSchema = object({
7959
+ redirect_uris: array(SafeUrlSchema),
7960
+ token_endpoint_auth_method: string().optional(),
7961
+ grant_types: array(string()).optional(),
7962
+ response_types: array(string()).optional(),
7963
+ client_name: string().optional(),
7964
+ client_uri: SafeUrlSchema.optional(),
7965
+ logo_uri: OptionalSafeUrlSchema,
7966
+ scope: string().optional(),
7967
+ contacts: array(string()).optional(),
7968
+ tos_uri: OptionalSafeUrlSchema,
7969
+ policy_uri: string().optional(),
7970
+ jwks_uri: SafeUrlSchema.optional(),
7971
+ jwks: any().optional(),
7972
+ software_id: string().optional(),
7973
+ software_version: string().optional(),
7974
+ software_statement: string().optional()
7975
+ }).strip();
7976
+ /**
7977
+ * RFC 7591 OAuth 2.0 Dynamic Client Registration client information
7978
+ */
7979
+ const OAuthClientInformationSchema = object({
7980
+ client_id: string(),
7981
+ client_secret: string().optional(),
7982
+ client_id_issued_at: number$1().optional(),
7983
+ client_secret_expires_at: number$1().optional()
7984
+ }).strip();
7985
+ /**
7986
+ * RFC 7591 OAuth 2.0 Dynamic Client Registration full response (client information plus metadata)
7987
+ */
7988
+ const OAuthClientInformationFullSchema = OAuthClientMetadataSchema.merge(OAuthClientInformationSchema);
7989
+ object({
7990
+ error: string(),
7991
+ error_description: string().optional()
7992
+ }).strip();
7993
+ object({
7994
+ token: string(),
7995
+ token_type_hint: string().optional()
7996
+ }).strip();
7997
+ //#endregion
7998
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/shared/auth-utils.js
7999
+ /**
8000
+ * Utilities for handling OAuth resource URIs.
8001
+ */
8002
+ /**
8003
+ * Converts a server URL to a resource URL by removing the fragment.
8004
+ * RFC 8707 section 2 states that resource URIs "MUST NOT include a fragment component".
8005
+ * Keeps everything else unchanged (scheme, domain, port, path, query).
8006
+ */
8007
+ function resourceUrlFromServerUrl(url) {
8008
+ const resourceURL = typeof url === "string" ? new URL(url) : new URL(url.href);
8009
+ resourceURL.hash = "";
8010
+ return resourceURL;
8011
+ }
8012
+ /**
8013
+ * Checks if a requested resource URL matches a configured resource URL.
8014
+ * A requested resource matches if it has the same scheme, domain, port,
8015
+ * and its path starts with the configured resource's path.
8016
+ *
8017
+ * @param requestedResource The resource URL being requested
8018
+ * @param configuredResource The resource URL that has been configured
8019
+ * @returns true if the requested resource matches the configured resource, false otherwise
8020
+ */
8021
+ function checkResourceAllowed({ requestedResource, configuredResource }) {
8022
+ const requested = typeof requestedResource === "string" ? new URL(requestedResource) : new URL(requestedResource.href);
8023
+ const configured = typeof configuredResource === "string" ? new URL(configuredResource) : new URL(configuredResource.href);
8024
+ if (requested.origin !== configured.origin) return false;
8025
+ if (requested.pathname.length < configured.pathname.length) return false;
8026
+ const requestedPath = requested.pathname.endsWith("/") ? requested.pathname : requested.pathname + "/";
8027
+ const configuredPath = configured.pathname.endsWith("/") ? configured.pathname : configured.pathname + "/";
8028
+ return requestedPath.startsWith(configuredPath);
8029
+ }
8030
+ //#endregion
8031
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/server/auth/errors.js
8032
+ /**
8033
+ * Base class for all OAuth errors
8034
+ */
8035
+ var OAuthError = class extends Error {
8036
+ constructor(message, errorUri) {
8037
+ super(message);
8038
+ this.errorUri = errorUri;
8039
+ this.name = this.constructor.name;
8040
+ }
8041
+ /**
8042
+ * Converts the error to a standard OAuth error response object
8043
+ */
8044
+ toResponseObject() {
8045
+ const response = {
8046
+ error: this.errorCode,
8047
+ error_description: this.message
8048
+ };
8049
+ if (this.errorUri) response.error_uri = this.errorUri;
8050
+ return response;
8051
+ }
8052
+ get errorCode() {
8053
+ return this.constructor.errorCode;
8054
+ }
8055
+ };
8056
+ /**
8057
+ * Invalid request error - The request is missing a required parameter,
8058
+ * includes an invalid parameter value, includes a parameter more than once,
8059
+ * or is otherwise malformed.
8060
+ */
8061
+ var InvalidRequestError = class extends OAuthError {};
8062
+ InvalidRequestError.errorCode = "invalid_request";
8063
+ /**
8064
+ * Invalid client error - Client authentication failed (e.g., unknown client, no client
8065
+ * authentication included, or unsupported authentication method).
8066
+ */
8067
+ var InvalidClientError = class extends OAuthError {};
8068
+ InvalidClientError.errorCode = "invalid_client";
8069
+ /**
8070
+ * Invalid grant error - The provided authorization grant or refresh token is
8071
+ * invalid, expired, revoked, does not match the redirection URI used in the
8072
+ * authorization request, or was issued to another client.
8073
+ */
8074
+ var InvalidGrantError = class extends OAuthError {};
8075
+ InvalidGrantError.errorCode = "invalid_grant";
8076
+ /**
8077
+ * Unauthorized client error - The authenticated client is not authorized to use
8078
+ * this authorization grant type.
8079
+ */
8080
+ var UnauthorizedClientError = class extends OAuthError {};
8081
+ UnauthorizedClientError.errorCode = "unauthorized_client";
8082
+ /**
8083
+ * Unsupported grant type error - The authorization grant type is not supported
8084
+ * by the authorization server.
8085
+ */
8086
+ var UnsupportedGrantTypeError = class extends OAuthError {};
8087
+ UnsupportedGrantTypeError.errorCode = "unsupported_grant_type";
8088
+ /**
8089
+ * Invalid scope error - The requested scope is invalid, unknown, malformed, or
8090
+ * exceeds the scope granted by the resource owner.
8091
+ */
8092
+ var InvalidScopeError = class extends OAuthError {};
8093
+ InvalidScopeError.errorCode = "invalid_scope";
8094
+ /**
8095
+ * Access denied error - The resource owner or authorization server denied the request.
8096
+ */
8097
+ var AccessDeniedError = class extends OAuthError {};
8098
+ AccessDeniedError.errorCode = "access_denied";
8099
+ /**
8100
+ * Server error - The authorization server encountered an unexpected condition
8101
+ * that prevented it from fulfilling the request.
8102
+ */
8103
+ var ServerError = class extends OAuthError {};
8104
+ ServerError.errorCode = "server_error";
8105
+ /**
8106
+ * Temporarily unavailable error - The authorization server is currently unable to
8107
+ * handle the request due to a temporary overloading or maintenance of the server.
8108
+ */
8109
+ var TemporarilyUnavailableError = class extends OAuthError {};
8110
+ TemporarilyUnavailableError.errorCode = "temporarily_unavailable";
8111
+ /**
8112
+ * Unsupported response type error - The authorization server does not support
8113
+ * obtaining an authorization code using this method.
8114
+ */
8115
+ var UnsupportedResponseTypeError = class extends OAuthError {};
8116
+ UnsupportedResponseTypeError.errorCode = "unsupported_response_type";
8117
+ /**
8118
+ * Unsupported token type error - The authorization server does not support
8119
+ * the requested token type.
8120
+ */
8121
+ var UnsupportedTokenTypeError = class extends OAuthError {};
8122
+ UnsupportedTokenTypeError.errorCode = "unsupported_token_type";
8123
+ /**
8124
+ * Invalid token error - The access token provided is expired, revoked, malformed,
8125
+ * or invalid for other reasons.
8126
+ */
8127
+ var InvalidTokenError = class extends OAuthError {};
8128
+ InvalidTokenError.errorCode = "invalid_token";
8129
+ /**
8130
+ * Method not allowed error - The HTTP method used is not allowed for this endpoint.
8131
+ * (Custom, non-standard error)
8132
+ */
8133
+ var MethodNotAllowedError = class extends OAuthError {};
8134
+ MethodNotAllowedError.errorCode = "method_not_allowed";
8135
+ /**
8136
+ * Too many requests error - Rate limit exceeded.
8137
+ * (Custom, non-standard error based on RFC 6585)
8138
+ */
8139
+ var TooManyRequestsError = class extends OAuthError {};
8140
+ TooManyRequestsError.errorCode = "too_many_requests";
8141
+ /**
8142
+ * Invalid client metadata error - The client metadata is invalid.
8143
+ * (Custom error for dynamic client registration - RFC 7591)
8144
+ */
8145
+ var InvalidClientMetadataError = class extends OAuthError {};
8146
+ InvalidClientMetadataError.errorCode = "invalid_client_metadata";
8147
+ /**
8148
+ * Insufficient scope error - The request requires higher privileges than provided by the access token.
8149
+ */
8150
+ var InsufficientScopeError = class extends OAuthError {};
8151
+ InsufficientScopeError.errorCode = "insufficient_scope";
8152
+ /**
8153
+ * Invalid target error - The requested resource is invalid, missing, unknown, or malformed.
8154
+ * (Custom error for resource indicators - RFC 8707)
8155
+ */
8156
+ var InvalidTargetError = class extends OAuthError {};
8157
+ InvalidTargetError.errorCode = "invalid_target";
8158
+ /**
8159
+ * A full list of all OAuthErrors, enabling parsing from error responses
8160
+ */
8161
+ const OAUTH_ERRORS = {
8162
+ [InvalidRequestError.errorCode]: InvalidRequestError,
8163
+ [InvalidClientError.errorCode]: InvalidClientError,
8164
+ [InvalidGrantError.errorCode]: InvalidGrantError,
8165
+ [UnauthorizedClientError.errorCode]: UnauthorizedClientError,
8166
+ [UnsupportedGrantTypeError.errorCode]: UnsupportedGrantTypeError,
8167
+ [InvalidScopeError.errorCode]: InvalidScopeError,
8168
+ [AccessDeniedError.errorCode]: AccessDeniedError,
8169
+ [ServerError.errorCode]: ServerError,
8170
+ [TemporarilyUnavailableError.errorCode]: TemporarilyUnavailableError,
8171
+ [UnsupportedResponseTypeError.errorCode]: UnsupportedResponseTypeError,
8172
+ [UnsupportedTokenTypeError.errorCode]: UnsupportedTokenTypeError,
8173
+ [InvalidTokenError.errorCode]: InvalidTokenError,
8174
+ [MethodNotAllowedError.errorCode]: MethodNotAllowedError,
8175
+ [TooManyRequestsError.errorCode]: TooManyRequestsError,
8176
+ [InvalidClientMetadataError.errorCode]: InvalidClientMetadataError,
8177
+ [InsufficientScopeError.errorCode]: InsufficientScopeError,
8178
+ [InvalidTargetError.errorCode]: InvalidTargetError
8179
+ };
8180
+ //#endregion
8181
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/client/auth.js
8182
+ var UnauthorizedError = class extends Error {
8183
+ constructor(message) {
8184
+ super(message ?? "Unauthorized");
8185
+ }
8186
+ };
8187
+ function isClientAuthMethod(method) {
8188
+ return [
8189
+ "client_secret_basic",
8190
+ "client_secret_post",
8191
+ "none"
8192
+ ].includes(method);
8193
+ }
8194
+ const AUTHORIZATION_CODE_RESPONSE_TYPE = "code";
8195
+ const AUTHORIZATION_CODE_CHALLENGE_METHOD = "S256";
8196
+ /**
8197
+ * Determines the best client authentication method to use based on server support and client configuration.
8198
+ *
8199
+ * Priority order (highest to lowest):
8200
+ * 1. client_secret_basic (if client secret is available)
8201
+ * 2. client_secret_post (if client secret is available)
8202
+ * 3. none (for public clients)
8203
+ *
8204
+ * @param clientInformation - OAuth client information containing credentials
8205
+ * @param supportedMethods - Authentication methods supported by the authorization server
8206
+ * @returns The selected authentication method
8207
+ */
8208
+ function selectClientAuthMethod(clientInformation, supportedMethods) {
8209
+ const hasClientSecret = clientInformation.client_secret !== void 0;
8210
+ if ("token_endpoint_auth_method" in clientInformation && clientInformation.token_endpoint_auth_method && isClientAuthMethod(clientInformation.token_endpoint_auth_method) && (supportedMethods.length === 0 || supportedMethods.includes(clientInformation.token_endpoint_auth_method))) return clientInformation.token_endpoint_auth_method;
8211
+ if (supportedMethods.length === 0) return hasClientSecret ? "client_secret_basic" : "none";
8212
+ if (hasClientSecret && supportedMethods.includes("client_secret_basic")) return "client_secret_basic";
8213
+ if (hasClientSecret && supportedMethods.includes("client_secret_post")) return "client_secret_post";
8214
+ if (supportedMethods.includes("none")) return "none";
8215
+ return hasClientSecret ? "client_secret_post" : "none";
8216
+ }
8217
+ /**
8218
+ * Applies client authentication to the request based on the specified method.
8219
+ *
8220
+ * Implements OAuth 2.1 client authentication methods:
8221
+ * - client_secret_basic: HTTP Basic authentication (RFC 6749 Section 2.3.1)
8222
+ * - client_secret_post: Credentials in request body (RFC 6749 Section 2.3.1)
8223
+ * - none: Public client authentication (RFC 6749 Section 2.1)
8224
+ *
8225
+ * @param method - The authentication method to use
8226
+ * @param clientInformation - OAuth client information containing credentials
8227
+ * @param headers - HTTP headers object to modify
8228
+ * @param params - URL search parameters to modify
8229
+ * @throws {Error} When required credentials are missing
8230
+ */
8231
+ function applyClientAuthentication(method, clientInformation, headers, params) {
8232
+ const { client_id, client_secret } = clientInformation;
8233
+ switch (method) {
8234
+ case "client_secret_basic":
8235
+ applyBasicAuth(client_id, client_secret, headers);
8236
+ return;
8237
+ case "client_secret_post":
8238
+ applyPostAuth(client_id, client_secret, params);
8239
+ return;
8240
+ case "none":
8241
+ applyPublicAuth(client_id, params);
8242
+ return;
8243
+ default: throw new Error(`Unsupported client authentication method: ${method}`);
8244
+ }
8245
+ }
8246
+ /**
8247
+ * Applies HTTP Basic authentication (RFC 6749 Section 2.3.1)
8248
+ */
8249
+ function applyBasicAuth(clientId, clientSecret, headers) {
8250
+ if (!clientSecret) throw new Error("client_secret_basic authentication requires a client_secret");
8251
+ const credentials = btoa(`${clientId}:${clientSecret}`);
8252
+ headers.set("Authorization", `Basic ${credentials}`);
8253
+ }
8254
+ /**
8255
+ * Applies POST body authentication (RFC 6749 Section 2.3.1)
8256
+ */
8257
+ function applyPostAuth(clientId, clientSecret, params) {
8258
+ params.set("client_id", clientId);
8259
+ if (clientSecret) params.set("client_secret", clientSecret);
8260
+ }
8261
+ /**
8262
+ * Applies public client authentication (RFC 6749 Section 2.1)
8263
+ */
8264
+ function applyPublicAuth(clientId, params) {
8265
+ params.set("client_id", clientId);
8266
+ }
8267
+ /**
8268
+ * Parses an OAuth error response from a string or Response object.
8269
+ *
8270
+ * If the input is a standard OAuth2.0 error response, it will be parsed according to the spec
8271
+ * and an instance of the appropriate OAuthError subclass will be returned.
8272
+ * If parsing fails, it falls back to a generic ServerError that includes
8273
+ * the response status (if available) and original content.
8274
+ *
8275
+ * @param input - A Response object or string containing the error response
8276
+ * @returns A Promise that resolves to an OAuthError instance
8277
+ */
8278
+ async function parseErrorResponse(input) {
8279
+ const statusCode = input instanceof Response ? input.status : void 0;
8280
+ const body = input instanceof Response ? await input.text() : input;
8281
+ try {
8282
+ const { error, error_description, error_uri } = OAuthErrorResponseSchema.parse(JSON.parse(body));
8283
+ return new (OAUTH_ERRORS[error] || ServerError)(error_description || "", error_uri);
8284
+ } catch (error) {
8285
+ return new ServerError(`${statusCode ? `HTTP ${statusCode}: ` : ""}Invalid OAuth error response: ${error}. Raw body: ${body}`);
8286
+ }
8287
+ }
8288
+ /**
8289
+ * Orchestrates the full auth flow with a server.
8290
+ *
8291
+ * This can be used as a single entry point for all authorization functionality,
8292
+ * instead of linking together the other lower-level functions in this module.
8293
+ */
8294
+ async function auth(provider, options) {
8295
+ try {
8296
+ return await authInternal(provider, options);
8297
+ } catch (error) {
8298
+ if (error instanceof InvalidClientError || error instanceof UnauthorizedClientError) {
8299
+ await provider.invalidateCredentials?.("all");
8300
+ return await authInternal(provider, options);
8301
+ } else if (error instanceof InvalidGrantError) {
8302
+ await provider.invalidateCredentials?.("tokens");
8303
+ return await authInternal(provider, options);
8304
+ }
8305
+ throw error;
8306
+ }
8307
+ }
8308
+ async function authInternal(provider, { serverUrl, authorizationCode, scope, resourceMetadataUrl, fetchFn }) {
8309
+ const cachedState = await provider.discoveryState?.();
8310
+ let resourceMetadata;
8311
+ let authorizationServerUrl;
8312
+ let metadata;
8313
+ let effectiveResourceMetadataUrl = resourceMetadataUrl;
8314
+ if (!effectiveResourceMetadataUrl && cachedState?.resourceMetadataUrl) effectiveResourceMetadataUrl = new URL(cachedState.resourceMetadataUrl);
8315
+ if (cachedState?.authorizationServerUrl) {
8316
+ authorizationServerUrl = cachedState.authorizationServerUrl;
8317
+ resourceMetadata = cachedState.resourceMetadata;
8318
+ metadata = cachedState.authorizationServerMetadata ?? await discoverAuthorizationServerMetadata(authorizationServerUrl, { fetchFn });
8319
+ if (!resourceMetadata) try {
8320
+ resourceMetadata = await discoverOAuthProtectedResourceMetadata(serverUrl, { resourceMetadataUrl: effectiveResourceMetadataUrl }, fetchFn);
8321
+ } catch {}
8322
+ if (metadata !== cachedState.authorizationServerMetadata || resourceMetadata !== cachedState.resourceMetadata) await provider.saveDiscoveryState?.({
8323
+ authorizationServerUrl: String(authorizationServerUrl),
8324
+ resourceMetadataUrl: effectiveResourceMetadataUrl?.toString(),
8325
+ resourceMetadata,
8326
+ authorizationServerMetadata: metadata
8327
+ });
8328
+ } else {
8329
+ const serverInfo = await discoverOAuthServerInfo(serverUrl, {
8330
+ resourceMetadataUrl: effectiveResourceMetadataUrl,
8331
+ fetchFn
8332
+ });
8333
+ authorizationServerUrl = serverInfo.authorizationServerUrl;
8334
+ metadata = serverInfo.authorizationServerMetadata;
8335
+ resourceMetadata = serverInfo.resourceMetadata;
8336
+ await provider.saveDiscoveryState?.({
8337
+ authorizationServerUrl: String(authorizationServerUrl),
8338
+ resourceMetadataUrl: effectiveResourceMetadataUrl?.toString(),
8339
+ resourceMetadata,
8340
+ authorizationServerMetadata: metadata
8341
+ });
8342
+ }
8343
+ const resource = await selectResourceURL(serverUrl, provider, resourceMetadata);
8344
+ const resolvedScope = scope || resourceMetadata?.scopes_supported?.join(" ") || provider.clientMetadata.scope;
8345
+ let clientInformation = await Promise.resolve(provider.clientInformation());
8346
+ if (!clientInformation) {
8347
+ if (authorizationCode !== void 0) throw new Error("Existing OAuth client information is required when exchanging an authorization code");
8348
+ const supportsUrlBasedClientId = metadata?.client_id_metadata_document_supported === true;
8349
+ const clientMetadataUrl = provider.clientMetadataUrl;
8350
+ if (clientMetadataUrl && !isHttpsUrl(clientMetadataUrl)) throw new InvalidClientMetadataError(`clientMetadataUrl must be a valid HTTPS URL with a non-root pathname, got: ${clientMetadataUrl}`);
8351
+ if (supportsUrlBasedClientId && clientMetadataUrl) {
8352
+ clientInformation = { client_id: clientMetadataUrl };
8353
+ await provider.saveClientInformation?.(clientInformation);
8354
+ } else {
8355
+ if (!provider.saveClientInformation) throw new Error("OAuth client information must be saveable for dynamic registration");
8356
+ const fullInformation = await registerClient(authorizationServerUrl, {
8357
+ metadata,
8358
+ clientMetadata: provider.clientMetadata,
8359
+ scope: resolvedScope,
8360
+ fetchFn
8361
+ });
8362
+ await provider.saveClientInformation(fullInformation);
8363
+ clientInformation = fullInformation;
8364
+ }
8365
+ }
8366
+ const nonInteractiveFlow = !provider.redirectUrl;
8367
+ if (authorizationCode !== void 0 || nonInteractiveFlow) {
8368
+ const tokens = await fetchToken(provider, authorizationServerUrl, {
8369
+ metadata,
8370
+ resource,
8371
+ authorizationCode,
8372
+ fetchFn
8373
+ });
8374
+ await provider.saveTokens(tokens);
8375
+ return "AUTHORIZED";
8376
+ }
8377
+ const tokens = await provider.tokens();
8378
+ if (tokens?.refresh_token) try {
8379
+ const newTokens = await refreshAuthorization(authorizationServerUrl, {
8380
+ metadata,
8381
+ clientInformation,
8382
+ refreshToken: tokens.refresh_token,
8383
+ resource,
8384
+ addClientAuthentication: provider.addClientAuthentication,
8385
+ fetchFn
8386
+ });
8387
+ await provider.saveTokens(newTokens);
8388
+ return "AUTHORIZED";
8389
+ } catch (error) {
8390
+ if (!(error instanceof OAuthError) || error instanceof ServerError) {} else throw error;
8391
+ }
8392
+ const state = provider.state ? await provider.state() : void 0;
8393
+ const { authorizationUrl, codeVerifier } = await startAuthorization(authorizationServerUrl, {
8394
+ metadata,
8395
+ clientInformation,
8396
+ state,
8397
+ redirectUrl: provider.redirectUrl,
8398
+ scope: resolvedScope,
8399
+ resource
8400
+ });
8401
+ await provider.saveCodeVerifier(codeVerifier);
8402
+ await provider.redirectToAuthorization(authorizationUrl);
8403
+ return "REDIRECT";
8404
+ }
8405
+ /**
8406
+ * SEP-991: URL-based Client IDs
8407
+ * Validate that the client_id is a valid URL with https scheme
8408
+ */
8409
+ function isHttpsUrl(value) {
8410
+ if (!value) return false;
8411
+ try {
8412
+ const url = new URL(value);
8413
+ return url.protocol === "https:" && url.pathname !== "/";
8414
+ } catch {
8415
+ return false;
8416
+ }
8417
+ }
8418
+ async function selectResourceURL(serverUrl, provider, resourceMetadata) {
8419
+ const defaultResource = resourceUrlFromServerUrl(serverUrl);
8420
+ if (provider.validateResourceURL) return await provider.validateResourceURL(defaultResource, resourceMetadata?.resource);
8421
+ if (!resourceMetadata) return;
8422
+ if (!checkResourceAllowed({
8423
+ requestedResource: defaultResource,
8424
+ configuredResource: resourceMetadata.resource
8425
+ })) throw new Error(`Protected resource ${resourceMetadata.resource} does not match expected ${defaultResource} (or origin)`);
8426
+ return new URL(resourceMetadata.resource);
8427
+ }
8428
+ /**
8429
+ * Extract resource_metadata, scope, and error from WWW-Authenticate header.
8430
+ */
8431
+ function extractWWWAuthenticateParams(res) {
8432
+ const authenticateHeader = res.headers.get("WWW-Authenticate");
8433
+ if (!authenticateHeader) return {};
8434
+ const [type, scheme] = authenticateHeader.split(" ");
8435
+ if (type.toLowerCase() !== "bearer" || !scheme) return {};
8436
+ const resourceMetadataMatch = extractFieldFromWwwAuth(res, "resource_metadata") || void 0;
8437
+ let resourceMetadataUrl;
8438
+ if (resourceMetadataMatch) try {
8439
+ resourceMetadataUrl = new URL(resourceMetadataMatch);
8440
+ } catch {}
8441
+ const scope = extractFieldFromWwwAuth(res, "scope") || void 0;
8442
+ const error = extractFieldFromWwwAuth(res, "error") || void 0;
8443
+ return {
8444
+ resourceMetadataUrl,
8445
+ scope,
8446
+ error
8447
+ };
8448
+ }
8449
+ /**
8450
+ * Extracts a specific field's value from the WWW-Authenticate header string.
8451
+ *
8452
+ * @param response The HTTP response object containing the headers.
8453
+ * @param fieldName The name of the field to extract (e.g., "realm", "nonce").
8454
+ * @returns The field value
8455
+ */
8456
+ function extractFieldFromWwwAuth(response, fieldName) {
8457
+ const wwwAuthHeader = response.headers.get("WWW-Authenticate");
8458
+ if (!wwwAuthHeader) return null;
8459
+ const pattern = new RegExp(`${fieldName}=(?:"([^"]+)"|([^\\s,]+))`);
8460
+ const match = wwwAuthHeader.match(pattern);
8461
+ if (match) return match[1] || match[2];
8462
+ return null;
8463
+ }
8464
+ /**
8465
+ * Looks up RFC 9728 OAuth 2.0 Protected Resource Metadata.
8466
+ *
8467
+ * If the server returns a 404 for the well-known endpoint, this function will
8468
+ * return `undefined`. Any other errors will be thrown as exceptions.
8469
+ */
8470
+ async function discoverOAuthProtectedResourceMetadata(serverUrl, opts, fetchFn = fetch) {
8471
+ const response = await discoverMetadataWithFallback(serverUrl, "oauth-protected-resource", fetchFn, {
8472
+ protocolVersion: opts?.protocolVersion,
8473
+ metadataUrl: opts?.resourceMetadataUrl
8474
+ });
8475
+ if (!response || response.status === 404) {
8476
+ await response?.body?.cancel();
8477
+ throw new Error(`Resource server does not implement OAuth 2.0 Protected Resource Metadata.`);
8478
+ }
8479
+ if (!response.ok) {
8480
+ await response.body?.cancel();
8481
+ throw new Error(`HTTP ${response.status} trying to load well-known OAuth protected resource metadata.`);
8482
+ }
8483
+ return OAuthProtectedResourceMetadataSchema.parse(await response.json());
8484
+ }
8485
+ /**
8486
+ * Helper function to handle fetch with CORS retry logic
8487
+ */
8488
+ async function fetchWithCorsRetry(url, headers, fetchFn = fetch) {
8489
+ try {
8490
+ return await fetchFn(url, { headers });
8491
+ } catch (error) {
8492
+ if (error instanceof TypeError) if (headers) return fetchWithCorsRetry(url, void 0, fetchFn);
8493
+ else return;
8494
+ throw error;
8495
+ }
8496
+ }
8497
+ /**
8498
+ * Constructs the well-known path for auth-related metadata discovery
8499
+ */
8500
+ function buildWellKnownPath(wellKnownPrefix, pathname = "", options = {}) {
8501
+ if (pathname.endsWith("/")) pathname = pathname.slice(0, -1);
8502
+ return options.prependPathname ? `${pathname}/.well-known/${wellKnownPrefix}` : `/.well-known/${wellKnownPrefix}${pathname}`;
8503
+ }
8504
+ /**
8505
+ * Tries to discover OAuth metadata at a specific URL
8506
+ */
8507
+ async function tryMetadataDiscovery(url, protocolVersion, fetchFn = fetch) {
8508
+ return await fetchWithCorsRetry(url, { "MCP-Protocol-Version": protocolVersion }, fetchFn);
8509
+ }
8510
+ /**
8511
+ * Determines if fallback to root discovery should be attempted
8512
+ */
8513
+ function shouldAttemptFallback(response, pathname) {
8514
+ return !response || response.status >= 400 && response.status < 500 && pathname !== "/";
8515
+ }
8516
+ /**
8517
+ * Generic function for discovering OAuth metadata with fallback support
8518
+ */
8519
+ async function discoverMetadataWithFallback(serverUrl, wellKnownType, fetchFn, opts) {
8520
+ const issuer = new URL(serverUrl);
8521
+ const protocolVersion = opts?.protocolVersion ?? "2025-11-25";
8522
+ let url;
8523
+ if (opts?.metadataUrl) url = new URL(opts.metadataUrl);
8524
+ else {
8525
+ const wellKnownPath = buildWellKnownPath(wellKnownType, issuer.pathname);
8526
+ url = new URL(wellKnownPath, opts?.metadataServerUrl ?? issuer);
8527
+ url.search = issuer.search;
8528
+ }
8529
+ let response = await tryMetadataDiscovery(url, protocolVersion, fetchFn);
8530
+ if (!opts?.metadataUrl && shouldAttemptFallback(response, issuer.pathname)) response = await tryMetadataDiscovery(new URL(`/.well-known/${wellKnownType}`, issuer), protocolVersion, fetchFn);
8531
+ return response;
8532
+ }
8533
+ /**
8534
+ * Builds a list of discovery URLs to try for authorization server metadata.
8535
+ * URLs are returned in priority order:
8536
+ * 1. OAuth metadata at the given URL
8537
+ * 2. OIDC metadata endpoints at the given URL
8538
+ */
8539
+ function buildDiscoveryUrls(authorizationServerUrl) {
8540
+ const url = typeof authorizationServerUrl === "string" ? new URL(authorizationServerUrl) : authorizationServerUrl;
8541
+ const hasPath = url.pathname !== "/";
8542
+ const urlsToTry = [];
8543
+ if (!hasPath) {
8544
+ urlsToTry.push({
8545
+ url: new URL("/.well-known/oauth-authorization-server", url.origin),
8546
+ type: "oauth"
8547
+ });
8548
+ urlsToTry.push({
8549
+ url: new URL(`/.well-known/openid-configuration`, url.origin),
8550
+ type: "oidc"
8551
+ });
8552
+ return urlsToTry;
8553
+ }
8554
+ let pathname = url.pathname;
8555
+ if (pathname.endsWith("/")) pathname = pathname.slice(0, -1);
8556
+ urlsToTry.push({
8557
+ url: new URL(`/.well-known/oauth-authorization-server${pathname}`, url.origin),
8558
+ type: "oauth"
8559
+ });
8560
+ urlsToTry.push({
8561
+ url: new URL(`/.well-known/openid-configuration${pathname}`, url.origin),
8562
+ type: "oidc"
8563
+ });
8564
+ urlsToTry.push({
8565
+ url: new URL(`${pathname}/.well-known/openid-configuration`, url.origin),
8566
+ type: "oidc"
8567
+ });
8568
+ return urlsToTry;
8569
+ }
8570
+ /**
8571
+ * Discovers authorization server metadata with support for RFC 8414 OAuth 2.0 Authorization Server Metadata
8572
+ * and OpenID Connect Discovery 1.0 specifications.
8573
+ *
8574
+ * This function implements a fallback strategy for authorization server discovery:
8575
+ * 1. Attempts RFC 8414 OAuth metadata discovery first
8576
+ * 2. If OAuth discovery fails, falls back to OpenID Connect Discovery
8577
+ *
8578
+ * @param authorizationServerUrl - The authorization server URL obtained from the MCP Server's
8579
+ * protected resource metadata, or the MCP server's URL if the
8580
+ * metadata was not found.
8581
+ * @param options - Configuration options
8582
+ * @param options.fetchFn - Optional fetch function for making HTTP requests, defaults to global fetch
8583
+ * @param options.protocolVersion - MCP protocol version to use, defaults to LATEST_PROTOCOL_VERSION
8584
+ * @returns Promise resolving to authorization server metadata, or undefined if discovery fails
8585
+ */
8586
+ async function discoverAuthorizationServerMetadata(authorizationServerUrl, { fetchFn = fetch, protocolVersion = LATEST_PROTOCOL_VERSION } = {}) {
8587
+ const headers = {
8588
+ "MCP-Protocol-Version": protocolVersion,
8589
+ Accept: "application/json"
8590
+ };
8591
+ const urlsToTry = buildDiscoveryUrls(authorizationServerUrl);
8592
+ for (const { url: endpointUrl, type } of urlsToTry) {
8593
+ const response = await fetchWithCorsRetry(endpointUrl, headers, fetchFn);
8594
+ if (!response)
8595
+ /**
8596
+ * CORS error occurred - don't throw as the endpoint may not allow CORS,
8597
+ * continue trying other possible endpoints
8598
+ */
8599
+ continue;
8600
+ if (!response.ok) {
8601
+ await response.body?.cancel();
8602
+ if (response.status >= 400 && response.status < 500) continue;
8603
+ throw new Error(`HTTP ${response.status} trying to load ${type === "oauth" ? "OAuth" : "OpenID provider"} metadata from ${endpointUrl}`);
8604
+ }
8605
+ if (type === "oauth") return OAuthMetadataSchema.parse(await response.json());
8606
+ else return OpenIdProviderDiscoveryMetadataSchema.parse(await response.json());
8607
+ }
8608
+ }
8609
+ /**
8610
+ * Discovers the authorization server for an MCP server following
8611
+ * {@link https://datatracker.ietf.org/doc/html/rfc9728 | RFC 9728} (OAuth 2.0 Protected
8612
+ * Resource Metadata), with fallback to treating the server URL as the
8613
+ * authorization server.
8614
+ *
8615
+ * This function combines two discovery steps into one call:
8616
+ * 1. Probes `/.well-known/oauth-protected-resource` on the MCP server to find the
8617
+ * authorization server URL (RFC 9728).
8618
+ * 2. Fetches authorization server metadata from that URL (RFC 8414 / OpenID Connect Discovery).
8619
+ *
8620
+ * Use this when you need the authorization server metadata for operations outside the
8621
+ * {@linkcode auth} orchestrator, such as token refresh or token revocation.
8622
+ *
8623
+ * @param serverUrl - The MCP resource server URL
8624
+ * @param opts - Optional configuration
8625
+ * @param opts.resourceMetadataUrl - Override URL for the protected resource metadata endpoint
8626
+ * @param opts.fetchFn - Custom fetch function for HTTP requests
8627
+ * @returns Authorization server URL, metadata, and resource metadata (if available)
8628
+ */
8629
+ async function discoverOAuthServerInfo(serverUrl, opts) {
8630
+ let resourceMetadata;
8631
+ let authorizationServerUrl;
8632
+ try {
8633
+ resourceMetadata = await discoverOAuthProtectedResourceMetadata(serverUrl, { resourceMetadataUrl: opts?.resourceMetadataUrl }, opts?.fetchFn);
8634
+ if (resourceMetadata.authorization_servers && resourceMetadata.authorization_servers.length > 0) authorizationServerUrl = resourceMetadata.authorization_servers[0];
8635
+ } catch {}
8636
+ if (!authorizationServerUrl) authorizationServerUrl = String(new URL("/", serverUrl));
8637
+ const authorizationServerMetadata = await discoverAuthorizationServerMetadata(authorizationServerUrl, { fetchFn: opts?.fetchFn });
8638
+ return {
8639
+ authorizationServerUrl,
8640
+ authorizationServerMetadata,
8641
+ resourceMetadata
8642
+ };
8643
+ }
8644
+ /**
8645
+ * Begins the authorization flow with the given server, by generating a PKCE challenge and constructing the authorization URL.
8646
+ */
8647
+ async function startAuthorization(authorizationServerUrl, { metadata, clientInformation, redirectUrl, scope, state, resource }) {
8648
+ let authorizationUrl;
8649
+ if (metadata) {
8650
+ authorizationUrl = new URL(metadata.authorization_endpoint);
8651
+ if (!metadata.response_types_supported.includes(AUTHORIZATION_CODE_RESPONSE_TYPE)) throw new Error(`Incompatible auth server: does not support response type ${AUTHORIZATION_CODE_RESPONSE_TYPE}`);
8652
+ if (metadata.code_challenge_methods_supported && !metadata.code_challenge_methods_supported.includes(AUTHORIZATION_CODE_CHALLENGE_METHOD)) throw new Error(`Incompatible auth server: does not support code challenge method ${AUTHORIZATION_CODE_CHALLENGE_METHOD}`);
8653
+ } else authorizationUrl = new URL("/authorize", authorizationServerUrl);
8654
+ const challenge = await pkceChallenge();
8655
+ const codeVerifier = challenge.code_verifier;
8656
+ const codeChallenge = challenge.code_challenge;
8657
+ authorizationUrl.searchParams.set("response_type", AUTHORIZATION_CODE_RESPONSE_TYPE);
8658
+ authorizationUrl.searchParams.set("client_id", clientInformation.client_id);
8659
+ authorizationUrl.searchParams.set("code_challenge", codeChallenge);
8660
+ authorizationUrl.searchParams.set("code_challenge_method", AUTHORIZATION_CODE_CHALLENGE_METHOD);
8661
+ authorizationUrl.searchParams.set("redirect_uri", String(redirectUrl));
8662
+ if (state) authorizationUrl.searchParams.set("state", state);
8663
+ if (scope) authorizationUrl.searchParams.set("scope", scope);
8664
+ if (scope?.includes("offline_access")) authorizationUrl.searchParams.append("prompt", "consent");
8665
+ if (resource) authorizationUrl.searchParams.set("resource", resource.href);
8666
+ return {
8667
+ authorizationUrl,
8668
+ codeVerifier
8669
+ };
8670
+ }
8671
+ /**
8672
+ * Prepares token request parameters for an authorization code exchange.
8673
+ *
8674
+ * This is the default implementation used by fetchToken when the provider
8675
+ * doesn't implement prepareTokenRequest.
8676
+ *
8677
+ * @param authorizationCode - The authorization code received from the authorization endpoint
8678
+ * @param codeVerifier - The PKCE code verifier
8679
+ * @param redirectUri - The redirect URI used in the authorization request
8680
+ * @returns URLSearchParams for the authorization_code grant
8681
+ */
8682
+ function prepareAuthorizationCodeRequest(authorizationCode, codeVerifier, redirectUri) {
8683
+ return new URLSearchParams({
8684
+ grant_type: "authorization_code",
8685
+ code: authorizationCode,
8686
+ code_verifier: codeVerifier,
8687
+ redirect_uri: String(redirectUri)
8688
+ });
8689
+ }
8690
+ /**
8691
+ * Internal helper to execute a token request with the given parameters.
8692
+ * Used by exchangeAuthorization, refreshAuthorization, and fetchToken.
8693
+ */
8694
+ async function executeTokenRequest(authorizationServerUrl, { metadata, tokenRequestParams, clientInformation, addClientAuthentication, resource, fetchFn }) {
8695
+ const tokenUrl = metadata?.token_endpoint ? new URL(metadata.token_endpoint) : new URL("/token", authorizationServerUrl);
8696
+ const headers = new Headers({
8697
+ "Content-Type": "application/x-www-form-urlencoded",
8698
+ Accept: "application/json"
8699
+ });
8700
+ if (resource) tokenRequestParams.set("resource", resource.href);
8701
+ if (addClientAuthentication) await addClientAuthentication(headers, tokenRequestParams, tokenUrl, metadata);
8702
+ else if (clientInformation) applyClientAuthentication(selectClientAuthMethod(clientInformation, metadata?.token_endpoint_auth_methods_supported ?? []), clientInformation, headers, tokenRequestParams);
8703
+ const response = await (fetchFn ?? fetch)(tokenUrl, {
8704
+ method: "POST",
8705
+ headers,
8706
+ body: tokenRequestParams
8707
+ });
8708
+ if (!response.ok) throw await parseErrorResponse(response);
8709
+ return OAuthTokensSchema.parse(await response.json());
8710
+ }
8711
+ /**
8712
+ * Exchange a refresh token for an updated access token.
8713
+ *
8714
+ * Supports multiple client authentication methods as specified in OAuth 2.1:
8715
+ * - Automatically selects the best authentication method based on server support
8716
+ * - Preserves the original refresh token if a new one is not returned
8717
+ *
8718
+ * @param authorizationServerUrl - The authorization server's base URL
8719
+ * @param options - Configuration object containing client info, refresh token, etc.
8720
+ * @returns Promise resolving to OAuth tokens (preserves original refresh_token if not replaced)
8721
+ * @throws {Error} When token refresh fails or authentication is invalid
8722
+ */
8723
+ async function refreshAuthorization(authorizationServerUrl, { metadata, clientInformation, refreshToken, resource, addClientAuthentication, fetchFn }) {
8724
+ return {
8725
+ refresh_token: refreshToken,
8726
+ ...await executeTokenRequest(authorizationServerUrl, {
8727
+ metadata,
8728
+ tokenRequestParams: new URLSearchParams({
8729
+ grant_type: "refresh_token",
8730
+ refresh_token: refreshToken
8731
+ }),
8732
+ clientInformation,
8733
+ addClientAuthentication,
8734
+ resource,
8735
+ fetchFn
8736
+ })
8737
+ };
8738
+ }
8739
+ /**
8740
+ * Unified token fetching that works with any grant type via provider.prepareTokenRequest().
8741
+ *
8742
+ * This function provides a single entry point for obtaining tokens regardless of the
8743
+ * OAuth grant type. The provider's prepareTokenRequest() method determines which grant
8744
+ * to use and supplies the grant-specific parameters.
8745
+ *
8746
+ * @param provider - OAuth client provider that implements prepareTokenRequest()
8747
+ * @param authorizationServerUrl - The authorization server's base URL
8748
+ * @param options - Configuration for the token request
8749
+ * @returns Promise resolving to OAuth tokens
8750
+ * @throws {Error} When provider doesn't implement prepareTokenRequest or token fetch fails
8751
+ *
8752
+ * @example
8753
+ * // Provider for client_credentials:
8754
+ * class MyProvider implements OAuthClientProvider {
8755
+ * prepareTokenRequest(scope) {
8756
+ * const params = new URLSearchParams({ grant_type: 'client_credentials' });
8757
+ * if (scope) params.set('scope', scope);
8758
+ * return params;
8759
+ * }
8760
+ * // ... other methods
8761
+ * }
8762
+ *
8763
+ * const tokens = await fetchToken(provider, authServerUrl, { metadata });
8764
+ */
8765
+ async function fetchToken(provider, authorizationServerUrl, { metadata, resource, authorizationCode, fetchFn } = {}) {
8766
+ const scope = provider.clientMetadata.scope;
8767
+ let tokenRequestParams;
8768
+ if (provider.prepareTokenRequest) tokenRequestParams = await provider.prepareTokenRequest(scope);
8769
+ if (!tokenRequestParams) {
8770
+ if (!authorizationCode) throw new Error("Either provider.prepareTokenRequest() or authorizationCode is required");
8771
+ if (!provider.redirectUrl) throw new Error("redirectUrl is required for authorization_code flow");
8772
+ tokenRequestParams = prepareAuthorizationCodeRequest(authorizationCode, await provider.codeVerifier(), provider.redirectUrl);
8773
+ }
8774
+ const clientInformation = await provider.clientInformation();
8775
+ return executeTokenRequest(authorizationServerUrl, {
8776
+ metadata,
8777
+ tokenRequestParams,
8778
+ clientInformation: clientInformation ?? void 0,
8779
+ addClientAuthentication: provider.addClientAuthentication,
8780
+ resource,
8781
+ fetchFn
8782
+ });
8783
+ }
8784
+ /**
8785
+ * Performs OAuth 2.0 Dynamic Client Registration according to RFC 7591.
8786
+ *
8787
+ * If `scope` is provided, it overrides `clientMetadata.scope` in the registration
8788
+ * request body. This allows callers to apply the Scope Selection Strategy (SEP-835)
8789
+ * consistently across both DCR and the subsequent authorization request.
8790
+ */
8791
+ async function registerClient(authorizationServerUrl, { metadata, clientMetadata, scope, fetchFn }) {
8792
+ let registrationUrl;
8793
+ if (metadata) {
8794
+ if (!metadata.registration_endpoint) throw new Error("Incompatible auth server: does not support dynamic client registration");
8795
+ registrationUrl = new URL(metadata.registration_endpoint);
8796
+ } else registrationUrl = new URL("/register", authorizationServerUrl);
8797
+ const response = await (fetchFn ?? fetch)(registrationUrl, {
8798
+ method: "POST",
8799
+ headers: { "Content-Type": "application/json" },
8800
+ body: JSON.stringify({
8801
+ ...clientMetadata,
8802
+ ...scope !== void 0 ? { scope } : {}
8803
+ })
8804
+ });
8805
+ if (!response.ok) throw await parseErrorResponse(response);
8806
+ return OAuthClientInformationFullSchema.parse(await response.json());
8807
+ }
8808
+ //#endregion
8809
+ //#region ../../node_modules/.pnpm/eventsource-parser@3.1.0/node_modules/eventsource-parser/dist/index.js
8810
+ var ParseError = class extends Error {
8811
+ constructor(message, options) {
8812
+ super(message), this.name = "ParseError", this.type = options.type, this.field = options.field, this.value = options.value, this.line = options.line;
8813
+ }
8814
+ };
8815
+ const LF = 10, CR = 13, SPACE = 32;
8816
+ function noop(_arg) {}
8817
+ function createParser(config) {
8818
+ if (typeof config == "function") throw new TypeError("`config` must be an object, got a function instead. Did you mean `createParser({onEvent: fn})`?");
8819
+ const { onEvent = noop, onError = noop, onRetry = noop, onComment, maxBufferSize } = config, pendingFragments = [];
8820
+ let pendingFragmentsLength = 0, isFirstChunk = !0, id, data = "", dataLines = 0, eventType, terminated = !1;
8821
+ function feed(chunk) {
8822
+ if (terminated) throw new Error("Cannot feed parser: it was terminated after exceeding the configured max buffer size. Call `reset()` to resume parsing.");
8823
+ if (isFirstChunk && (isFirstChunk = !1, chunk.charCodeAt(0) === 239 && chunk.charCodeAt(1) === 187 && chunk.charCodeAt(2) === 191 && (chunk = chunk.slice(3))), pendingFragments.length === 0) {
8824
+ const trailing2 = processLines(chunk);
8825
+ trailing2 !== "" && (pendingFragments.push(trailing2), pendingFragmentsLength = trailing2.length), checkBufferSize();
8826
+ return;
8827
+ }
8828
+ if (chunk.indexOf(`
8829
+ `) === -1 && chunk.indexOf("\r") === -1) {
8830
+ pendingFragments.push(chunk), pendingFragmentsLength += chunk.length, checkBufferSize();
8831
+ return;
8832
+ }
8833
+ pendingFragments.push(chunk);
8834
+ const input = pendingFragments.join("");
8835
+ pendingFragments.length = 0, pendingFragmentsLength = 0;
8836
+ const trailing = processLines(input);
8837
+ trailing !== "" && (pendingFragments.push(trailing), pendingFragmentsLength = trailing.length), checkBufferSize();
8838
+ }
8839
+ function checkBufferSize() {
8840
+ maxBufferSize !== void 0 && (pendingFragmentsLength + data.length <= maxBufferSize || (terminated = !0, pendingFragments.length = 0, pendingFragmentsLength = 0, id = void 0, data = "", dataLines = 0, eventType = void 0, onError(new ParseError(`Buffered data exceeded max buffer size of ${maxBufferSize} characters`, { type: "max-buffer-size-exceeded" }))));
8841
+ }
8842
+ function processLines(chunk) {
8843
+ let searchIndex = 0;
8844
+ if (chunk.indexOf("\r") === -1) {
8845
+ let lfIndex = chunk.indexOf(`
8846
+ `, searchIndex);
8847
+ for (; lfIndex !== -1;) {
8848
+ if (searchIndex === lfIndex) {
8849
+ dataLines > 0 && onEvent({
8850
+ id,
8851
+ event: eventType,
8852
+ data
8853
+ }), id = void 0, data = "", dataLines = 0, eventType = void 0, searchIndex = lfIndex + 1, lfIndex = chunk.indexOf(`
8854
+ `, searchIndex);
8855
+ continue;
8856
+ }
8857
+ const firstCharCode = chunk.charCodeAt(searchIndex);
8858
+ if (isDataPrefix(chunk, searchIndex, firstCharCode)) {
8859
+ const valueStart = chunk.charCodeAt(searchIndex + 5) === SPACE ? searchIndex + 6 : searchIndex + 5, value = chunk.slice(valueStart, lfIndex);
8860
+ if (dataLines === 0 && chunk.charCodeAt(lfIndex + 1) === LF) {
8861
+ onEvent({
8862
+ id,
8863
+ event: eventType,
8864
+ data: value
8865
+ }), id = void 0, data = "", eventType = void 0, searchIndex = lfIndex + 2, lfIndex = chunk.indexOf(`
8866
+ `, searchIndex);
8867
+ continue;
8868
+ }
8869
+ data = dataLines === 0 ? value : `${data}
8870
+ ${value}`, dataLines++;
8871
+ } else isEventPrefix(chunk, searchIndex, firstCharCode) ? eventType = chunk.slice(chunk.charCodeAt(searchIndex + 6) === SPACE ? searchIndex + 7 : searchIndex + 6, lfIndex) || void 0 : parseLine(chunk, searchIndex, lfIndex);
8872
+ searchIndex = lfIndex + 1, lfIndex = chunk.indexOf(`
8873
+ `, searchIndex);
8874
+ }
8875
+ return chunk.slice(searchIndex);
8876
+ }
8877
+ for (; searchIndex < chunk.length;) {
8878
+ const crIndex = chunk.indexOf("\r", searchIndex), lfIndex = chunk.indexOf(`
8879
+ `, searchIndex);
8880
+ let lineEnd = -1;
8881
+ if (crIndex !== -1 && lfIndex !== -1 ? lineEnd = crIndex < lfIndex ? crIndex : lfIndex : crIndex !== -1 ? crIndex === chunk.length - 1 ? lineEnd = -1 : lineEnd = crIndex : lfIndex !== -1 && (lineEnd = lfIndex), lineEnd === -1) break;
8882
+ parseLine(chunk, searchIndex, lineEnd), searchIndex = lineEnd + 1, chunk.charCodeAt(searchIndex - 1) === CR && chunk.charCodeAt(searchIndex) === LF && searchIndex++;
8883
+ }
8884
+ return chunk.slice(searchIndex);
8885
+ }
8886
+ function parseLine(chunk, start, end) {
8887
+ if (start === end) {
8888
+ dispatchEvent();
8889
+ return;
8890
+ }
8891
+ const firstCharCode = chunk.charCodeAt(start);
8892
+ if (isDataPrefix(chunk, start, firstCharCode)) {
8893
+ const valueStart = chunk.charCodeAt(start + 5) === SPACE ? start + 6 : start + 5, value2 = chunk.slice(valueStart, end);
8894
+ data = dataLines === 0 ? value2 : `${data}
8895
+ ${value2}`, dataLines++;
8896
+ return;
8897
+ }
8898
+ if (isEventPrefix(chunk, start, firstCharCode)) {
8899
+ eventType = chunk.slice(chunk.charCodeAt(start + 6) === SPACE ? start + 7 : start + 6, end) || void 0;
8900
+ return;
8901
+ }
8902
+ if (firstCharCode === 105 && chunk.charCodeAt(start + 1) === 100 && chunk.charCodeAt(start + 2) === 58) {
8903
+ const value2 = chunk.slice(chunk.charCodeAt(start + 3) === SPACE ? start + 4 : start + 3, end);
8904
+ id = value2.includes("\0") ? void 0 : value2;
8905
+ return;
8906
+ }
8907
+ if (firstCharCode === 58) {
8908
+ if (onComment) {
8909
+ const line2 = chunk.slice(start, end);
8910
+ onComment(line2.slice(chunk.charCodeAt(start + 1) === SPACE ? 2 : 1));
8911
+ }
8912
+ return;
8913
+ }
8914
+ const line = chunk.slice(start, end), fieldSeparatorIndex = line.indexOf(":");
8915
+ if (fieldSeparatorIndex === -1) {
8916
+ processField(line, "", line);
8917
+ return;
8918
+ }
8919
+ const field = line.slice(0, fieldSeparatorIndex), offset = line.charCodeAt(fieldSeparatorIndex + 1) === SPACE ? 2 : 1;
8920
+ processField(field, line.slice(fieldSeparatorIndex + offset), line);
8921
+ }
8922
+ function processField(field, value, line) {
8923
+ switch (field) {
8924
+ case "event":
8925
+ eventType = value || void 0;
8926
+ break;
8927
+ case "data":
8928
+ data = dataLines === 0 ? value : `${data}
8929
+ ${value}`, dataLines++;
8930
+ break;
8931
+ case "id":
8932
+ id = value.includes("\0") ? void 0 : value;
8933
+ break;
8934
+ case "retry":
8935
+ /^\d+$/.test(value) ? onRetry(parseInt(value, 10)) : onError(new ParseError(`Invalid \`retry\` value: "${value}"`, {
8936
+ type: "invalid-retry",
8937
+ value,
8938
+ line
8939
+ }));
8940
+ break;
8941
+ default:
8942
+ onError(new ParseError(`Unknown field "${field.length > 20 ? `${field.slice(0, 20)}\u2026` : field}"`, {
8943
+ type: "unknown-field",
8944
+ field,
8945
+ value,
8946
+ line
8947
+ }));
8948
+ break;
8949
+ }
8950
+ }
8951
+ function dispatchEvent() {
8952
+ dataLines > 0 && onEvent({
8953
+ id,
8954
+ event: eventType,
8955
+ data
8956
+ }), id = void 0, data = "", dataLines = 0, eventType = void 0;
8957
+ }
8958
+ function reset(options = {}) {
8959
+ if (options.consume && pendingFragments.length > 0) {
8960
+ const incompleteLine = pendingFragments.join("");
8961
+ parseLine(incompleteLine, 0, incompleteLine.length);
8962
+ }
8963
+ isFirstChunk = !0, id = void 0, data = "", dataLines = 0, eventType = void 0, pendingFragments.length = 0, pendingFragmentsLength = 0, terminated = !1;
8964
+ }
8965
+ return {
8966
+ feed,
8967
+ reset
8968
+ };
8969
+ }
8970
+ function isDataPrefix(chunk, i, firstCharCode) {
8971
+ return firstCharCode === 100 && chunk.charCodeAt(i + 1) === 97 && chunk.charCodeAt(i + 2) === 116 && chunk.charCodeAt(i + 3) === 97 && chunk.charCodeAt(i + 4) === 58;
8972
+ }
8973
+ function isEventPrefix(chunk, i, firstCharCode) {
8974
+ return firstCharCode === 101 && chunk.charCodeAt(i + 1) === 118 && chunk.charCodeAt(i + 2) === 101 && chunk.charCodeAt(i + 3) === 110 && chunk.charCodeAt(i + 4) === 116 && chunk.charCodeAt(i + 5) === 58;
8975
+ }
8976
+ //#endregion
8977
+ //#region ../../node_modules/.pnpm/eventsource-parser@3.1.0/node_modules/eventsource-parser/dist/stream.js
8978
+ var EventSourceParserStream = class extends TransformStream {
8979
+ constructor({ onError, onRetry, onComment, maxBufferSize } = {}) {
8980
+ let parser;
8981
+ super({
8982
+ start(controller) {
8983
+ parser = createParser({
8984
+ onEvent: (event) => {
8985
+ controller.enqueue(event);
8986
+ },
8987
+ onError(error) {
8988
+ typeof onError == "function" && onError(error), (onError === "terminate" || error.type === "max-buffer-size-exceeded") && controller.error(error);
8989
+ },
8990
+ onRetry,
8991
+ onComment,
8992
+ maxBufferSize
8993
+ });
8994
+ },
8995
+ transform(chunk) {
8996
+ parser.feed(chunk);
8997
+ }
8998
+ });
8999
+ }
9000
+ };
9001
+ //#endregion
9002
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/client/streamableHttp.js
9003
+ const DEFAULT_STREAMABLE_HTTP_RECONNECTION_OPTIONS = {
9004
+ initialReconnectionDelay: 1e3,
9005
+ maxReconnectionDelay: 3e4,
9006
+ reconnectionDelayGrowFactor: 1.5,
9007
+ maxRetries: 2
9008
+ };
9009
+ var StreamableHTTPError = class extends Error {
9010
+ constructor(code, message) {
9011
+ super(`Streamable HTTP error: ${message}`);
9012
+ this.code = code;
9013
+ }
9014
+ };
9015
+ /**
9016
+ * Client transport for Streamable HTTP: this implements the MCP Streamable HTTP transport specification.
9017
+ * It will connect to a server using HTTP POST for sending messages and HTTP GET with Server-Sent Events
9018
+ * for receiving messages.
9019
+ */
9020
+ var StreamableHTTPClientTransport = class {
9021
+ constructor(url, opts) {
9022
+ this._hasCompletedAuthFlow = false;
9023
+ this._url = url;
9024
+ this._resourceMetadataUrl = void 0;
9025
+ this._scope = void 0;
9026
+ this._requestInit = opts?.requestInit;
9027
+ this._authProvider = opts?.authProvider;
9028
+ this._fetch = opts?.fetch;
9029
+ this._fetchWithInit = createFetchWithInit(opts?.fetch, opts?.requestInit);
9030
+ this._sessionId = opts?.sessionId;
9031
+ this._reconnectionOptions = opts?.reconnectionOptions ?? DEFAULT_STREAMABLE_HTTP_RECONNECTION_OPTIONS;
9032
+ }
9033
+ async _authThenStart() {
9034
+ if (!this._authProvider) throw new UnauthorizedError("No auth provider");
9035
+ let result;
9036
+ try {
9037
+ result = await auth(this._authProvider, {
9038
+ serverUrl: this._url,
9039
+ resourceMetadataUrl: this._resourceMetadataUrl,
9040
+ scope: this._scope,
9041
+ fetchFn: this._fetchWithInit
9042
+ });
9043
+ } catch (error) {
9044
+ this.onerror?.(error);
9045
+ throw error;
9046
+ }
9047
+ if (result !== "AUTHORIZED") throw new UnauthorizedError();
9048
+ return await this._startOrAuthSse({ resumptionToken: void 0 });
9049
+ }
9050
+ async _commonHeaders() {
9051
+ const headers = {};
9052
+ if (this._authProvider) {
9053
+ const tokens = await this._authProvider.tokens();
9054
+ if (tokens) headers["Authorization"] = `Bearer ${tokens.access_token}`;
9055
+ }
9056
+ if (this._sessionId) headers["mcp-session-id"] = this._sessionId;
9057
+ if (this._protocolVersion) headers["mcp-protocol-version"] = this._protocolVersion;
9058
+ const extraHeaders = normalizeHeaders(this._requestInit?.headers);
9059
+ return new Headers({
9060
+ ...headers,
9061
+ ...extraHeaders
9062
+ });
9063
+ }
9064
+ async _startOrAuthSse(options) {
9065
+ const { resumptionToken } = options;
9066
+ try {
9067
+ const headers = await this._commonHeaders();
9068
+ headers.set("Accept", "text/event-stream");
9069
+ if (resumptionToken) headers.set("last-event-id", resumptionToken);
9070
+ const response = await (this._fetch ?? fetch)(this._url, {
9071
+ method: "GET",
9072
+ headers,
9073
+ signal: this._abortController?.signal
9074
+ });
9075
+ if (!response.ok) {
9076
+ await response.body?.cancel();
9077
+ if (response.status === 401 && this._authProvider) return await this._authThenStart();
9078
+ if (response.status === 405) return;
9079
+ throw new StreamableHTTPError(response.status, `Failed to open SSE stream: ${response.statusText}`);
9080
+ }
9081
+ this._handleSseStream(response.body, options, true);
9082
+ } catch (error) {
9083
+ this.onerror?.(error);
9084
+ throw error;
9085
+ }
9086
+ }
9087
+ /**
9088
+ * Calculates the next reconnection delay using backoff algorithm
9089
+ *
9090
+ * @param attempt Current reconnection attempt count for the specific stream
9091
+ * @returns Time to wait in milliseconds before next reconnection attempt
9092
+ */
9093
+ _getNextReconnectionDelay(attempt) {
9094
+ if (this._serverRetryMs !== void 0) return this._serverRetryMs;
9095
+ const initialDelay = this._reconnectionOptions.initialReconnectionDelay;
9096
+ const growFactor = this._reconnectionOptions.reconnectionDelayGrowFactor;
9097
+ const maxDelay = this._reconnectionOptions.maxReconnectionDelay;
9098
+ return Math.min(initialDelay * Math.pow(growFactor, attempt), maxDelay);
9099
+ }
9100
+ /**
9101
+ * Schedule a reconnection attempt using server-provided retry interval or backoff
9102
+ *
9103
+ * @param lastEventId The ID of the last received event for resumability
9104
+ * @param attemptCount Current reconnection attempt count for this specific stream
9105
+ */
9106
+ _scheduleReconnection(options, attemptCount = 0) {
9107
+ const maxRetries = this._reconnectionOptions.maxRetries;
9108
+ if (attemptCount >= maxRetries) {
9109
+ this.onerror?.(/* @__PURE__ */ new Error(`Maximum reconnection attempts (${maxRetries}) exceeded.`));
9110
+ return;
9111
+ }
9112
+ const delay = this._getNextReconnectionDelay(attemptCount);
9113
+ this._reconnectionTimeout = setTimeout(() => {
9114
+ this._startOrAuthSse(options).catch((error) => {
9115
+ this.onerror?.(/* @__PURE__ */ new Error(`Failed to reconnect SSE stream: ${error instanceof Error ? error.message : String(error)}`));
9116
+ this._scheduleReconnection(options, attemptCount + 1);
9117
+ });
9118
+ }, delay);
9119
+ }
9120
+ _handleSseStream(stream, options, isReconnectable) {
9121
+ if (!stream) return;
9122
+ const { onresumptiontoken, replayMessageId } = options;
9123
+ let lastEventId;
9124
+ let hasPrimingEvent = false;
9125
+ let receivedResponse = false;
9126
+ const processStream = async () => {
9127
+ try {
9128
+ const reader = stream.pipeThrough(new TextDecoderStream()).pipeThrough(new EventSourceParserStream({ onRetry: (retryMs) => {
9129
+ this._serverRetryMs = retryMs;
9130
+ } })).getReader();
9131
+ while (true) {
9132
+ const { value: event, done } = await reader.read();
9133
+ if (done) break;
9134
+ if (event.id) {
9135
+ lastEventId = event.id;
9136
+ hasPrimingEvent = true;
9137
+ onresumptiontoken?.(event.id);
9138
+ }
9139
+ if (!event.data) continue;
9140
+ if (!event.event || event.event === "message") try {
9141
+ const message = JSONRPCMessageSchema.parse(JSON.parse(event.data));
9142
+ if (isJSONRPCResultResponse(message)) {
9143
+ receivedResponse = true;
9144
+ if (replayMessageId !== void 0) message.id = replayMessageId;
9145
+ }
9146
+ this.onmessage?.(message);
9147
+ } catch (error) {
9148
+ this.onerror?.(error);
9149
+ }
9150
+ }
9151
+ if ((isReconnectable || hasPrimingEvent) && !receivedResponse && this._abortController && !this._abortController.signal.aborted) this._scheduleReconnection({
9152
+ resumptionToken: lastEventId,
9153
+ onresumptiontoken,
9154
+ replayMessageId
9155
+ }, 0);
9156
+ } catch (error) {
9157
+ this.onerror?.(/* @__PURE__ */ new Error(`SSE stream disconnected: ${error}`));
9158
+ if ((isReconnectable || hasPrimingEvent) && !receivedResponse && this._abortController && !this._abortController.signal.aborted) try {
9159
+ this._scheduleReconnection({
9160
+ resumptionToken: lastEventId,
9161
+ onresumptiontoken,
9162
+ replayMessageId
9163
+ }, 0);
9164
+ } catch (error) {
9165
+ this.onerror?.(/* @__PURE__ */ new Error(`Failed to reconnect: ${error instanceof Error ? error.message : String(error)}`));
9166
+ }
9167
+ }
9168
+ };
9169
+ processStream();
9170
+ }
9171
+ async start() {
9172
+ if (this._abortController) throw new Error("StreamableHTTPClientTransport already started! If using Client class, note that connect() calls start() automatically.");
9173
+ this._abortController = new AbortController();
9174
+ }
9175
+ /**
9176
+ * Call this method after the user has finished authorizing via their user agent and is redirected back to the MCP client application. This will exchange the authorization code for an access token, enabling the next connection attempt to successfully auth.
9177
+ */
9178
+ async finishAuth(authorizationCode) {
9179
+ if (!this._authProvider) throw new UnauthorizedError("No auth provider");
9180
+ if (await auth(this._authProvider, {
9181
+ serverUrl: this._url,
9182
+ authorizationCode,
9183
+ resourceMetadataUrl: this._resourceMetadataUrl,
9184
+ scope: this._scope,
9185
+ fetchFn: this._fetchWithInit
9186
+ }) !== "AUTHORIZED") throw new UnauthorizedError("Failed to authorize");
9187
+ }
9188
+ async close() {
9189
+ if (this._reconnectionTimeout) {
9190
+ clearTimeout(this._reconnectionTimeout);
9191
+ this._reconnectionTimeout = void 0;
9192
+ }
9193
+ this._abortController?.abort();
9194
+ this.onclose?.();
9195
+ }
9196
+ async send(message, options) {
9197
+ try {
9198
+ const { resumptionToken, onresumptiontoken } = options || {};
9199
+ if (resumptionToken) {
9200
+ this._startOrAuthSse({
9201
+ resumptionToken,
9202
+ replayMessageId: isJSONRPCRequest(message) ? message.id : void 0
9203
+ }).catch((err) => this.onerror?.(err));
9204
+ return;
9205
+ }
9206
+ const headers = await this._commonHeaders();
9207
+ headers.set("content-type", "application/json");
9208
+ headers.set("accept", "application/json, text/event-stream");
9209
+ const init = {
9210
+ ...this._requestInit,
9211
+ method: "POST",
9212
+ headers,
9213
+ body: JSON.stringify(message),
9214
+ signal: this._abortController?.signal
9215
+ };
9216
+ const response = await (this._fetch ?? fetch)(this._url, init);
9217
+ const sessionId = response.headers.get("mcp-session-id");
9218
+ if (sessionId) this._sessionId = sessionId;
9219
+ if (!response.ok) {
9220
+ const text = await response.text().catch(() => null);
9221
+ if (response.status === 401 && this._authProvider) {
9222
+ if (this._hasCompletedAuthFlow) throw new StreamableHTTPError(401, "Server returned 401 after successful authentication");
9223
+ const { resourceMetadataUrl, scope } = extractWWWAuthenticateParams(response);
9224
+ this._resourceMetadataUrl = resourceMetadataUrl;
9225
+ this._scope = scope;
9226
+ if (await auth(this._authProvider, {
9227
+ serverUrl: this._url,
9228
+ resourceMetadataUrl: this._resourceMetadataUrl,
9229
+ scope: this._scope,
9230
+ fetchFn: this._fetchWithInit
9231
+ }) !== "AUTHORIZED") throw new UnauthorizedError();
9232
+ this._hasCompletedAuthFlow = true;
9233
+ return this.send(message);
9234
+ }
9235
+ if (response.status === 403 && this._authProvider) {
9236
+ const { resourceMetadataUrl, scope, error } = extractWWWAuthenticateParams(response);
9237
+ if (error === "insufficient_scope") {
9238
+ const wwwAuthHeader = response.headers.get("WWW-Authenticate");
9239
+ if (this._lastUpscopingHeader === wwwAuthHeader) throw new StreamableHTTPError(403, "Server returned 403 after trying upscoping");
9240
+ if (scope) this._scope = scope;
9241
+ if (resourceMetadataUrl) this._resourceMetadataUrl = resourceMetadataUrl;
9242
+ this._lastUpscopingHeader = wwwAuthHeader ?? void 0;
9243
+ if (await auth(this._authProvider, {
9244
+ serverUrl: this._url,
9245
+ resourceMetadataUrl: this._resourceMetadataUrl,
9246
+ scope: this._scope,
9247
+ fetchFn: this._fetch
9248
+ }) !== "AUTHORIZED") throw new UnauthorizedError();
9249
+ return this.send(message);
9250
+ }
9251
+ }
9252
+ throw new StreamableHTTPError(response.status, `Error POSTing to endpoint: ${text}`);
9253
+ }
9254
+ this._hasCompletedAuthFlow = false;
9255
+ this._lastUpscopingHeader = void 0;
9256
+ if (response.status === 202) {
9257
+ await response.body?.cancel();
9258
+ if (isInitializedNotification(message)) this._startOrAuthSse({ resumptionToken: void 0 }).catch((err) => this.onerror?.(err));
9259
+ return;
9260
+ }
9261
+ const hasRequests = (Array.isArray(message) ? message : [message]).filter((msg) => "method" in msg && "id" in msg && msg.id !== void 0).length > 0;
9262
+ const contentType = response.headers.get("content-type");
9263
+ if (hasRequests) if (contentType?.includes("text/event-stream")) this._handleSseStream(response.body, { onresumptiontoken }, false);
9264
+ else if (contentType?.includes("application/json")) {
9265
+ const data = await response.json();
9266
+ const responseMessages = Array.isArray(data) ? data.map((msg) => JSONRPCMessageSchema.parse(msg)) : [JSONRPCMessageSchema.parse(data)];
9267
+ for (const msg of responseMessages) this.onmessage?.(msg);
9268
+ } else {
9269
+ await response.body?.cancel();
9270
+ throw new StreamableHTTPError(-1, `Unexpected content type: ${contentType}`);
9271
+ }
9272
+ else await response.body?.cancel();
9273
+ } catch (error) {
9274
+ this.onerror?.(error);
9275
+ throw error;
9276
+ }
9277
+ }
9278
+ get sessionId() {
9279
+ return this._sessionId;
9280
+ }
9281
+ /**
9282
+ * Terminates the current session by sending a DELETE request to the server.
9283
+ *
9284
+ * Clients that no longer need a particular session
9285
+ * (e.g., because the user is leaving the client application) SHOULD send an
9286
+ * HTTP DELETE to the MCP endpoint with the Mcp-Session-Id header to explicitly
9287
+ * terminate the session.
9288
+ *
9289
+ * The server MAY respond with HTTP 405 Method Not Allowed, indicating that
9290
+ * the server does not allow clients to terminate sessions.
9291
+ */
9292
+ async terminateSession() {
9293
+ if (!this._sessionId) return;
9294
+ try {
9295
+ const headers = await this._commonHeaders();
9296
+ const init = {
9297
+ ...this._requestInit,
9298
+ method: "DELETE",
9299
+ headers,
9300
+ signal: this._abortController?.signal
9301
+ };
9302
+ const response = await (this._fetch ?? fetch)(this._url, init);
9303
+ await response.body?.cancel();
9304
+ if (!response.ok && response.status !== 405) throw new StreamableHTTPError(response.status, `Failed to terminate session: ${response.statusText}`);
9305
+ this._sessionId = void 0;
9306
+ } catch (error) {
9307
+ this.onerror?.(error);
9308
+ throw error;
9309
+ }
9310
+ }
9311
+ setProtocolVersion(version) {
9312
+ this._protocolVersion = version;
9313
+ }
9314
+ get protocolVersion() {
9315
+ return this._protocolVersion;
9316
+ }
9317
+ /**
9318
+ * Resume an SSE stream from a previous event ID.
9319
+ * Opens a GET SSE connection with Last-Event-ID header to replay missed events.
9320
+ *
9321
+ * @param lastEventId The event ID to resume from
9322
+ * @param options Optional callback to receive new resumption tokens
9323
+ */
9324
+ async resumeStream(lastEventId, options) {
9325
+ await this._startOrAuthSse({
9326
+ resumptionToken: lastEventId,
9327
+ onresumptiontoken: options?.onresumptiontoken
9328
+ });
9329
+ }
9330
+ };
9331
+ //#endregion
9332
+ //#region ../../node_modules/.pnpm/eventsource@3.0.7/node_modules/eventsource/dist/index.js
9333
+ var ErrorEvent = class extends Event {
9334
+ /**
9335
+ * Constructs a new `ErrorEvent` instance. This is typically not called directly,
9336
+ * but rather emitted by the `EventSource` object when an error occurs.
9337
+ *
9338
+ * @param type - The type of the event (should be "error")
9339
+ * @param errorEventInitDict - Optional properties to include in the error event
9340
+ */
9341
+ constructor(type, errorEventInitDict) {
9342
+ var _a, _b;
9343
+ super(type), this.code = (_a = errorEventInitDict == null ? void 0 : errorEventInitDict.code) != null ? _a : void 0, this.message = (_b = errorEventInitDict == null ? void 0 : errorEventInitDict.message) != null ? _b : void 0;
9344
+ }
9345
+ /**
9346
+ * Node.js "hides" the `message` and `code` properties of the `ErrorEvent` instance,
9347
+ * when it is `console.log`'ed. This makes it harder to debug errors. To ease debugging,
9348
+ * we explicitly include the properties in the `inspect` method.
9349
+ *
9350
+ * This is automatically called by Node.js when you `console.log` an instance of this class.
9351
+ *
9352
+ * @param _depth - The current depth
9353
+ * @param options - The options passed to `util.inspect`
9354
+ * @param inspect - The inspect function to use (prevents having to import it from `util`)
9355
+ * @returns A string representation of the error
9356
+ */
9357
+ [Symbol.for("nodejs.util.inspect.custom")](_depth, options, inspect) {
9358
+ return inspect(inspectableError(this), options);
9359
+ }
9360
+ /**
9361
+ * Deno "hides" the `message` and `code` properties of the `ErrorEvent` instance,
9362
+ * when it is `console.log`'ed. This makes it harder to debug errors. To ease debugging,
9363
+ * we explicitly include the properties in the `inspect` method.
9364
+ *
9365
+ * This is automatically called by Deno when you `console.log` an instance of this class.
9366
+ *
9367
+ * @param inspect - The inspect function to use (prevents having to import it from `util`)
9368
+ * @param options - The options passed to `Deno.inspect`
9369
+ * @returns A string representation of the error
9370
+ */
9371
+ [Symbol.for("Deno.customInspect")](inspect, options) {
9372
+ return inspect(inspectableError(this), options);
9373
+ }
9374
+ };
9375
+ function syntaxError(message) {
9376
+ const DomException = globalThis.DOMException;
9377
+ return typeof DomException == "function" ? new DomException(message, "SyntaxError") : new SyntaxError(message);
9378
+ }
9379
+ function flattenError(err) {
9380
+ return err instanceof Error ? "errors" in err && Array.isArray(err.errors) ? err.errors.map(flattenError).join(", ") : "cause" in err && err.cause instanceof Error ? `${err}: ${flattenError(err.cause)}` : err.message : `${err}`;
9381
+ }
9382
+ function inspectableError(err) {
9383
+ return {
9384
+ type: err.type,
9385
+ message: err.message,
9386
+ code: err.code,
9387
+ defaultPrevented: err.defaultPrevented,
9388
+ cancelable: err.cancelable,
9389
+ timeStamp: err.timeStamp
9390
+ };
9391
+ }
9392
+ var __typeError = (msg) => {
9393
+ throw TypeError(msg);
9394
+ }, __accessCheck = (obj, member, msg) => member.has(obj) || __typeError("Cannot " + msg), __privateGet = (obj, member, getter) => (__accessCheck(obj, member, "read from private field"), getter ? getter.call(obj) : member.get(obj)), __privateAdd = (obj, member, value) => member.has(obj) ? __typeError("Cannot add the same private member more than once") : member instanceof WeakSet ? member.add(obj) : member.set(obj, value), __privateSet = (obj, member, value, setter) => (__accessCheck(obj, member, "write to private field"), member.set(obj, value), value), __privateMethod = (obj, member, method) => (__accessCheck(obj, member, "access private method"), method), _readyState, _url, _redirectUrl, _withCredentials, _fetch, _reconnectInterval, _reconnectTimer, _lastEventId, _controller, _parser, _onError, _onMessage, _onOpen, _EventSource_instances, connect_fn, _onFetchResponse, _onFetchError, getRequestOptions_fn, _onEvent, _onRetryChange, failConnection_fn, scheduleReconnect_fn, _reconnect;
9395
+ var EventSource = class extends EventTarget {
9396
+ constructor(url, eventSourceInitDict) {
9397
+ var _a, _b;
9398
+ super(), __privateAdd(this, _EventSource_instances), this.CONNECTING = 0, this.OPEN = 1, this.CLOSED = 2, __privateAdd(this, _readyState), __privateAdd(this, _url), __privateAdd(this, _redirectUrl), __privateAdd(this, _withCredentials), __privateAdd(this, _fetch), __privateAdd(this, _reconnectInterval), __privateAdd(this, _reconnectTimer), __privateAdd(this, _lastEventId, null), __privateAdd(this, _controller), __privateAdd(this, _parser), __privateAdd(this, _onError, null), __privateAdd(this, _onMessage, null), __privateAdd(this, _onOpen, null), __privateAdd(this, _onFetchResponse, async (response) => {
9399
+ var _a2;
9400
+ __privateGet(this, _parser).reset();
9401
+ const { body, redirected, status, headers } = response;
9402
+ if (status === 204) {
9403
+ __privateMethod(this, _EventSource_instances, failConnection_fn).call(this, "Server sent HTTP 204, not reconnecting", 204), this.close();
9404
+ return;
9405
+ }
9406
+ if (redirected ? __privateSet(this, _redirectUrl, new URL(response.url)) : __privateSet(this, _redirectUrl, void 0), status !== 200) {
9407
+ __privateMethod(this, _EventSource_instances, failConnection_fn).call(this, `Non-200 status code (${status})`, status);
9408
+ return;
9409
+ }
9410
+ if (!(headers.get("content-type") || "").startsWith("text/event-stream")) {
9411
+ __privateMethod(this, _EventSource_instances, failConnection_fn).call(this, "Invalid content type, expected \"text/event-stream\"", status);
9412
+ return;
9413
+ }
9414
+ if (__privateGet(this, _readyState) === this.CLOSED) return;
9415
+ __privateSet(this, _readyState, this.OPEN);
9416
+ const openEvent = new Event("open");
9417
+ if ((_a2 = __privateGet(this, _onOpen)) == null || _a2.call(this, openEvent), this.dispatchEvent(openEvent), typeof body != "object" || !body || !("getReader" in body)) {
9418
+ __privateMethod(this, _EventSource_instances, failConnection_fn).call(this, "Invalid response body, expected a web ReadableStream", status), this.close();
9419
+ return;
9420
+ }
9421
+ const decoder = new TextDecoder(), reader = body.getReader();
9422
+ let open = !0;
9423
+ do {
9424
+ const { done, value } = await reader.read();
9425
+ value && __privateGet(this, _parser).feed(decoder.decode(value, { stream: !done })), done && (open = !1, __privateGet(this, _parser).reset(), __privateMethod(this, _EventSource_instances, scheduleReconnect_fn).call(this));
9426
+ } while (open);
9427
+ }), __privateAdd(this, _onFetchError, (err) => {
9428
+ __privateSet(this, _controller, void 0), !(err.name === "AbortError" || err.type === "aborted") && __privateMethod(this, _EventSource_instances, scheduleReconnect_fn).call(this, flattenError(err));
9429
+ }), __privateAdd(this, _onEvent, (event) => {
9430
+ typeof event.id == "string" && __privateSet(this, _lastEventId, event.id);
9431
+ const messageEvent = new MessageEvent(event.event || "message", {
9432
+ data: event.data,
9433
+ origin: __privateGet(this, _redirectUrl) ? __privateGet(this, _redirectUrl).origin : __privateGet(this, _url).origin,
9434
+ lastEventId: event.id || ""
9435
+ });
9436
+ __privateGet(this, _onMessage) && (!event.event || event.event === "message") && __privateGet(this, _onMessage).call(this, messageEvent), this.dispatchEvent(messageEvent);
9437
+ }), __privateAdd(this, _onRetryChange, (value) => {
9438
+ __privateSet(this, _reconnectInterval, value);
9439
+ }), __privateAdd(this, _reconnect, () => {
9440
+ __privateSet(this, _reconnectTimer, void 0), __privateGet(this, _readyState) === this.CONNECTING && __privateMethod(this, _EventSource_instances, connect_fn).call(this);
9441
+ });
9442
+ try {
9443
+ if (url instanceof URL) __privateSet(this, _url, url);
9444
+ else if (typeof url == "string") __privateSet(this, _url, new URL(url, getBaseURL()));
9445
+ else throw new Error("Invalid URL");
9446
+ } catch {
9447
+ throw syntaxError("An invalid or illegal string was specified");
9448
+ }
9449
+ __privateSet(this, _parser, createParser({
9450
+ onEvent: __privateGet(this, _onEvent),
9451
+ onRetry: __privateGet(this, _onRetryChange)
9452
+ })), __privateSet(this, _readyState, this.CONNECTING), __privateSet(this, _reconnectInterval, 3e3), __privateSet(this, _fetch, (_a = eventSourceInitDict == null ? void 0 : eventSourceInitDict.fetch) != null ? _a : globalThis.fetch), __privateSet(this, _withCredentials, (_b = eventSourceInitDict == null ? void 0 : eventSourceInitDict.withCredentials) != null ? _b : !1), __privateMethod(this, _EventSource_instances, connect_fn).call(this);
9453
+ }
9454
+ /**
9455
+ * Returns the state of this EventSource object's connection. It can have the values described below.
9456
+ *
9457
+ * [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/readyState)
9458
+ *
9459
+ * Note: typed as `number` instead of `0 | 1 | 2` for compatibility with the `EventSource` interface,
9460
+ * defined in the TypeScript `dom` library.
9461
+ *
9462
+ * @public
9463
+ */
9464
+ get readyState() {
9465
+ return __privateGet(this, _readyState);
9466
+ }
9467
+ /**
9468
+ * Returns the URL providing the event stream.
9469
+ *
9470
+ * [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/url)
9471
+ *
9472
+ * @public
9473
+ */
9474
+ get url() {
9475
+ return __privateGet(this, _url).href;
9476
+ }
9477
+ /**
9478
+ * Returns true if the credentials mode for connection requests to the URL providing the event stream is set to "include", and false otherwise.
9479
+ *
9480
+ * [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/withCredentials)
9481
+ */
9482
+ get withCredentials() {
9483
+ return __privateGet(this, _withCredentials);
9484
+ }
9485
+ /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/error_event) */
9486
+ get onerror() {
9487
+ return __privateGet(this, _onError);
9488
+ }
9489
+ set onerror(value) {
9490
+ __privateSet(this, _onError, value);
9491
+ }
9492
+ /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/message_event) */
9493
+ get onmessage() {
9494
+ return __privateGet(this, _onMessage);
9495
+ }
9496
+ set onmessage(value) {
9497
+ __privateSet(this, _onMessage, value);
9498
+ }
9499
+ /** [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/open_event) */
9500
+ get onopen() {
9501
+ return __privateGet(this, _onOpen);
9502
+ }
9503
+ set onopen(value) {
9504
+ __privateSet(this, _onOpen, value);
9505
+ }
9506
+ addEventListener(type, listener, options) {
9507
+ const listen = listener;
9508
+ super.addEventListener(type, listen, options);
9509
+ }
9510
+ removeEventListener(type, listener, options) {
9511
+ const listen = listener;
9512
+ super.removeEventListener(type, listen, options);
9513
+ }
9514
+ /**
9515
+ * Aborts any instances of the fetch algorithm started for this EventSource object, and sets the readyState attribute to CLOSED.
9516
+ *
9517
+ * [MDN Reference](https://developer.mozilla.org/docs/Web/API/EventSource/close)
9518
+ *
9519
+ * @public
9520
+ */
9521
+ close() {
9522
+ __privateGet(this, _reconnectTimer) && clearTimeout(__privateGet(this, _reconnectTimer)), __privateGet(this, _readyState) !== this.CLOSED && (__privateGet(this, _controller) && __privateGet(this, _controller).abort(), __privateSet(this, _readyState, this.CLOSED), __privateSet(this, _controller, void 0));
9523
+ }
9524
+ };
9525
+ _readyState = /* @__PURE__ */ new WeakMap(), _url = /* @__PURE__ */ new WeakMap(), _redirectUrl = /* @__PURE__ */ new WeakMap(), _withCredentials = /* @__PURE__ */ new WeakMap(), _fetch = /* @__PURE__ */ new WeakMap(), _reconnectInterval = /* @__PURE__ */ new WeakMap(), _reconnectTimer = /* @__PURE__ */ new WeakMap(), _lastEventId = /* @__PURE__ */ new WeakMap(), _controller = /* @__PURE__ */ new WeakMap(), _parser = /* @__PURE__ */ new WeakMap(), _onError = /* @__PURE__ */ new WeakMap(), _onMessage = /* @__PURE__ */ new WeakMap(), _onOpen = /* @__PURE__ */ new WeakMap(), _EventSource_instances = /* @__PURE__ */ new WeakSet(), connect_fn = function() {
9526
+ __privateSet(this, _readyState, this.CONNECTING), __privateSet(this, _controller, new AbortController()), __privateGet(this, _fetch)(__privateGet(this, _url), __privateMethod(this, _EventSource_instances, getRequestOptions_fn).call(this)).then(__privateGet(this, _onFetchResponse)).catch(__privateGet(this, _onFetchError));
9527
+ }, _onFetchResponse = /* @__PURE__ */ new WeakMap(), _onFetchError = /* @__PURE__ */ new WeakMap(), getRequestOptions_fn = function() {
9528
+ var _a;
9529
+ const init = {
9530
+ mode: "cors",
9531
+ redirect: "follow",
9532
+ headers: {
9533
+ Accept: "text/event-stream",
9534
+ ...__privateGet(this, _lastEventId) ? { "Last-Event-ID": __privateGet(this, _lastEventId) } : void 0
9535
+ },
9536
+ cache: "no-store",
9537
+ signal: (_a = __privateGet(this, _controller)) == null ? void 0 : _a.signal
9538
+ };
9539
+ return "window" in globalThis && (init.credentials = this.withCredentials ? "include" : "same-origin"), init;
9540
+ }, _onEvent = /* @__PURE__ */ new WeakMap(), _onRetryChange = /* @__PURE__ */ new WeakMap(), failConnection_fn = function(message, code) {
9541
+ var _a;
9542
+ __privateGet(this, _readyState) !== this.CLOSED && __privateSet(this, _readyState, this.CLOSED);
9543
+ const errorEvent = new ErrorEvent("error", {
9544
+ code,
9545
+ message
9546
+ });
9547
+ (_a = __privateGet(this, _onError)) == null || _a.call(this, errorEvent), this.dispatchEvent(errorEvent);
9548
+ }, scheduleReconnect_fn = function(message, code) {
9549
+ var _a;
9550
+ if (__privateGet(this, _readyState) === this.CLOSED) return;
9551
+ __privateSet(this, _readyState, this.CONNECTING);
9552
+ const errorEvent = new ErrorEvent("error", {
9553
+ code,
9554
+ message
9555
+ });
9556
+ (_a = __privateGet(this, _onError)) == null || _a.call(this, errorEvent), this.dispatchEvent(errorEvent), __privateSet(this, _reconnectTimer, setTimeout(__privateGet(this, _reconnect), __privateGet(this, _reconnectInterval)));
9557
+ }, _reconnect = /* @__PURE__ */ new WeakMap(), EventSource.CONNECTING = 0, EventSource.OPEN = 1, EventSource.CLOSED = 2;
9558
+ function getBaseURL() {
9559
+ const doc = "document" in globalThis ? globalThis.document : void 0;
9560
+ return doc && typeof doc == "object" && "baseURI" in doc && typeof doc.baseURI == "string" ? doc.baseURI : void 0;
9561
+ }
9562
+ //#endregion
9563
+ //#region ../../node_modules/.pnpm/@modelcontextprotocol+sdk@1.29.0_zod@4.4.3/node_modules/@modelcontextprotocol/sdk/dist/esm/client/sse.js
9564
+ var SseError = class extends Error {
9565
+ constructor(code, message, event) {
9566
+ super(`SSE error: ${message}`);
9567
+ this.code = code;
9568
+ this.event = event;
9569
+ }
9570
+ };
9571
+ /**
9572
+ * Client transport for SSE: this will connect to a server using Server-Sent Events for receiving
9573
+ * messages and make separate POST requests for sending messages.
9574
+ * @deprecated SSEClientTransport is deprecated. Prefer to use StreamableHTTPClientTransport where possible instead. Note that because some servers are still using SSE, clients may need to support both transports during the migration period.
9575
+ */
9576
+ var SSEClientTransport = class {
9577
+ constructor(url, opts) {
9578
+ this._url = url;
9579
+ this._resourceMetadataUrl = void 0;
9580
+ this._scope = void 0;
9581
+ this._eventSourceInit = opts?.eventSourceInit;
9582
+ this._requestInit = opts?.requestInit;
9583
+ this._authProvider = opts?.authProvider;
9584
+ this._fetch = opts?.fetch;
9585
+ this._fetchWithInit = createFetchWithInit(opts?.fetch, opts?.requestInit);
9586
+ }
9587
+ async _authThenStart() {
9588
+ if (!this._authProvider) throw new UnauthorizedError("No auth provider");
9589
+ let result;
9590
+ try {
9591
+ result = await auth(this._authProvider, {
9592
+ serverUrl: this._url,
9593
+ resourceMetadataUrl: this._resourceMetadataUrl,
9594
+ scope: this._scope,
9595
+ fetchFn: this._fetchWithInit
9596
+ });
9597
+ } catch (error) {
9598
+ this.onerror?.(error);
9599
+ throw error;
9600
+ }
9601
+ if (result !== "AUTHORIZED") throw new UnauthorizedError();
9602
+ return await this._startOrAuth();
9603
+ }
9604
+ async _commonHeaders() {
9605
+ const headers = {};
9606
+ if (this._authProvider) {
9607
+ const tokens = await this._authProvider.tokens();
9608
+ if (tokens) headers["Authorization"] = `Bearer ${tokens.access_token}`;
9609
+ }
9610
+ if (this._protocolVersion) headers["mcp-protocol-version"] = this._protocolVersion;
9611
+ const extraHeaders = normalizeHeaders(this._requestInit?.headers);
9612
+ return new Headers({
9613
+ ...headers,
9614
+ ...extraHeaders
9615
+ });
9616
+ }
9617
+ _startOrAuth() {
9618
+ const fetchImpl = this?._eventSourceInit?.fetch ?? this._fetch ?? fetch;
9619
+ return new Promise((resolve, reject) => {
9620
+ this._eventSource = new EventSource(this._url.href, {
9621
+ ...this._eventSourceInit,
9622
+ fetch: async (url, init) => {
9623
+ const headers = await this._commonHeaders();
9624
+ headers.set("Accept", "text/event-stream");
9625
+ const response = await fetchImpl(url, {
9626
+ ...init,
9627
+ headers
9628
+ });
9629
+ if (response.status === 401 && response.headers.has("www-authenticate")) {
9630
+ const { resourceMetadataUrl, scope } = extractWWWAuthenticateParams(response);
9631
+ this._resourceMetadataUrl = resourceMetadataUrl;
9632
+ this._scope = scope;
9633
+ }
9634
+ return response;
9635
+ }
9636
+ });
9637
+ this._abortController = new AbortController();
9638
+ this._eventSource.onerror = (event) => {
9639
+ if (event.code === 401 && this._authProvider) {
9640
+ this._authThenStart().then(resolve, reject);
9641
+ return;
9642
+ }
9643
+ const error = new SseError(event.code, event.message, event);
9644
+ reject(error);
9645
+ this.onerror?.(error);
9646
+ };
9647
+ this._eventSource.onopen = () => {};
9648
+ this._eventSource.addEventListener("endpoint", (event) => {
9649
+ const messageEvent = event;
9650
+ try {
9651
+ this._endpoint = new URL(messageEvent.data, this._url);
9652
+ if (this._endpoint.origin !== this._url.origin) throw new Error(`Endpoint origin does not match connection origin: ${this._endpoint.origin}`);
9653
+ } catch (error) {
9654
+ reject(error);
9655
+ this.onerror?.(error);
9656
+ this.close();
9657
+ return;
9658
+ }
9659
+ resolve();
9660
+ });
9661
+ this._eventSource.onmessage = (event) => {
9662
+ const messageEvent = event;
9663
+ let message;
9664
+ try {
9665
+ message = JSONRPCMessageSchema.parse(JSON.parse(messageEvent.data));
9666
+ } catch (error) {
9667
+ this.onerror?.(error);
9668
+ return;
9669
+ }
9670
+ this.onmessage?.(message);
9671
+ };
9672
+ });
9673
+ }
9674
+ async start() {
9675
+ if (this._eventSource) throw new Error("SSEClientTransport already started! If using Client class, note that connect() calls start() automatically.");
9676
+ return await this._startOrAuth();
9677
+ }
9678
+ /**
9679
+ * Call this method after the user has finished authorizing via their user agent and is redirected back to the MCP client application. This will exchange the authorization code for an access token, enabling the next connection attempt to successfully auth.
9680
+ */
9681
+ async finishAuth(authorizationCode) {
9682
+ if (!this._authProvider) throw new UnauthorizedError("No auth provider");
9683
+ if (await auth(this._authProvider, {
9684
+ serverUrl: this._url,
9685
+ authorizationCode,
9686
+ resourceMetadataUrl: this._resourceMetadataUrl,
9687
+ scope: this._scope,
9688
+ fetchFn: this._fetchWithInit
9689
+ }) !== "AUTHORIZED") throw new UnauthorizedError("Failed to authorize");
9690
+ }
9691
+ async close() {
9692
+ this._abortController?.abort();
9693
+ this._eventSource?.close();
9694
+ this.onclose?.();
9695
+ }
9696
+ async send(message) {
9697
+ if (!this._endpoint) throw new Error("Not connected");
9698
+ try {
9699
+ const headers = await this._commonHeaders();
9700
+ headers.set("content-type", "application/json");
9701
+ const init = {
9702
+ ...this._requestInit,
9703
+ method: "POST",
9704
+ headers,
9705
+ body: JSON.stringify(message),
9706
+ signal: this._abortController?.signal
9707
+ };
9708
+ const response = await (this._fetch ?? fetch)(this._endpoint, init);
9709
+ if (!response.ok) {
9710
+ const text = await response.text().catch(() => null);
9711
+ if (response.status === 401 && this._authProvider) {
9712
+ const { resourceMetadataUrl, scope } = extractWWWAuthenticateParams(response);
9713
+ this._resourceMetadataUrl = resourceMetadataUrl;
9714
+ this._scope = scope;
9715
+ if (await auth(this._authProvider, {
9716
+ serverUrl: this._url,
9717
+ resourceMetadataUrl: this._resourceMetadataUrl,
9718
+ scope: this._scope,
9719
+ fetchFn: this._fetchWithInit
9720
+ }) !== "AUTHORIZED") throw new UnauthorizedError();
9721
+ return this.send(message);
9722
+ }
9723
+ throw new Error(`Error POSTing to endpoint (HTTP ${response.status}): ${text}`);
9724
+ }
9725
+ await response.body?.cancel();
9726
+ } catch (error) {
9727
+ this.onerror?.(error);
9728
+ throw error;
9729
+ }
9730
+ }
9731
+ setProtocolVersion(version) {
9732
+ this._protocolVersion = version;
9733
+ }
9734
+ };
9735
+ //#endregion
9736
+ //#region src/mcp/mcp-prober.ts
9737
+ const DEFAULT_TIMEOUT_MS$1 = 15e3;
9738
+ const DEFAULT_CONCURRENCY$1 = 3;
9739
+ function envRecord(pairs) {
9740
+ return Object.fromEntries(pairs.map((e) => [e.name, e.value]));
9741
+ }
9742
+ function buildTransport(def) {
9743
+ switch (def.transport) {
9744
+ case "stdio": return new StdioClientTransport({
9745
+ command: def.command,
9746
+ args: def.args,
9747
+ env: {
9748
+ ...getDefaultEnvironment(),
9749
+ ...envRecord(def.env)
9750
+ },
9751
+ stderr: "ignore"
9752
+ });
9753
+ case "http": return new StreamableHTTPClientTransport(new URL(def.url), { requestInit: { headers: envRecord(def.headers) } });
9754
+ case "sse": return new SSEClientTransport(new URL(def.url), { requestInit: { headers: envRecord(def.headers) } });
9755
+ }
9756
+ }
9757
+ async function connectReal(name, def) {
9758
+ const client = new Client({
9759
+ name: "agentconnect",
9760
+ version: DAEMON_VERSION
9761
+ });
9762
+ await client.connect(buildTransport(def));
9763
+ return {
9764
+ listTools: async () => (await client.listTools()).tools.map((t) => t.name),
9765
+ serverVersion: () => client.getServerVersion()?.version,
9766
+ close: () => client.close()
9767
+ };
9768
+ }
9769
+ /**
9770
+ * Probe one configured MCP server. Never throws: any failure (spawn error, bad
9771
+ * URL, handshake failure, timeout) is captured in `{ ok: false, error }`. On
9772
+ * success, `tools` reflects whatever `tools/list` returned — an empty list is
9773
+ * not a failure.
9774
+ */
9775
+ async function probeMcpServer(name, def, opts = {}) {
9776
+ const timeoutMs = opts.timeoutMs ?? DEFAULT_TIMEOUT_MS$1;
9777
+ let timer;
9778
+ let timedOut = false;
9779
+ const timeout = new Promise((_, reject) => {
9780
+ timer = setTimeout(() => {
9781
+ timedOut = true;
9782
+ reject(/* @__PURE__ */ new Error(`probe timed out after ${timeoutMs}ms`));
9783
+ }, timeoutMs);
9784
+ });
9785
+ let conn;
9786
+ const run = async () => {
9787
+ conn = await (opts.connectFactory ?? connectReal)(name, def);
9788
+ return {
9789
+ tools: await conn.listTools(),
9790
+ version: conn.serverVersion()
9791
+ };
9792
+ };
9793
+ const pending = run();
9794
+ try {
9795
+ const { tools, version } = await Promise.race([pending, timeout]);
9796
+ opts.log?.info(`mcp-probe: ${name} ok (tools: ${tools.length ? tools.join(", ") : "none"})`);
9797
+ return {
9798
+ name,
9799
+ transport: def.transport,
9800
+ ok: true,
9801
+ tools,
9802
+ ...version !== void 0 ? { version } : {}
9803
+ };
9804
+ } catch (err) {
9805
+ const error = err.message;
9806
+ opts.log?.warn(`mcp-probe: ${name} failed — ${error}`);
9807
+ return {
9808
+ name,
9809
+ transport: def.transport,
9810
+ ok: false,
9811
+ tools: [],
9812
+ error
9813
+ };
9814
+ } finally {
9815
+ if (timer) clearTimeout(timer);
9816
+ const closeConn = () => conn?.close().catch(() => {});
9817
+ if (timedOut) pending.then(closeConn, closeConn);
9818
+ else await closeConn();
9819
+ }
9820
+ }
9821
+ /**
9822
+ * Probe every configured MCP server with bounded concurrency. Result order is
9823
+ * not meaningful — callers key by `result.name`.
9824
+ */
9825
+ async function probeAllMcpServers(defs, opts = {}) {
9826
+ const names = Object.keys(defs);
9827
+ if (names.length === 0) return [];
9828
+ const limit = Math.max(1, opts.concurrency ?? DEFAULT_CONCURRENCY$1);
9829
+ const results = [];
9830
+ let next = 0;
9831
+ const worker = async () => {
9832
+ for (let i = next++; i < names.length; i = next++) {
9833
+ const name = names[i];
9834
+ results.push(await probeMcpServer(name, defs[name], opts));
9835
+ }
9836
+ };
9837
+ await Promise.all(Array.from({ length: Math.min(limit, names.length) }, () => worker()));
9838
+ return results;
9839
+ }
9840
+ //#endregion
9841
+ //#region src/mcp/resolve-servers.ts
9842
+ /**
9843
+ * Resolve an agent's enabled MCP-server names against the daemon's configured
9844
+ * definitions, producing the ACP `McpServer` entries to attach at
9845
+ * session/new|load (after the daemon's own bridge entry).
9846
+ *
9847
+ * Skips (with a warn) rather than fails: an unknown name, the reserved bridge
9848
+ * name, and an http/sse server the agent's runtime is KNOWN not to accept
9849
+ * (`caps` from the runtime probe). When `caps` is undefined (runtime not probed
9850
+ * yet) http/sse entries are included optimistically — the runtime rejecting an
9851
+ * unsupported transport at session/new is a clearer failure than silently
9852
+ * withholding a server the user enabled.
9853
+ */
9854
+ function resolveAgentMcpServers(opts) {
9855
+ const out = [];
9856
+ for (const name of opts.enabled) {
9857
+ if (name === "agentconnect") {
9858
+ opts.warn?.(`mcp: server name "${name}" is reserved for the daemon bridge — skipped`);
9859
+ continue;
9860
+ }
9861
+ const def = opts.defs[name];
9862
+ if (!def) {
9863
+ opts.warn?.(`mcp: server "${name}" is not configured on this daemon — skipped`);
9864
+ continue;
9865
+ }
9866
+ if (def.transport === "stdio") {
9867
+ out.push({
9868
+ name,
9869
+ command: def.command,
9870
+ args: def.args,
9871
+ env: def.env
9872
+ });
9873
+ continue;
9874
+ }
9875
+ if (opts.caps && !opts.caps[def.transport]) {
9876
+ opts.warn?.(`mcp: server "${name}" needs the ${def.transport} transport, which the runtime doesn't accept — skipped`);
9877
+ continue;
9878
+ }
9879
+ out.push({
9880
+ type: def.transport,
9881
+ name,
9882
+ url: def.url,
9883
+ headers: def.headers
9884
+ });
9885
+ }
9886
+ return out;
9887
+ }
9888
+ //#endregion
6506
9889
  //#region src/mcp/tools.ts
6507
9890
  const obj = (properties, required = []) => ({
6508
9891
  type: "object",
@@ -65068,13 +68451,15 @@ async function probeRuntime(id, rt, cwd, opts = {}) {
65068
68451
  const opt = await Promise.race([run(), timeout]);
65069
68452
  const models = (opt?.models ?? []).filter((m) => m !== "default");
65070
68453
  const acpProtocolVersion = host.acpProtocolVersion();
68454
+ const mcpCapabilities = host.mcpCapabilities?.() ?? void 0;
65071
68455
  opts.log?.info(`probe: ${id} ok (models: ${models.length ? models.join(", ") : "none advertised"})`);
65072
68456
  return {
65073
68457
  runtime: id,
65074
68458
  ok: true,
65075
68459
  models,
65076
68460
  currentModel: opt?.current,
65077
- acpProtocolVersion
68461
+ acpProtocolVersion,
68462
+ mcpCapabilities
65078
68463
  };
65079
68464
  } catch (err) {
65080
68465
  const error = err.message;
@@ -65690,7 +69075,7 @@ var CpClient = class {
65690
69075
  this.heartbeatMs = ok.heartbeatSec > 0 ? ok.heartbeatSec * 1e3 : this.deps.heartbeatDefaultMs;
65691
69076
  this.armHeartbeat();
65692
69077
  this.deps.log.info(`cp: READY (epoch=${this.sessionEpoch}, routingEpoch=${this.routingEpoch})`);
65693
- this.emitDaemonRuntimes(this.deps.runtimeProfiles());
69078
+ this.emitDaemonRuntimes(this.deps.runtimeProfiles(), this.deps.mcpServerFacts?.() ?? []);
65694
69079
  this.deps.onReady?.();
65695
69080
  }
65696
69081
  /**
@@ -65700,9 +69085,12 @@ var CpClient = class {
65700
69085
  * runtime list to exactly this snapshot, pruning runtimes that are no longer
65701
69086
  * installed. No-op unless READY/DRAINING.
65702
69087
  */
65703
- emitDaemonRuntimes(runtimes) {
69088
+ emitDaemonRuntimes(runtimes, mcpServers = []) {
65704
69089
  if (this.state !== "READY" && this.state !== "DRAINING") return;
65705
- this.transport?.send(encode(buildEnvelope("facts/daemon-runtimes", { runtimes })));
69090
+ this.transport?.send(encode(buildEnvelope("facts/daemon-runtimes", {
69091
+ runtimes,
69092
+ mcpServers
69093
+ })));
65706
69094
  }
65707
69095
  /**
65708
69096
  * Report a session's cumulative token usage (D→C `usage/report` EVT,
@@ -66478,6 +69866,7 @@ function applySpecFields(raw, spec, opts) {
66478
69866
  if (spec.executionMode !== void 0) raw.executionMode = spec.executionMode;
66479
69867
  if (spec.fastMode !== void 0) raw.fastMode = spec.fastMode;
66480
69868
  if (spec.permissionMode !== void 0) raw.permissionMode = spec.permissionMode;
69869
+ if (spec.mcpServers !== void 0) raw.mcpServers = spec.mcpServers;
66481
69870
  if (spec.outputMode !== void 0) {
66482
69871
  const out = typeof raw.output === "object" && raw.output !== null ? raw.output : {};
66483
69872
  out.mode = spec.outputMode;
@@ -82599,6 +85988,9 @@ var Daemon = class Daemon {
82599
85988
  runtimeVersions = {};
82600
85989
  runtimeModels = /* @__PURE__ */ new Map();
82601
85990
  runtimeAcpVersions = /* @__PURE__ */ new Map();
85991
+ runtimeMcpCaps = /* @__PURE__ */ new Map();
85992
+ mcpServerDefs = {};
85993
+ mcpServerFacts = [];
82602
85994
  probing = false;
82603
85995
  lastProbeAtMs = 0;
82604
85996
  cpClient;
@@ -82674,6 +86066,10 @@ var Daemon = class Daemon {
82674
86066
  this.log.info(`runtimes ready: ${Object.keys(this.runtimes).join(", ") || "(none)"}`);
82675
86067
  const skipped = Object.keys(resolvedRuntimes).filter((id) => !this.runtimes[id]);
82676
86068
  if (skipped.length) this.log.info(`runtimes not installed (skipped): ${skipped.join(", ")}`);
86069
+ const { [RESERVED_MCP_SERVER_NAME]: reservedMcp, ...mcpServerDefs } = cfg.mcpServers ?? {};
86070
+ if (reservedMcp) this.log.warn(`mcp: config server name "${RESERVED_MCP_SERVER_NAME}" is reserved for the daemon bridge — ignored`);
86071
+ this.mcpServerDefs = mcpServerDefs;
86072
+ if (Object.keys(mcpServerDefs).length) this.log.info(`mcp servers configured: ${Object.keys(mcpServerDefs).join(", ")}`);
82677
86073
  this.store = new LocalStore(statePath(root));
82678
86074
  this.nameResolver = new SlackNameResolver((id, name) => {
82679
86075
  this.store.setDisplayName(id, name, Date.now());
@@ -82723,21 +86119,30 @@ var Daemon = class Daemon {
82723
86119
  hostFor: (agentId) => this.ensureHostAsync(agentId),
82724
86120
  agentById: (id) => this.agents.get(id),
82725
86121
  mcpServersFor: ({ agent, channel, thread }) => {
86122
+ const servers = [];
82726
86123
  const tools = toolsForIntegrations(agent.integrations);
82727
- if (tools.length === 0) return [];
82728
86124
  const integrationId = agent.integrations.find((i) => i.platform === "slack")?.id;
82729
- const token = this.mcp.register({
82730
- agentId: agent.id,
82731
- ...integrationId ? { integrationId } : {},
82732
- channel,
82733
- thread,
82734
- tools
82735
- });
82736
- return buildMcpServers({
82737
- socketPath: mcpSocketPath(root),
82738
- token,
82739
- cliEntry
82740
- });
86125
+ if (tools.length > 0) {
86126
+ const token = this.mcp.register({
86127
+ agentId: agent.id,
86128
+ ...integrationId ? { integrationId } : {},
86129
+ channel,
86130
+ thread,
86131
+ tools
86132
+ });
86133
+ servers.push(...buildMcpServers({
86134
+ socketPath: mcpSocketPath(root),
86135
+ token,
86136
+ cliEntry
86137
+ }));
86138
+ }
86139
+ servers.push(...resolveAgentMcpServers({
86140
+ enabled: agent.mcpServers,
86141
+ defs: this.mcpServerDefs,
86142
+ caps: this.runtimeMcpCaps.get(agent.runtime),
86143
+ warn: (m) => this.log.warn(m)
86144
+ }));
86145
+ return servers;
82741
86146
  },
82742
86147
  downloadAttachment: (agentId, att) => this.replyConnFor(agentId)?.downloadFile?.(att.sourceUrl, this.cfg.limits.maxAttachmentBytes) ?? Promise.resolve(null),
82743
86148
  attachmentMaxBytes: cfg.limits.maxAttachmentBytes,
@@ -84432,6 +87837,7 @@ var Daemon = class Daemon {
84432
87837
  features: []
84433
87838
  }),
84434
87839
  runtimeProfiles: () => Object.keys(this.runtimes).map((id) => this.runtimeProfileFor(id)),
87840
+ mcpServerFacts: () => this.mcpServerFacts,
84435
87841
  onReady: () => {
84436
87842
  this.probeRuntimesAndEmit();
84437
87843
  for (const [integrationId, channels] of this.channelSnapshots) this.cpClient?.emitIntegrationChannels({
@@ -84491,7 +87897,8 @@ var Daemon = class Daemon {
84491
87897
  models: this.runtimeModels.get(id) ?? [],
84492
87898
  acpSupport: "full",
84493
87899
  acpProtocolVersion: this.runtimeAcpVersions.get(id),
84494
- toolCalling: true
87900
+ toolCalling: true,
87901
+ mcpCapabilities: this.runtimeMcpCaps.get(id)
84495
87902
  };
84496
87903
  }
84497
87904
  /** How long a completed probe sweep stays fresh — reconnects within this window
@@ -84499,8 +87906,10 @@ var Daemon = class Daemon {
84499
87906
  static PROBE_TTL_MS = 5 * 6e4;
84500
87907
  /**
84501
87908
  * Probe every installed runtime in the background (launch → initialize →
84502
- * session/new → read models → tear down), then emit one `facts/daemon-runtimes`
84503
- * snapshot once the whole sweep completes so the CP replaces its runtime list.
87909
+ * session/new → read models → tear down) and, concurrently, every configured
87910
+ * MCP server (MCP handshake + tools/list), then emit one `facts/daemon-runtimes`
87911
+ * snapshot once the whole sweep completes so the CP replaces its runtime +
87912
+ * MCP-server lists.
84504
87913
  *
84505
87914
  * Triggered on each CP (re)connect. Deduped while in flight; skipped (with a
84506
87915
  * cached re-emit) when the last sweep is still fresh, so a reconnect storm can't
@@ -84510,25 +87919,33 @@ var Daemon = class Daemon {
84510
87919
  async probeRuntimesAndEmit() {
84511
87920
  if (this.opts.hostFactory && !this.opts.probeRuntimes) return;
84512
87921
  const ids = Object.keys(this.runtimes);
84513
- if (ids.length === 0) return;
87922
+ const mcpNames = Object.keys(this.mcpServerDefs);
87923
+ if (ids.length === 0 && mcpNames.length === 0) return;
84514
87924
  if (this.probing) return;
84515
87925
  if (this.lastProbeAtMs > 0 && Date.now() - this.lastProbeAtMs < Daemon.PROBE_TTL_MS) {
84516
- this.cpClient?.emitDaemonRuntimes(ids.map((id) => this.runtimeProfileFor(id)));
87926
+ this.cpClient?.emitDaemonRuntimes(ids.map((id) => this.runtimeProfileFor(id)), this.mcpServerFacts);
84517
87927
  return;
84518
87928
  }
84519
87929
  this.probing = true;
84520
- this.log.info(`probe: sweeping ${ids.length} runtime(s): ${ids.join(", ")}`);
87930
+ this.log.info(`probe: sweeping ${ids.length} runtime(s): ${ids.join(", ") || "(none)"}`);
87931
+ if (mcpNames.length) this.log.info(`probe: sweeping ${mcpNames.length} MCP server(s): ${mcpNames.join(", ")}`);
84521
87932
  try {
84522
- const results = await (this.opts.probeRuntimes ?? probeAllRuntimes)(this.runtimes, { log: this.log });
87933
+ const probe = this.opts.probeRuntimes ?? probeAllRuntimes;
87934
+ const probeMcp = this.opts.probeMcpServers ?? probeAllMcpServers;
87935
+ const [results, mcpFacts] = await Promise.all([probe(this.runtimes, { log: this.log }), probeMcp(this.mcpServerDefs, { log: this.log })]);
84523
87936
  for (const r of results) {
84524
87937
  this.runtimeModels.set(r.runtime, r.ok ? r.models : []);
84525
87938
  if (r.ok && r.acpProtocolVersion !== void 0) this.runtimeAcpVersions.set(r.runtime, r.acpProtocolVersion);
84526
87939
  else this.runtimeAcpVersions.delete(r.runtime);
87940
+ if (r.ok && r.mcpCapabilities) this.runtimeMcpCaps.set(r.runtime, r.mcpCapabilities);
87941
+ else this.runtimeMcpCaps.delete(r.runtime);
84527
87942
  }
87943
+ this.mcpServerFacts = mcpFacts;
84528
87944
  this.lastProbeAtMs = Date.now();
84529
87945
  const okCount = results.filter((r) => r.ok).length;
84530
87946
  this.log.info(`probe: sweep complete — ${okCount}/${results.length} runtime(s) reachable`);
84531
- this.cpClient?.emitDaemonRuntimes(ids.map((id) => this.runtimeProfileFor(id)));
87947
+ if (mcpFacts.length) this.log.info(`probe: ${mcpFacts.filter((s) => s.ok).length}/${mcpFacts.length} MCP server(s) reachable`);
87948
+ this.cpClient?.emitDaemonRuntimes(ids.map((id) => this.runtimeProfileFor(id)), this.mcpServerFacts);
84532
87949
  } catch (err) {
84533
87950
  this.log.warn(`probe: sweep failed: ${formatErr(err)}`);
84534
87951
  } finally {
@@ -84588,4 +88005,4 @@ async function runForeground(opts, deps = {}) {
84588
88005
  //#endregion
84589
88006
  export { ClientTransport as n, runForeground as t };
84590
88007
 
84591
- //# sourceMappingURL=run-foreground-mvTzCScX.js.map
88008
+ //# sourceMappingURL=run-foreground-B05rDr1z.js.map