@astralyn/pi 1.0.3 → 1.0.5

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 (135) hide show
  1. package/CHANGELOG.md +34 -0
  2. package/dist/bundle/chunks/{anthropic-messages-YET4T7BO.js → anthropic-messages-YIOJIMVL.js} +1 -1
  3. package/dist/bundle/chunks/azure-openai-responses-LDW4FGAQ.js +2 -0
  4. package/dist/bundle/chunks/{chunk-MPDALHNJ.js → chunk-57XI7YJH.js} +1 -1
  5. package/dist/bundle/chunks/{chunk-SVJ7OGEB.js → chunk-A6ALEEY5.js} +1 -1
  6. package/dist/bundle/chunks/chunk-D3ZCGC4T.js +2 -0
  7. package/dist/bundle/chunks/{chunk-N2LEX5CU.js → chunk-HDHRZ7GT.js} +1 -1
  8. package/dist/bundle/chunks/{chunk-Q7TDQ5LT.js → chunk-IE3Z7ESB.js} +184 -79
  9. package/dist/bundle/chunks/{chunk-IZ3S3GDX.js → chunk-IFELM7MW.js} +1 -1
  10. package/dist/bundle/chunks/chunk-RZ2V53SP.js +2 -0
  11. package/dist/bundle/chunks/{chunk-V66VGGOM.js → chunk-TCQ4HHQD.js} +1 -1
  12. package/dist/bundle/chunks/chunk-TXJO4AJ7.js +11 -0
  13. package/dist/bundle/chunks/{chunk-NY3CWK44.js → chunk-UCXU7KLO.js} +1 -1
  14. package/dist/bundle/chunks/{cloudflare-workers-ai-system-one-QI46LUZ6.js → cloudflare-workers-ai-system-one-OWU5SM6J.js} +1 -1
  15. package/dist/bundle/chunks/codemode-worker.js +99 -4
  16. package/dist/bundle/chunks/{google-generative-ai-YTZCSHQN.js → google-generative-ai-S5A5IBU4.js} +1 -1
  17. package/dist/bundle/chunks/{google-vertex-OTFZJJXQ.js → google-vertex-UBRQFDB4.js} +1 -1
  18. package/dist/bundle/chunks/{mistral-conversations-ELH4V4TY.js → mistral-conversations-A2N5FSOV.js} +1 -1
  19. package/dist/bundle/chunks/{openai-codex-responses-OLVTU4UA.js → openai-codex-responses-Q6JHCWLE.js} +1 -1
  20. package/dist/bundle/chunks/{openai-completions-53M2KJ67.js → openai-completions-H4VMO7AU.js} +1 -1
  21. package/dist/bundle/chunks/{openai-responses-4ABDEL4Z.js → openai-responses-G4PGNM2H.js} +1 -1
  22. package/dist/bundle/chunks/{typesafe-system-one-RREJAKWB.js → typesafe-system-one-KYKKNU3E.js} +1 -1
  23. package/dist/bundle/chunks/virtual-modules-46MSJGKO.js +2 -0
  24. package/dist/bundle/cli.js +1 -1
  25. package/dist/bundle/index.js +1 -1
  26. package/dist/bundle/rpc-entry.js +1 -1
  27. package/dist/cli/args.d.ts +1 -0
  28. package/dist/cli/args.d.ts.map +1 -1
  29. package/dist/cli/args.js +11 -4
  30. package/dist/cli/args.js.map +1 -1
  31. package/dist/config.d.ts +18 -1
  32. package/dist/config.d.ts.map +1 -1
  33. package/dist/config.js +44 -6
  34. package/dist/config.js.map +1 -1
  35. package/dist/core/agent-session.d.ts +26 -4
  36. package/dist/core/agent-session.d.ts.map +1 -1
  37. package/dist/core/agent-session.js +44 -12
  38. package/dist/core/agent-session.js.map +1 -1
  39. package/dist/core/bash-executor.d.ts.map +1 -1
  40. package/dist/core/bash-executor.js +2 -7
  41. package/dist/core/bash-executor.js.map +1 -1
  42. package/dist/core/extensions/types.d.ts +2 -0
  43. package/dist/core/extensions/types.d.ts.map +1 -1
  44. package/dist/core/extensions/types.js.map +1 -1
  45. package/dist/core/keybindings.d.ts +4 -4
  46. package/dist/core/mcp-servers.d.ts +8 -0
  47. package/dist/core/mcp-servers.d.ts.map +1 -1
  48. package/dist/core/mcp-servers.js +30 -7
  49. package/dist/core/mcp-servers.js.map +1 -1
  50. package/dist/core/model-resolver.js +1 -1
  51. package/dist/core/model-resolver.js.map +1 -1
  52. package/dist/core/resource-loader.d.ts +3 -0
  53. package/dist/core/resource-loader.d.ts.map +1 -1
  54. package/dist/core/resource-loader.js +3 -3
  55. package/dist/core/resource-loader.js.map +1 -1
  56. package/dist/core/sdk.d.ts +9 -4
  57. package/dist/core/sdk.d.ts.map +1 -1
  58. package/dist/core/sdk.js +3 -2
  59. package/dist/core/sdk.js.map +1 -1
  60. package/dist/core/skills.d.ts +4 -1
  61. package/dist/core/skills.d.ts.map +1 -1
  62. package/dist/core/skills.js +6 -1
  63. package/dist/core/skills.js.map +1 -1
  64. package/dist/core/system-prompt.d.ts +6 -0
  65. package/dist/core/system-prompt.d.ts.map +1 -1
  66. package/dist/core/system-prompt.js +9 -4
  67. package/dist/core/system-prompt.js.map +1 -1
  68. package/dist/core/tools/output-accumulator.d.ts.map +1 -1
  69. package/dist/core/tools/output-accumulator.js +6 -11
  70. package/dist/core/tools/output-accumulator.js.map +1 -1
  71. package/dist/core/tools/read.d.ts +13 -0
  72. package/dist/core/tools/read.d.ts.map +1 -1
  73. package/dist/core/tools/read.js +18 -1
  74. package/dist/core/tools/read.js.map +1 -1
  75. package/dist/extensions/codemode/execute.d.ts.map +1 -1
  76. package/dist/extensions/codemode/execute.js +51 -9
  77. package/dist/extensions/codemode/execute.js.map +1 -1
  78. package/dist/extensions/codemode/index.d.ts.map +1 -1
  79. package/dist/extensions/codemode/index.js +1 -0
  80. package/dist/extensions/codemode/index.js.map +1 -1
  81. package/dist/extensions/codemode/tool.d.ts +9 -2
  82. package/dist/extensions/codemode/tool.d.ts.map +1 -1
  83. package/dist/extensions/codemode/tool.js +13 -5
  84. package/dist/extensions/codemode/tool.js.map +1 -1
  85. package/dist/extensions/mcp/resources.d.ts +3 -4
  86. package/dist/extensions/mcp/resources.d.ts.map +1 -1
  87. package/dist/extensions/mcp/resources.js +3 -4
  88. package/dist/extensions/mcp/resources.js.map +1 -1
  89. package/dist/extensions/mcp/runtime.d.ts +4 -1
  90. package/dist/extensions/mcp/runtime.d.ts.map +1 -1
  91. package/dist/extensions/mcp/runtime.js +22 -5
  92. package/dist/extensions/mcp/runtime.js.map +1 -1
  93. package/dist/extensions/mcp/tools.d.ts +2 -1
  94. package/dist/extensions/mcp/tools.d.ts.map +1 -1
  95. package/dist/extensions/mcp/tools.js +6 -10
  96. package/dist/extensions/mcp/tools.js.map +1 -1
  97. package/dist/main.d.ts.map +1 -1
  98. package/dist/main.js +1 -0
  99. package/dist/main.js.map +1 -1
  100. package/dist/modes/interactive/interactive-mode.d.ts +7 -0
  101. package/dist/modes/interactive/interactive-mode.d.ts.map +1 -1
  102. package/dist/modes/interactive/interactive-mode.js +42 -6
  103. package/dist/modes/interactive/interactive-mode.js.map +1 -1
  104. package/dist/modes/interactive/theme/theme.d.ts.map +1 -1
  105. package/dist/modes/interactive/theme/theme.js +1 -0
  106. package/dist/modes/interactive/theme/theme.js.map +1 -1
  107. package/dist/utils/output-files.d.ts +17 -0
  108. package/dist/utils/output-files.d.ts.map +1 -0
  109. package/dist/utils/output-files.js +30 -0
  110. package/dist/utils/output-files.js.map +1 -0
  111. package/dist/utils/syntax-highlight.d.ts.map +1 -1
  112. package/dist/utils/syntax-highlight.js +6 -1
  113. package/dist/utils/syntax-highlight.js.map +1 -1
  114. package/docs/codemode.md +6 -5
  115. package/docs/extensions.md +1 -1
  116. package/docs/keybindings.md +7 -7
  117. package/docs/mcp.md +3 -1
  118. package/docs/providers.md +5 -1
  119. package/docs/settings.md +1 -1
  120. package/docs/usage.md +15 -3
  121. package/examples/extensions/custom-provider-anthropic/package-lock.json +2 -2
  122. package/examples/extensions/custom-provider-anthropic/package.json +1 -1
  123. package/examples/extensions/custom-provider-gitlab-duo/package.json +1 -1
  124. package/examples/extensions/gondolin/package-lock.json +2 -2
  125. package/examples/extensions/gondolin/package.json +1 -1
  126. package/examples/extensions/sandbox/package-lock.json +2 -2
  127. package/examples/extensions/sandbox/package.json +1 -1
  128. package/examples/extensions/with-deps/package-lock.json +2 -2
  129. package/examples/extensions/with-deps/package.json +1 -1
  130. package/npm-shrinkwrap.json +54 -54
  131. package/package.json +11 -11
  132. package/dist/bundle/chunks/azure-openai-responses-SBLL5YN3.js +0 -2
  133. package/dist/bundle/chunks/chunk-G4RY3GN7.js +0 -11
  134. package/dist/bundle/chunks/chunk-TRHTWM3C.js +0 -2
  135. package/dist/bundle/chunks/virtual-modules-UUHBXSJB.js +0 -2
@@ -1 +1 @@
1
- {"version":3,"file":"resources.js","sourceRoot":"","sources":["../../../src/extensions/mcp/resources.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * MCP resources, through the tools Codex and opencode use: `list_mcp_resources`,\n * `list_mcp_resource_templates`, and `read_mcp_resource`. They take a `server` argument and cover\n * every connected server with resources, so models trained on those tools use them unchanged.\n *\n * Listings are JSON, as in Codex: `{ server?, resources: [{ server, ...resource }], nextCursor? }`.\n * With a `server`, one page is listed and `cursor` continues it; without, every page of every server.\n * MCP App resources (`ui://` URIs and `profile=mcp-app` HTML) are left out, since they are user\n * interfaces for hosts that render them, and so are icons. Read resources become text and images for\n * the model; binary resources are saved to temp files. Scripts get the JSON payloads.\n */\n\nimport type { ImageContent, JsonValue, TextContent } from \"@earendil-works/pi-ai\";\nimport type {\n\tContentBlock,\n\tListResourcesResult,\n\tListResourceTemplatesResult,\n\tMcpRequestOptions,\n\tReadResourceResult,\n\tResource,\n\tResourceTemplate,\n} from \"@earendil-works/pi-mcp\";\nimport type { TSchema } from \"typebox\";\nimport type { ToolAnnotations, ToolDefinition } from \"../../core/extensions/types.ts\";\nimport type { McpExposure } from \"./config.ts\";\nimport {\n\tlimitMcpContent,\n\ttype McpToolDetails,\n\tREAD_MCP_RESOURCE_TOOL,\n\ttoModelContent,\n\ttoToolExposure,\n} from \"./tools.ts\";\n\nexport const LIST_MCP_RESOURCES_TOOL = \"list_mcp_resources\";\nexport const LIST_MCP_RESOURCE_TEMPLATES_TOOL = \"list_mcp_resource_templates\";\nexport { READ_MCP_RESOURCE_TOOL };\n\n/** A connected server that offers resources. */\nexport interface McpResourceServer {\n\tname: string;\n\ttimeoutMs: number;\n\tresourcesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourcesResult>;\n\tresourceTemplatesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourceTemplatesResult>;\n\tallResources(options: McpRequestOptions): Promise<Resource[]>;\n\tallResourceTemplates(options: McpRequestOptions): Promise<ResourceTemplate[]>;\n\treadResource(uri: string, options: McpRequestOptions): Promise<ReadResourceResult>;\n}\n\n/** MCP App user interfaces, which only hosts that render them can use. */\nexport function isMcpAppResource(item: { uri?: string; uriTemplate?: string; mimeType?: string }): boolean {\n\tconst uri = item.uri ?? item.uriTemplate ?? \"\";\n\treturn uri.startsWith(\"ui://\") || /;\\s*profile\\s*=\\s*\"?mcp-app\"?/i.test(item.mimeType ?? \"\");\n}\n\n/** A listed resource or template without `_meta` and icons, tagged with its server. */\nfunction listed<T extends { _meta?: unknown }>(server: string, item: T): Record<string, unknown> {\n\tconst { _meta, icons: _icons, ...rest } = item as T & { icons?: unknown };\n\treturn { server, ...rest };\n}\n\nconst stringProperty = (description: string) => ({ type: \"string\", description });\nconst SERVER_FILTER = stringProperty(\"MCP server name. Omit to list every server with resources.\");\nconst CURSOR = stringProperty(\"Opaque cursor from a previous call with the same server; omit for the first page.\");\nconst LIST_PARAMETERS = {\n\ttype: \"object\",\n\tproperties: { server: SERVER_FILTER, cursor: CURSOR },\n\tadditionalProperties: false,\n};\nconst READ_PARAMETERS = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: stringProperty(\n\t\t\t\"MCP server name exactly as configured. Must match the 'server' field returned by list_mcp_resources.\",\n\t\t),\n\t\turi: stringProperty(\"Resource URI to read. Must be one of the URIs returned by list_mcp_resources.\"),\n\t},\n\trequired: [\"server\", \"uri\"],\n\tadditionalProperties: false,\n};\n\nconst optionalString = { type: \"string\" };\nconst LISTING_ERRORS = {\n\ttype: \"array\",\n\tdescription: \"Servers that could not be listed\",\n\titems: {\n\t\ttype: \"object\",\n\t\tproperties: { server: { type: \"string\" }, error: { type: \"string\" } },\n\t\trequired: [\"server\", \"error\"],\n\t},\n};\nconst LIST_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: optionalString,\n\t\tresources: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\ttype: \"object\",\n\t\t\t\tproperties: {\n\t\t\t\t\tserver: { type: \"string\" },\n\t\t\t\t\turi: { type: \"string\" },\n\t\t\t\t\tname: { type: \"string\" },\n\t\t\t\t\ttitle: optionalString,\n\t\t\t\t\tdescription: optionalString,\n\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t\tsize: { type: \"number\" },\n\t\t\t\t},\n\t\t\t\trequired: [\"server\", \"uri\", \"name\"],\n\t\t\t},\n\t\t},\n\t\tnextCursor: optionalString,\n\t\terrors: LISTING_ERRORS,\n\t},\n\trequired: [\"resources\"],\n};\nconst LIST_TEMPLATES_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: optionalString,\n\t\tresourceTemplates: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\ttype: \"object\",\n\t\t\t\tproperties: {\n\t\t\t\t\tserver: { type: \"string\" },\n\t\t\t\t\turiTemplate: { type: \"string\", description: \"RFC 6570 URI template\" },\n\t\t\t\t\tname: { type: \"string\" },\n\t\t\t\t\ttitle: optionalString,\n\t\t\t\t\tdescription: optionalString,\n\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t},\n\t\t\t\trequired: [\"server\", \"uriTemplate\", \"name\"],\n\t\t\t},\n\t\t},\n\t\tnextCursor: optionalString,\n\t\terrors: LISTING_ERRORS,\n\t},\n\trequired: [\"resourceTemplates\"],\n};\nconst READ_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: { type: \"string\" },\n\t\turi: { type: \"string\" },\n\t\tcontents: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\tanyOf: [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"object\",\n\t\t\t\t\t\tproperties: { uri: { type: \"string\" }, mimeType: optionalString, text: { type: \"string\" } },\n\t\t\t\t\t\trequired: [\"uri\", \"text\"],\n\t\t\t\t\t},\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"object\",\n\t\t\t\t\t\tproperties: {\n\t\t\t\t\t\t\turi: { type: \"string\" },\n\t\t\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t\t\t\tblob: { type: \"string\", description: \"base64\" },\n\t\t\t\t\t\t},\n\t\t\t\t\t\trequired: [\"uri\", \"blob\"],\n\t\t\t\t\t},\n\t\t\t\t],\n\t\t\t},\n\t\t},\n\t},\n\trequired: [\"server\", \"uri\", \"contents\"],\n};\n\nfunction stringArgument(params: unknown, key: string): string | undefined {\n\tconst value = (params as Record<string, unknown> | undefined)?.[key];\n\tif (value === undefined || value === null) return undefined;\n\tif (typeof value !== \"string\") throw new Error(`${key} must be a string`);\n\treturn value.trim() || undefined;\n}\n\nfunction errorMessage(error: unknown): string {\n\treturn error instanceof Error ? error.message : String(error);\n}\n\nasync function jsonResult(\n\ttool: string,\n\tserver: string | undefined,\n\tpayload: Record<string, unknown>,\n): Promise<{ content: (TextContent | ImageContent)[]; details: McpToolDetails; structuredContent: JsonValue }> {\n\tconst { content, fullOutputPath } = await limitMcpContent([{ type: \"text\", text: JSON.stringify(payload) }]);\n\treturn {\n\t\tcontent,\n\t\tdetails: { server: server ?? \"\", tool, ...(fullOutputPath ? { fullOutputPath } : {}) },\n\t\tstructuredContent: payload as unknown as JsonValue,\n\t};\n}\n\n/**\n * The three resource tools. `servers` returns the servers whose resources they reach, at call time.\n */\nexport function createMcpResourceToolDefinitions(options: {\n\texposure: McpExposure;\n\tservers: () => readonly McpResourceServer[];\n}): ToolDefinition<TSchema, McpToolDetails>[] {\n\tconst readOnly: ToolAnnotations = { readOnlyHint: true };\n\n\tconst findServer = (name: string): McpResourceServer => {\n\t\tconst servers = options.servers();\n\t\tconst server = servers.find((candidate) => candidate.name === name);\n\t\tif (server) return server;\n\t\tconst available = servers.map((candidate) => candidate.name).join(\", \");\n\t\tthrow new Error(\n\t\t\t`MCP server \"${name}\" has no resources${available ? `. Servers with resources: ${available}` : \"\"}`,\n\t\t);\n\t};\n\n\t/** One page of one server, or every page of every server. */\n\tconst list = async <T extends { _meta?: unknown }>(\n\t\tparams: unknown,\n\t\tsignal: AbortSignal | undefined,\n\t\tkey: \"resources\" | \"resourceTemplates\",\n\t\tpage: (\n\t\t\tserver: McpResourceServer,\n\t\t\tcursor: string | undefined,\n\t\t\toptions: McpRequestOptions,\n\t\t) => Promise<{\n\t\t\titems: T[];\n\t\t\tnextCursor?: string;\n\t\t}>,\n\t\tall: (server: McpResourceServer, options: McpRequestOptions) => Promise<T[]>,\n\t): Promise<Record<string, unknown>> => {\n\t\tconst serverName = stringArgument(params, \"server\");\n\t\tconst cursor = stringArgument(params, \"cursor\");\n\t\tconst visible = (item: T) => !isMcpAppResource(item as { uri?: string; uriTemplate?: string; mimeType?: string });\n\t\tif (serverName) {\n\t\t\tconst server = findServer(serverName);\n\t\t\tconst result = await page(server, cursor, { signal, timeoutMs: server.timeoutMs });\n\t\t\treturn {\n\t\t\t\tserver: server.name,\n\t\t\t\t[key]: result.items.filter(visible).map((item) => listed(server.name, item)),\n\t\t\t\t...(result.nextCursor === undefined ? {} : { nextCursor: result.nextCursor }),\n\t\t\t};\n\t\t}\n\t\tif (cursor) throw new Error(\"cursor can only be used when a server is specified\");\n\t\tconst servers = [...options.servers()].sort((a, b) => a.name.localeCompare(b.name));\n\t\tconst results = await Promise.allSettled(\n\t\t\tservers.map((server) => all(server, { signal, timeoutMs: server.timeoutMs })),\n\t\t);\n\t\tconst items: Record<string, unknown>[] = [];\n\t\tconst errors: { server: string; error: string }[] = [];\n\t\tresults.forEach((result, index) => {\n\t\t\tconst server = servers[index].name;\n\t\t\tif (result.status === \"fulfilled\")\n\t\t\t\titems.push(...result.value.filter(visible).map((item) => listed(server, item)));\n\t\t\telse errors.push({ server, error: errorMessage(result.reason) });\n\t\t});\n\t\treturn { [key]: items, ...(errors.length > 0 ? { errors } : {}) };\n\t};\n\n\tconst listResources: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: LIST_MCP_RESOURCES_TOOL,\n\t\tlabel: LIST_MCP_RESOURCES_TOOL,\n\t\tdescription:\n\t\t\t\"Lists resources provided by MCP servers. Resources allow servers to share data that provides context to language models, such as files, database schemas, or application-specific information. Prefer resources over web search when possible.\",\n\t\tparameters: LIST_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: LIST_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst payload = await list(\n\t\t\t\tparams,\n\t\t\t\tsignal,\n\t\t\t\t\"resources\",\n\t\t\t\tasync (server, cursor, requestOptions) => {\n\t\t\t\t\tconst result = await server.resourcesPage(cursor, requestOptions);\n\t\t\t\t\treturn { items: result.resources, nextCursor: result.nextCursor };\n\t\t\t\t},\n\t\t\t\t(server, requestOptions) => server.allResources(requestOptions),\n\t\t\t);\n\t\t\treturn jsonResult(LIST_MCP_RESOURCES_TOOL, stringArgument(params, \"server\"), payload);\n\t\t},\n\t};\n\n\tconst listTemplates: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: LIST_MCP_RESOURCE_TEMPLATES_TOOL,\n\t\tlabel: LIST_MCP_RESOURCE_TEMPLATES_TOOL,\n\t\tdescription:\n\t\t\t\"Lists resource templates provided by MCP servers. Parameterized resource templates allow servers to share data that takes parameters and provides context to language models, such as files, database schemas, or application-specific information. Prefer resource templates over web search when possible.\",\n\t\tparameters: LIST_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: LIST_TEMPLATES_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst payload = await list(\n\t\t\t\tparams,\n\t\t\t\tsignal,\n\t\t\t\t\"resourceTemplates\",\n\t\t\t\tasync (server, cursor, requestOptions) => {\n\t\t\t\t\tconst result = await server.resourceTemplatesPage(cursor, requestOptions);\n\t\t\t\t\treturn { items: result.resourceTemplates, nextCursor: result.nextCursor };\n\t\t\t\t},\n\t\t\t\t(server, requestOptions) => server.allResourceTemplates(requestOptions),\n\t\t\t);\n\t\t\treturn jsonResult(LIST_MCP_RESOURCE_TEMPLATES_TOOL, stringArgument(params, \"server\"), payload);\n\t\t},\n\t};\n\n\tconst readResource: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: READ_MCP_RESOURCE_TOOL,\n\t\tlabel: READ_MCP_RESOURCE_TOOL,\n\t\tdescription: \"Read a specific resource from an MCP server given the server name and resource URI.\",\n\t\tparameters: READ_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: READ_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst serverName = stringArgument(params, \"server\");\n\t\t\tconst uri = stringArgument(params, \"uri\");\n\t\t\tif (!serverName) throw new Error(\"server must be provided\");\n\t\t\tif (!uri) throw new Error(\"uri must be provided\");\n\t\t\tconst server = findServer(serverName);\n\t\t\tconst result = await server.readResource(uri, { signal, timeoutMs: server.timeoutMs });\n\t\t\t// Several contents (for example a directory) are labeled with their URIs.\n\t\t\tconst blocks: ContentBlock[] = result.contents.flatMap((contents) => [\n\t\t\t\t...(result.contents.length > 1 ? [{ type: \"text\" as const, text: `${contents.uri}:` }] : []),\n\t\t\t\t{ type: \"resource\" as const, resource: contents },\n\t\t\t]);\n\t\t\tconst converted = await toModelContent(server.name, blocks);\n\t\t\tconst { content, fullOutputPath } = await limitMcpContent(\n\t\t\t\tconverted.length > 0 ? converted : [{ type: \"text\", text: `Resource ${uri} is empty.` }],\n\t\t\t);\n\t\t\tconst contents = result.contents.map(({ _meta: _ignored, ...rest }) => rest);\n\t\t\treturn {\n\t\t\t\tcontent,\n\t\t\t\tdetails: {\n\t\t\t\t\tserver: server.name,\n\t\t\t\t\ttool: READ_MCP_RESOURCE_TOOL,\n\t\t\t\t\t...(fullOutputPath ? { fullOutputPath } : {}),\n\t\t\t\t},\n\t\t\t\tstructuredContent: { server: server.name, uri, contents } as unknown as JsonValue,\n\t\t\t};\n\t\t},\n\t};\n\n\treturn [listResources, listTemplates, readResource];\n}\n"]}
1
+ {"version":3,"file":"resources.js","sourceRoot":"","sources":["../../../src/extensions/mcp/resources.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * MCP resources, through the tools Codex and opencode use: `list_mcp_resources`,\n * `list_mcp_resource_templates`, and `read_mcp_resource`. They take a `server` argument and cover\n * every connected server with resources, so models trained on those tools use them unchanged.\n *\n * Listings are JSON, as in Codex: `{ server?, resources: [{ server, ...resource }], nextCursor? }`.\n * With a `server`, one page is listed and `cursor` continues it; without, every page of every server.\n * MCP App resources (`ui://` URIs and `profile=mcp-app` HTML) are left out, since they are user\n * interfaces for hosts that render them, and so are icons. Read resources become text and images for\n * the model; binary resources are saved to temp files. Scripts get the JSON payloads.\n */\n\nimport type { ImageContent, JsonValue, TextContent } from \"@earendil-works/pi-ai\";\nimport type {\n\tContentBlock,\n\tListResourcesResult,\n\tListResourceTemplatesResult,\n\tMcpRequestOptions,\n\tReadResourceResult,\n\tResource,\n\tResourceTemplate,\n} from \"@earendil-works/pi-mcp\";\nimport type { TSchema } from \"typebox\";\nimport type { ToolAnnotations, ToolDefinition } from \"../../core/extensions/types.ts\";\nimport {\n\tLIST_MCP_RESOURCE_TEMPLATES_TOOL,\n\tLIST_MCP_RESOURCES_TOOL,\n\tREAD_MCP_RESOURCE_TOOL,\n} from \"../../core/mcp-servers.ts\";\nimport type { McpExposure } from \"./config.ts\";\nimport { limitMcpContent, type McpToolDetails, toModelContent, toToolExposure } from \"./tools.ts\";\n\nexport { LIST_MCP_RESOURCE_TEMPLATES_TOOL, LIST_MCP_RESOURCES_TOOL, READ_MCP_RESOURCE_TOOL };\n\n/** A connected server that offers resources. */\nexport interface McpResourceServer {\n\tname: string;\n\ttimeoutMs: number;\n\tresourcesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourcesResult>;\n\tresourceTemplatesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourceTemplatesResult>;\n\tallResources(options: McpRequestOptions): Promise<Resource[]>;\n\tallResourceTemplates(options: McpRequestOptions): Promise<ResourceTemplate[]>;\n\treadResource(uri: string, options: McpRequestOptions): Promise<ReadResourceResult>;\n}\n\n/** MCP App user interfaces, which only hosts that render them can use. */\nexport function isMcpAppResource(item: { uri?: string; uriTemplate?: string; mimeType?: string }): boolean {\n\tconst uri = item.uri ?? item.uriTemplate ?? \"\";\n\treturn uri.startsWith(\"ui://\") || /;\\s*profile\\s*=\\s*\"?mcp-app\"?/i.test(item.mimeType ?? \"\");\n}\n\n/** A listed resource or template without `_meta` and icons, tagged with its server. */\nfunction listed<T extends { _meta?: unknown }>(server: string, item: T): Record<string, unknown> {\n\tconst { _meta, icons: _icons, ...rest } = item as T & { icons?: unknown };\n\treturn { server, ...rest };\n}\n\nconst stringProperty = (description: string) => ({ type: \"string\", description });\nconst SERVER_FILTER = stringProperty(\"MCP server name. Omit to list every server with resources.\");\nconst CURSOR = stringProperty(\"Opaque cursor from a previous call with the same server; omit for the first page.\");\nconst LIST_PARAMETERS = {\n\ttype: \"object\",\n\tproperties: { server: SERVER_FILTER, cursor: CURSOR },\n\tadditionalProperties: false,\n};\nconst READ_PARAMETERS = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: stringProperty(\n\t\t\t\"MCP server name exactly as configured. Must match the 'server' field returned by list_mcp_resources.\",\n\t\t),\n\t\turi: stringProperty(\"Resource URI to read. Must be one of the URIs returned by list_mcp_resources.\"),\n\t},\n\trequired: [\"server\", \"uri\"],\n\tadditionalProperties: false,\n};\n\nconst optionalString = { type: \"string\" };\nconst LISTING_ERRORS = {\n\ttype: \"array\",\n\tdescription: \"Servers that could not be listed\",\n\titems: {\n\t\ttype: \"object\",\n\t\tproperties: { server: { type: \"string\" }, error: { type: \"string\" } },\n\t\trequired: [\"server\", \"error\"],\n\t},\n};\nconst LIST_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: optionalString,\n\t\tresources: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\ttype: \"object\",\n\t\t\t\tproperties: {\n\t\t\t\t\tserver: { type: \"string\" },\n\t\t\t\t\turi: { type: \"string\" },\n\t\t\t\t\tname: { type: \"string\" },\n\t\t\t\t\ttitle: optionalString,\n\t\t\t\t\tdescription: optionalString,\n\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t\tsize: { type: \"number\" },\n\t\t\t\t},\n\t\t\t\trequired: [\"server\", \"uri\", \"name\"],\n\t\t\t},\n\t\t},\n\t\tnextCursor: optionalString,\n\t\terrors: LISTING_ERRORS,\n\t},\n\trequired: [\"resources\"],\n};\nconst LIST_TEMPLATES_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: optionalString,\n\t\tresourceTemplates: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\ttype: \"object\",\n\t\t\t\tproperties: {\n\t\t\t\t\tserver: { type: \"string\" },\n\t\t\t\t\turiTemplate: { type: \"string\", description: \"RFC 6570 URI template\" },\n\t\t\t\t\tname: { type: \"string\" },\n\t\t\t\t\ttitle: optionalString,\n\t\t\t\t\tdescription: optionalString,\n\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t},\n\t\t\t\trequired: [\"server\", \"uriTemplate\", \"name\"],\n\t\t\t},\n\t\t},\n\t\tnextCursor: optionalString,\n\t\terrors: LISTING_ERRORS,\n\t},\n\trequired: [\"resourceTemplates\"],\n};\nconst READ_OUTPUT_SCHEMA = {\n\ttype: \"object\",\n\tproperties: {\n\t\tserver: { type: \"string\" },\n\t\turi: { type: \"string\" },\n\t\tcontents: {\n\t\t\ttype: \"array\",\n\t\t\titems: {\n\t\t\t\tanyOf: [\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"object\",\n\t\t\t\t\t\tproperties: { uri: { type: \"string\" }, mimeType: optionalString, text: { type: \"string\" } },\n\t\t\t\t\t\trequired: [\"uri\", \"text\"],\n\t\t\t\t\t},\n\t\t\t\t\t{\n\t\t\t\t\t\ttype: \"object\",\n\t\t\t\t\t\tproperties: {\n\t\t\t\t\t\t\turi: { type: \"string\" },\n\t\t\t\t\t\t\tmimeType: optionalString,\n\t\t\t\t\t\t\tblob: { type: \"string\", description: \"base64\" },\n\t\t\t\t\t\t},\n\t\t\t\t\t\trequired: [\"uri\", \"blob\"],\n\t\t\t\t\t},\n\t\t\t\t],\n\t\t\t},\n\t\t},\n\t},\n\trequired: [\"server\", \"uri\", \"contents\"],\n};\n\nfunction stringArgument(params: unknown, key: string): string | undefined {\n\tconst value = (params as Record<string, unknown> | undefined)?.[key];\n\tif (value === undefined || value === null) return undefined;\n\tif (typeof value !== \"string\") throw new Error(`${key} must be a string`);\n\treturn value.trim() || undefined;\n}\n\nfunction errorMessage(error: unknown): string {\n\treturn error instanceof Error ? error.message : String(error);\n}\n\nasync function jsonResult(\n\ttool: string,\n\tserver: string | undefined,\n\tpayload: Record<string, unknown>,\n): Promise<{ content: (TextContent | ImageContent)[]; details: McpToolDetails; structuredContent: JsonValue }> {\n\tconst { content, fullOutputPath } = await limitMcpContent([{ type: \"text\", text: JSON.stringify(payload) }]);\n\treturn {\n\t\tcontent,\n\t\tdetails: { server: server ?? \"\", tool, ...(fullOutputPath ? { fullOutputPath } : {}) },\n\t\tstructuredContent: payload as unknown as JsonValue,\n\t};\n}\n\n/**\n * The three resource tools. `servers` returns the servers whose resources they reach, at call time.\n */\nexport function createMcpResourceToolDefinitions(options: {\n\texposure: McpExposure;\n\tservers: () => readonly McpResourceServer[];\n}): ToolDefinition<TSchema, McpToolDetails>[] {\n\tconst readOnly: ToolAnnotations = { readOnlyHint: true };\n\n\tconst findServer = (name: string): McpResourceServer => {\n\t\tconst servers = options.servers();\n\t\tconst server = servers.find((candidate) => candidate.name === name);\n\t\tif (server) return server;\n\t\tconst available = servers.map((candidate) => candidate.name).join(\", \");\n\t\tthrow new Error(\n\t\t\t`MCP server \"${name}\" has no resources${available ? `. Servers with resources: ${available}` : \"\"}`,\n\t\t);\n\t};\n\n\t/** One page of one server, or every page of every server. */\n\tconst list = async <T extends { _meta?: unknown }>(\n\t\tparams: unknown,\n\t\tsignal: AbortSignal | undefined,\n\t\tkey: \"resources\" | \"resourceTemplates\",\n\t\tpage: (\n\t\t\tserver: McpResourceServer,\n\t\t\tcursor: string | undefined,\n\t\t\toptions: McpRequestOptions,\n\t\t) => Promise<{\n\t\t\titems: T[];\n\t\t\tnextCursor?: string;\n\t\t}>,\n\t\tall: (server: McpResourceServer, options: McpRequestOptions) => Promise<T[]>,\n\t): Promise<Record<string, unknown>> => {\n\t\tconst serverName = stringArgument(params, \"server\");\n\t\tconst cursor = stringArgument(params, \"cursor\");\n\t\tconst visible = (item: T) => !isMcpAppResource(item as { uri?: string; uriTemplate?: string; mimeType?: string });\n\t\tif (serverName) {\n\t\t\tconst server = findServer(serverName);\n\t\t\tconst result = await page(server, cursor, { signal, timeoutMs: server.timeoutMs });\n\t\t\treturn {\n\t\t\t\tserver: server.name,\n\t\t\t\t[key]: result.items.filter(visible).map((item) => listed(server.name, item)),\n\t\t\t\t...(result.nextCursor === undefined ? {} : { nextCursor: result.nextCursor }),\n\t\t\t};\n\t\t}\n\t\tif (cursor) throw new Error(\"cursor can only be used when a server is specified\");\n\t\tconst servers = [...options.servers()].sort((a, b) => a.name.localeCompare(b.name));\n\t\tconst results = await Promise.allSettled(\n\t\t\tservers.map((server) => all(server, { signal, timeoutMs: server.timeoutMs })),\n\t\t);\n\t\tconst items: Record<string, unknown>[] = [];\n\t\tconst errors: { server: string; error: string }[] = [];\n\t\tresults.forEach((result, index) => {\n\t\t\tconst server = servers[index].name;\n\t\t\tif (result.status === \"fulfilled\")\n\t\t\t\titems.push(...result.value.filter(visible).map((item) => listed(server, item)));\n\t\t\telse errors.push({ server, error: errorMessage(result.reason) });\n\t\t});\n\t\treturn { [key]: items, ...(errors.length > 0 ? { errors } : {}) };\n\t};\n\n\tconst listResources: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: LIST_MCP_RESOURCES_TOOL,\n\t\tlabel: LIST_MCP_RESOURCES_TOOL,\n\t\tdescription:\n\t\t\t\"Lists resources provided by MCP servers. Resources allow servers to share data that provides context to language models, such as files, database schemas, or application-specific information. Prefer resources over web search when possible.\",\n\t\tparameters: LIST_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: LIST_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst payload = await list(\n\t\t\t\tparams,\n\t\t\t\tsignal,\n\t\t\t\t\"resources\",\n\t\t\t\tasync (server, cursor, requestOptions) => {\n\t\t\t\t\tconst result = await server.resourcesPage(cursor, requestOptions);\n\t\t\t\t\treturn { items: result.resources, nextCursor: result.nextCursor };\n\t\t\t\t},\n\t\t\t\t(server, requestOptions) => server.allResources(requestOptions),\n\t\t\t);\n\t\t\treturn jsonResult(LIST_MCP_RESOURCES_TOOL, stringArgument(params, \"server\"), payload);\n\t\t},\n\t};\n\n\tconst listTemplates: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: LIST_MCP_RESOURCE_TEMPLATES_TOOL,\n\t\tlabel: LIST_MCP_RESOURCE_TEMPLATES_TOOL,\n\t\tdescription:\n\t\t\t\"Lists resource templates provided by MCP servers. Parameterized resource templates allow servers to share data that takes parameters and provides context to language models, such as files, database schemas, or application-specific information. Prefer resource templates over web search when possible.\",\n\t\tparameters: LIST_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: LIST_TEMPLATES_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst payload = await list(\n\t\t\t\tparams,\n\t\t\t\tsignal,\n\t\t\t\t\"resourceTemplates\",\n\t\t\t\tasync (server, cursor, requestOptions) => {\n\t\t\t\t\tconst result = await server.resourceTemplatesPage(cursor, requestOptions);\n\t\t\t\t\treturn { items: result.resourceTemplates, nextCursor: result.nextCursor };\n\t\t\t\t},\n\t\t\t\t(server, requestOptions) => server.allResourceTemplates(requestOptions),\n\t\t\t);\n\t\t\treturn jsonResult(LIST_MCP_RESOURCE_TEMPLATES_TOOL, stringArgument(params, \"server\"), payload);\n\t\t},\n\t};\n\n\tconst readResource: ToolDefinition<TSchema, McpToolDetails> = {\n\t\tname: READ_MCP_RESOURCE_TOOL,\n\t\tlabel: READ_MCP_RESOURCE_TOOL,\n\t\tdescription: \"Read a specific resource from an MCP server given the server name and resource URI.\",\n\t\tparameters: READ_PARAMETERS as unknown as TSchema,\n\t\toutputSchema: READ_OUTPUT_SCHEMA as unknown as TSchema,\n\t\texposure: toToolExposure(options.exposure),\n\t\tannotations: readOnly,\n\t\tasync execute(_toolCallId, params, signal) {\n\t\t\tconst serverName = stringArgument(params, \"server\");\n\t\t\tconst uri = stringArgument(params, \"uri\");\n\t\t\tif (!serverName) throw new Error(\"server must be provided\");\n\t\t\tif (!uri) throw new Error(\"uri must be provided\");\n\t\t\tconst server = findServer(serverName);\n\t\t\tconst result = await server.readResource(uri, { signal, timeoutMs: server.timeoutMs });\n\t\t\t// Several contents (for example a directory) are labeled with their URIs.\n\t\t\tconst blocks: ContentBlock[] = result.contents.flatMap((contents) => [\n\t\t\t\t...(result.contents.length > 1 ? [{ type: \"text\" as const, text: `${contents.uri}:` }] : []),\n\t\t\t\t{ type: \"resource\" as const, resource: contents },\n\t\t\t]);\n\t\t\tconst converted = await toModelContent(server.name, blocks);\n\t\t\tconst { content, fullOutputPath } = await limitMcpContent(\n\t\t\t\tconverted.length > 0 ? converted : [{ type: \"text\", text: `Resource ${uri} is empty.` }],\n\t\t\t);\n\t\t\tconst contents = result.contents.map(({ _meta: _ignored, ...rest }) => rest);\n\t\t\treturn {\n\t\t\t\tcontent,\n\t\t\t\tdetails: {\n\t\t\t\t\tserver: server.name,\n\t\t\t\t\ttool: READ_MCP_RESOURCE_TOOL,\n\t\t\t\t\t...(fullOutputPath ? { fullOutputPath } : {}),\n\t\t\t\t},\n\t\t\t\tstructuredContent: { server: server.name, uri, contents } as unknown as JsonValue,\n\t\t\t};\n\t\t},\n\t};\n\n\treturn [listResources, listTemplates, readResource];\n}\n"]}
@@ -38,7 +38,8 @@ export declare class McpServerConnection implements McpToolCaller, McpResourceSe
38
38
  challenge: OAuthChallenge | undefined;
39
39
  private client;
40
40
  private opening;
41
- private closed;
41
+ /** Aborted by `close()`; cancels a connect in progress, including the wait between retries. */
42
+ private readonly shutdown;
42
43
  /** Stderr of the last stdio server that failed to connect. */
43
44
  private stderrTail;
44
45
  private readonly cwd;
@@ -61,6 +62,7 @@ export declare class McpServerConnection implements McpToolCaller, McpResourceSe
61
62
  log?: McpServerLog;
62
63
  });
63
64
  get name(): string;
65
+ private get closed();
64
66
  get timeoutMs(): number;
65
67
  /** Server URL when the server authenticates with OAuth. */
66
68
  get oauthUrl(): string | undefined;
@@ -93,6 +95,7 @@ export declare class McpServerConnection implements McpToolCaller, McpResourceSe
93
95
  private handleClientClose;
94
96
  private refreshTools;
95
97
  private refreshResources;
98
+ /** Resolves once no transport of this server is open, including one that was still connecting. */
96
99
  close(): Promise<void>;
97
100
  }
98
101
  //# sourceMappingURL=runtime.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../../src/extensions/mcp/runtime.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"runtime.d.ts","sourceRoot":"","sources":["../../../src/extensions/mcp/runtime.ts"],"names":[],"mappings":"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"}
@@ -5,6 +5,7 @@
5
5
  */
6
6
  import { homedir } from "node:os";
7
7
  import { basename, join, resolve } from "node:path";
8
+ import { setTimeout as sleep } from "node:timers/promises";
8
9
  import { pathToFileURL } from "node:url";
9
10
  import { JSON_RPC_ERROR_CODES, McpAuthRequiredError, McpClient, McpError, McpHttpError, McpSessionExpiredError, StdioTransport, StreamableHttpTransport, } from "@earendil-works/pi-mcp";
10
11
  import { McpOAuthAuthorizationRequiredError } from "@earendil-works/pi-mcp/oauth";
@@ -109,7 +110,8 @@ export class McpServerConnection {
109
110
  this.hasResources = false;
110
111
  this.resources = [];
111
112
  this.resourceTemplates = [];
112
- this.closed = false;
113
+ /** Aborted by `close()`; cancels a connect in progress, including the wait between retries. */
114
+ this.shutdown = new AbortController();
113
115
  this.entry = options.entry;
114
116
  this.cwd = options.cwd;
115
117
  this.createTransport = options.createTransport;
@@ -135,6 +137,9 @@ export class McpServerConnection {
135
137
  get name() {
136
138
  return this.entry.name;
137
139
  }
140
+ get closed() {
141
+ return this.shutdown.signal.aborted;
142
+ }
138
143
  get timeoutMs() {
139
144
  return (this.entry.config.timeout ?? DEFAULT_TIMEOUT_SECONDS) * 1000;
140
145
  }
@@ -265,7 +270,7 @@ export class McpServerConnection {
265
270
  if (this.closed || delay === undefined || !isTransientError(error)) {
266
271
  throw this.connectFailed(error);
267
272
  }
268
- await new Promise((resolve) => setTimeout(resolve, delay));
273
+ await sleep(delay, undefined, { signal: this.shutdown.signal }).catch(() => undefined);
269
274
  if (this.closed)
270
275
  throw this.connectFailed(error);
271
276
  }
@@ -281,6 +286,14 @@ export class McpServerConnection {
281
286
  const log = this.log;
282
287
  if (log)
283
288
  client.onNotification("notifications/message", (params) => log.write(this.entry.name, params));
289
+ // Closing the client fails its pending initialize or discovery requests and closes the transport.
290
+ // Memoized: a second `client.close()` returns before the first finished closing the transport.
291
+ let closing;
292
+ const closeClient = () => {
293
+ closing ??= client.close().catch(() => undefined);
294
+ return closing;
295
+ };
296
+ this.shutdown.signal.addEventListener("abort", closeClient, { once: true });
284
297
  let transport;
285
298
  try {
286
299
  transport = this.createTransport(this.entry, this.cwd, this.authProvider);
@@ -316,12 +329,15 @@ export class McpServerConnection {
316
329
  return client;
317
330
  }
318
331
  catch (error) {
319
- await client.close().catch(() => undefined);
332
+ await closeClient();
320
333
  if (transport instanceof StdioTransport) {
321
334
  this.stderrTail = transport.stderr.trim().slice(-STDERR_TAIL_CHARS) || undefined;
322
335
  }
323
336
  throw error;
324
337
  }
338
+ finally {
339
+ this.shutdown.signal.removeEventListener("abort", closeClient);
340
+ }
325
341
  }
326
342
  connectFailed(error) {
327
343
  if (this.needsSignIn(error) && !this.closed) {
@@ -365,13 +381,14 @@ export class McpServerConnection {
365
381
  this.onTools(this);
366
382
  this.changed();
367
383
  }
384
+ /** Resolves once no transport of this server is open, including one that was still connecting. */
368
385
  async close() {
369
- this.closed = true;
386
+ this.shutdown.abort();
370
387
  this.state = "closed";
371
388
  this.changed();
372
389
  const client = this.client;
373
390
  this.client = undefined;
374
- await client?.close().catch(() => undefined);
391
+ await Promise.all([client?.close().catch(() => undefined), this.opening?.catch(() => undefined)]);
375
392
  // A refresh the server already answered may have rotated the refresh token; exiting before the
376
393
  // new tokens are saved would lose the grant.
377
394
  await this.authProvider?.settled();
@@ -1 +1 @@
1
- {"version":3,"file":"runtime.js","sourceRoot":"","sources":["../../../src/extensions/mcp/runtime.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * The part of the MCP integration that talks to servers: connections, transports, and OAuth\n * sign-in. It pulls in the MCP client, so index.ts loads it through runtime.lazy.ts only when a\n * server is configured.\n */\n\nimport { homedir } from \"node:os\";\nimport { basename, join, resolve } from \"node:path\";\nimport { pathToFileURL } from \"node:url\";\nimport {\n\ttype AuthProvider,\n\ttype CallToolResult,\n\tJSON_RPC_ERROR_CODES,\n\ttype ListResourcesResult,\n\ttype ListResourceTemplatesResult,\n\tMcpAuthRequiredError,\n\tMcpClient,\n\tMcpError,\n\tMcpHttpError,\n\ttype McpRequestOptions,\n\tMcpSessionExpiredError,\n\ttype Tool as McpTool,\n\ttype McpTransport,\n\ttype ReadResourceResult,\n\ttype Resource,\n\ttype ResourceTemplate,\n\tStdioTransport,\n\tStreamableHttpTransport,\n} from \"@earendil-works/pi-mcp\";\nimport { McpOAuthAuthorizationRequiredError, type OAuthChallenge } from \"@earendil-works/pi-mcp/oauth\";\nimport { VERSION } from \"../../config.ts\";\nimport { resolveConfigValueOrThrow, resolveHeadersOrThrow } from \"../../core/resolve-config-value.ts\";\nimport type { McpServerEntry } from \"./config.ts\";\nimport type { McpServerLog } from \"./log.ts\";\nimport {\n\tcreateMcpAuthProvider,\n\ttype McpAuthProvider,\n\ttype McpOAuthCredentialStore,\n\ttype McpOAuthSettings,\n} from \"./oauth.ts\";\nimport { isMcpAppResource, type McpResourceServer } from \"./resources.ts\";\nimport type { McpToolCaller } from \"./tools.ts\";\n\nexport { McpServerLog } from \"./log.ts\";\nexport { McpOAuthCredentialStore, McpSignInCancelledError, signInMcpServer } from \"./oauth.ts\";\n\nconst DEFAULT_TIMEOUT_SECONDS = 60;\nconst STDERR_TAIL_CHARS = 2_000;\n/** Delays between attempts to connect to an HTTP server that failed with a transient error. */\nconst CONNECT_RETRY_DELAYS_MS = [250, 1_000];\n\n/**\n * `disconnected`: the connection dropped (for example the stdio server exited); the next call\n * reconnects.\n */\ntype ServerState = \"connecting\" | \"connected\" | \"disconnected\" | \"needs-auth\" | \"failed\" | \"closed\";\n\nexport type McpTransportFactory = (\n\tentry: McpServerEntry,\n\tcwd: string,\n\tauthProvider: AuthProvider | undefined,\n) => McpTransport;\n\nfunction errorMessage(error: unknown): string {\n\treturn error instanceof Error ? error.message : String(error);\n}\n\n/** Network failures and overloaded or restarting servers, which are worth another attempt. */\nfunction isTransientError(error: unknown): boolean {\n\tif (error instanceof McpHttpError) {\n\t\treturn error.status === 408 || error.status === 429 || (error.status >= 500 && error.status !== 501);\n\t}\n\treturn error instanceof TypeError;\n}\n\nfunction signInRequiredMessage(entry: McpServerEntry): string {\n\tconst provider = \"url\" in entry.config ? entry.config.auth?.provider : undefined;\n\treturn `MCP server \"${entry.name}\" requires sign-in. Run ${provider ? `/login ${provider}` : \"/mcp\"} to sign in.`;\n}\n\n/** HTTP servers authenticate with OAuth unless the config supplies an `Authorization` header or `auth`. */\nfunction usesOAuth(entry: McpServerEntry): boolean {\n\tconst { config } = entry;\n\tif (!(\"url\" in config) || config.auth) return false;\n\treturn !Object.keys(config.headers ?? {}).some((header) => header.toLowerCase() === \"authorization\");\n}\n\n/** `~` and `~/…` (also `~\\…` on Windows) name the home directory, like in a shell. */\nfunction expandHome(value: string): string {\n\tif (value === \"~\") return homedir();\n\tif (value.startsWith(\"~/\") || (process.platform === \"win32\" && value.startsWith(\"~\\\\\"))) {\n\t\treturn join(homedir(), value.slice(2));\n\t}\n\treturn value;\n}\n\nexport function createDefaultTransport(\n\tentry: McpServerEntry,\n\tcwd: string,\n\tauthProvider: AuthProvider | undefined,\n): McpTransport {\n\tconst { config, name } = entry;\n\tif (\"url\" in config) {\n\t\treturn new StreamableHttpTransport({\n\t\t\turl: config.url,\n\t\t\theaders: resolveHeadersOrThrow(config.headers, `MCP server \"${name}\"`),\n\t\t\tauthProvider,\n\t\t});\n\t}\n\tconst env: Record<string, string> = {};\n\tfor (const [key, value] of Object.entries(config.env ?? {})) {\n\t\tenv[key] = resolveConfigValueOrThrow(value, `MCP server \"${name}\" env \"${key}\"`);\n\t}\n\treturn new StdioTransport({\n\t\tcommand: expandHome(config.command),\n\t\targs: config.args?.map(expandHome),\n\t\tcwd: resolve(cwd, expandHome(config.cwd ?? \".\")),\n\t\tenv,\n\t\tstderr: \"pipe\",\n\t});\n}\n\n/** Servers that do not implement `resources/templates/list` have no templates. */\nasync function withoutTemplates<T>(list: () => Promise<T>, empty: T): Promise<T> {\n\ttry {\n\t\treturn await list();\n\t} catch (error) {\n\t\tif (error instanceof McpError && error.code === JSON_RPC_ERROR_CODES.methodNotFound) return empty;\n\t\tthrow error;\n\t}\n}\n\nfunction listTemplates(client: McpClient, options: McpRequestOptions = {}): Promise<ResourceTemplate[]> {\n\treturn withoutTemplates(() => client.listResourceTemplates(options), []);\n}\n\n/**\n * Resources and templates at connect time, for the counts in `/mcp` and `pi mcp list`. A server\n * whose lists fail still connects: the resource tools list and read its resources on demand.\n */\nasync function fetchResources(\n\tclient: McpClient,\n): Promise<{ resources: Resource[]; resourceTemplates: ResourceTemplate[] }> {\n\tconst [resources, resourceTemplates] = await Promise.all([\n\t\tclient.listResources().catch(() => []),\n\t\tlistTemplates(client).catch(() => []),\n\t]);\n\treturn {\n\t\tresources: resources.filter((resource) => !isMcpAppResource(resource)),\n\t\tresourceTemplates: resourceTemplates.filter((template) => !isMcpAppResource(template)),\n\t};\n}\n\n/** One configured server. Reconnects lazily when a call finds the connection gone. */\nexport class McpServerConnection implements McpToolCaller, McpResourceServer {\n\treadonly entry: McpServerEntry;\n\tstate: ServerState = \"connecting\";\n\terror: string | undefined;\n\ttools: McpTool[] = [];\n\t/**\n\t * Whether the server offers resources. The lists below are what it listed at the last connect or\n\t * change, without MCP App resources.\n\t */\n\thasResources = false;\n\tresources: Resource[] = [];\n\tresourceTemplates: ResourceTemplate[] = [];\n\t/** Server instructions from `initialize`, describing its tools as a group. */\n\tinstructions: string | undefined;\n\t/** Last OAuth challenge from the server; sign-in uses its resource metadata URL and scope. */\n\tchallenge: OAuthChallenge | undefined;\n\tprivate client: McpClient | undefined;\n\tprivate opening: Promise<McpClient> | undefined;\n\tprivate closed = false;\n\t/** Stderr of the last stdio server that failed to connect. */\n\tprivate stderrTail: string | undefined;\n\tprivate readonly cwd: string;\n\tprivate readonly createTransport: McpTransportFactory;\n\tprivate readonly authProvider: McpAuthProvider | undefined;\n\tprivate readonly onTools: (connection: McpServerConnection) => void;\n\tprivate readonly onChange: ((connection: McpServerConnection) => void) | undefined;\n\tprivate readonly log: McpServerLog | undefined;\n\n\tconstructor(options: {\n\t\tentry: McpServerEntry;\n\t\tcwd: string;\n\t\tcreateTransport: McpTransportFactory;\n\t\tcredentials: McpOAuthCredentialStore;\n\t\t/** The current token of a pi provider, for servers with `auth.provider`. */\n\t\tproviderToken?: (provider: string) => Promise<string | undefined>;\n\t\tonTools: (connection: McpServerConnection) => void;\n\t\t/** Called when `state`, `error`, or `tools` change. */\n\t\tonChange?: (connection: McpServerConnection) => void;\n\t\t/** Receives the server's log messages (`notifications/message`). */\n\t\tlog?: McpServerLog;\n\t}) {\n\t\tthis.entry = options.entry;\n\t\tthis.cwd = options.cwd;\n\t\tthis.createTransport = options.createTransport;\n\t\tthis.onTools = options.onTools;\n\t\tthis.onChange = options.onChange;\n\t\tthis.log = options.log;\n\t\tconst url = this.oauthUrl;\n\t\tconst provider = \"url\" in this.entry.config ? this.entry.config.auth?.provider : undefined;\n\t\tthis.authProvider = url\n\t\t\t? createMcpAuthProvider({\n\t\t\t\t\tserverUrl: url,\n\t\t\t\t\tstore: options.credentials.forServer(this.entry.name, url),\n\t\t\t\t\tsettings: () => this.oauthSettings(),\n\t\t\t\t\tonChallenge: (challenge) => {\n\t\t\t\t\t\tthis.challenge = challenge;\n\t\t\t\t\t},\n\t\t\t\t})\n\t\t\t: provider\n\t\t\t\t? // Read on every request, so the provider's refreshes apply; MCP stores no copy.\n\t\t\t\t\t{ token: async () => options.providerToken?.(provider), settled: async () => {} }\n\t\t\t\t: undefined;\n\t}\n\n\tget name(): string {\n\t\treturn this.entry.name;\n\t}\n\n\tget timeoutMs(): number {\n\t\treturn (this.entry.config.timeout ?? DEFAULT_TIMEOUT_SECONDS) * 1000;\n\t}\n\n\t/** Server URL when the server authenticates with OAuth. */\n\tget oauthUrl(): string | undefined {\n\t\treturn usesOAuth(this.entry) && \"url\" in this.entry.config ? this.entry.config.url : undefined;\n\t}\n\n\toauthSettings(): McpOAuthSettings {\n\t\tconst oauth = \"url\" in this.entry.config ? this.entry.config.oauth : undefined;\n\t\tif (!oauth) return {};\n\t\treturn {\n\t\t\tclientId: oauth.clientId,\n\t\t\tclientSecret:\n\t\t\t\toauth.clientSecret === undefined\n\t\t\t\t\t? undefined\n\t\t\t\t\t: resolveConfigValueOrThrow(oauth.clientSecret, `MCP server \"${this.entry.name}\" oauth.clientSecret`),\n\t\t\tcallbackPort: oauth.callbackPort,\n\t\t\tcallbackUrl: oauth.callbackUrl,\n\t\t\tscope: oauth.scope,\n\t\t\tclientName: oauth.clientName,\n\t\t\tclientRegistration: oauth.clientRegistration,\n\t\t\tauthServerMetadataUrl: oauth.authServerMetadataUrl ? new URL(oauth.authServerMetadataUrl) : undefined,\n\t\t};\n\t}\n\n\tgetClient(): Promise<McpClient> {\n\t\tif (this.closed) return Promise.reject(new Error(`MCP server \"${this.entry.name}\" is shut down`));\n\t\tif (this.client?.connectionState === \"connected\") return Promise.resolve(this.client);\n\t\tthis.opening ??= this.open().finally(() => {\n\t\t\tthis.opening = undefined;\n\t\t});\n\t\treturn this.opening;\n\t}\n\n\tcallTool(name: string, args: Record<string, unknown>, options: McpRequestOptions): Promise<CallToolResult> {\n\t\treturn this.withClient((client) => client.callTool(name, args, options));\n\t}\n\n\treadResource(uri: string, options: McpRequestOptions): Promise<ReadResourceResult> {\n\t\treturn this.withClient((client) => client.readResource(uri, options), true);\n\t}\n\n\tresourcesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourcesResult> {\n\t\treturn this.withClient((client) => client.listResourcesPage(cursor, options), true);\n\t}\n\n\tresourceTemplatesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourceTemplatesResult> {\n\t\treturn this.withClient(\n\t\t\t(client) =>\n\t\t\t\twithoutTemplates(() => client.listResourceTemplatesPage(cursor, options), { resourceTemplates: [] }),\n\t\t\ttrue,\n\t\t);\n\t}\n\n\tallResources(options: McpRequestOptions): Promise<Resource[]> {\n\t\treturn this.withClient((client) => client.listResources(options), true);\n\t}\n\n\tallResourceTemplates(options: McpRequestOptions): Promise<ResourceTemplate[]> {\n\t\treturn this.withClient((client) => listTemplates(client, options), true);\n\t}\n\n\t/**\n\t * Run a request, reconnecting when needed. `readOnly` requests are retried once after a transient\n\t * HTTP error; tool calls are not, since they may have run.\n\t */\n\tprivate async withClient<T>(run: (client: McpClient) => Promise<T>, readOnly = false): Promise<T> {\n\t\tfor (let attempt = 1; ; attempt++) {\n\t\t\tconst client = await this.getClient();\n\t\t\ttry {\n\t\t\t\treturn await run(client);\n\t\t\t} catch (error) {\n\t\t\t\tif (readOnly && attempt === 1 && error instanceof McpHttpError && isTransientError(error)) {\n\t\t\t\t\tawait new Promise((resolve) => setTimeout(resolve, CONNECT_RETRY_DELAYS_MS[0]));\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (error instanceof McpSessionExpiredError && attempt === 1) {\n\t\t\t\t\t// The server no longer knows the session (restart, deploy), so it did not run the request.\n\t\t\t\t\t// Retry once on a new session. The old client is detached but not closed: closing would\n\t\t\t\t\t// fail its other in-flight calls, which instead get the same 404 and retry the same way.\n\t\t\t\t\tif (this.client === client) this.client = undefined;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (!this.needsSignIn(error)) throw error;\n\t\t\t\tawait this.dropClient(client);\n\t\t\t\tthis.markNeedsAuth();\n\t\t\t\tthrow new Error(signInRequiredMessage(this.entry));\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Connect again with fresh credentials, for example after signing in. */\n\tasync reconnect(): Promise<void> {\n\t\tawait this.opening?.catch(() => undefined);\n\t\tif (this.client) await this.dropClient(this.client);\n\t\tawait this.getClient();\n\t}\n\n\t/** Disconnect after the stored credentials were removed. */\n\tasync signOut(): Promise<void> {\n\t\tawait this.opening?.catch(() => undefined);\n\t\tif (this.client) await this.dropClient(this.client);\n\t\tif (!this.closed) this.markNeedsAuth();\n\t}\n\n\t/** OAuth servers that still reject the request after a refresh need the user to sign in again. */\n\tprivate needsSignIn(error: unknown): boolean {\n\t\treturn (\n\t\t\terror instanceof McpOAuthAuthorizationRequiredError ||\n\t\t\t(this.authProvider !== undefined && error instanceof McpAuthRequiredError)\n\t\t);\n\t}\n\n\tprivate markNeedsAuth(): void {\n\t\tthis.state = \"needs-auth\";\n\t\tthis.error = undefined;\n\t\tthis.changed();\n\t}\n\n\tprivate changed(): void {\n\t\tthis.onChange?.(this);\n\t}\n\n\tprivate async dropClient(client: McpClient): Promise<void> {\n\t\tif (this.client === client) this.client = undefined;\n\t\tawait client.close().catch(() => undefined);\n\t}\n\n\tprivate async open(): Promise<McpClient> {\n\t\tthis.state = \"connecting\";\n\t\tthis.changed();\n\t\tconst retries = \"url\" in this.entry.config ? CONNECT_RETRY_DELAYS_MS : [];\n\t\tfor (let attempt = 0; ; attempt++) {\n\t\t\tthis.stderrTail = undefined;\n\t\t\ttry {\n\t\t\t\treturn await this.connectOnce();\n\t\t\t} catch (error) {\n\t\t\t\tconst delay = retries[attempt];\n\t\t\t\tif (this.closed || delay === undefined || !isTransientError(error)) {\n\t\t\t\t\tthrow this.connectFailed(error);\n\t\t\t\t}\n\t\t\t\tawait new Promise((resolve) => setTimeout(resolve, delay));\n\t\t\t\tif (this.closed) throw this.connectFailed(error);\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate async connectOnce(): Promise<McpClient> {\n\t\tconst client = new McpClient({\n\t\t\tname: \"pi\",\n\t\t\tversion: VERSION,\n\t\t\trequestTimeoutMs: this.timeoutMs,\n\t\t\troots: [{ uri: pathToFileURL(this.cwd).href, name: basename(this.cwd) }],\n\t\t});\n\t\tconst log = this.log;\n\t\tif (log) client.onNotification(\"notifications/message\", (params) => log.write(this.entry.name, params));\n\t\tlet transport: McpTransport | undefined;\n\t\ttry {\n\t\t\ttransport = this.createTransport(this.entry, this.cwd, this.authProvider);\n\t\t\tawait client.connect(transport);\n\t\t\tclient.onNotification(\"notifications/tools/list_changed\", () => {\n\t\t\t\tvoid this.refreshTools(client);\n\t\t\t});\n\t\t\tclient.onNotification(\"notifications/resources/list_changed\", () => {\n\t\t\t\tvoid this.refreshResources(client);\n\t\t\t});\n\t\t\tconst stdio = transport instanceof StdioTransport ? transport : undefined;\n\t\t\tclient.onClose(() => this.handleClientClose(client, stdio));\n\t\t\t// Servers without the tools capability (prompts or resources only) do not answer tools/list.\n\t\t\tconst hasResources = client.serverCapabilities?.resources !== undefined;\n\t\t\tconst [tools, resources] = await Promise.all([\n\t\t\t\tclient.serverCapabilities?.tools ? client.listTools() : [],\n\t\t\t\thasResources ? fetchResources(client) : { resources: [], resourceTemplates: [] },\n\t\t\t]);\n\t\t\tif (this.closed) throw new Error(\"shut down while connecting\");\n\t\t\tif (client.connectionState !== \"connected\") throw new Error(\"connection closed during setup\");\n\t\t\tthis.client = client;\n\t\t\tthis.tools = tools;\n\t\t\tthis.hasResources = hasResources;\n\t\t\tthis.resources = resources.resources;\n\t\t\tthis.resourceTemplates = resources.resourceTemplates;\n\t\t\tthis.instructions = client.instructions?.trim() || undefined;\n\t\t\tthis.state = \"connected\";\n\t\t\tthis.error = undefined;\n\t\t\tthis.onTools(this);\n\t\t\tthis.changed();\n\t\t\treturn client;\n\t\t} catch (error) {\n\t\t\tawait client.close().catch(() => undefined);\n\t\t\tif (transport instanceof StdioTransport) {\n\t\t\t\tthis.stderrTail = transport.stderr.trim().slice(-STDERR_TAIL_CHARS) || undefined;\n\t\t\t}\n\t\t\tthrow error;\n\t\t}\n\t}\n\n\tprivate connectFailed(error: unknown): Error {\n\t\tif (this.needsSignIn(error) && !this.closed) {\n\t\t\tthis.markNeedsAuth();\n\t\t\treturn new Error(signInRequiredMessage(this.entry));\n\t\t}\n\t\tthis.state = this.closed ? \"closed\" : \"failed\";\n\t\tthis.error = this.stderrTail ? `${errorMessage(error)}\\n${this.stderrTail}` : errorMessage(error);\n\t\tthis.changed();\n\t\treturn new Error(`MCP server \"${this.entry.name}\" failed to connect: ${this.error}`);\n\t}\n\n\t/** The transport dropped. The next call reconnects; until then the status shows why. */\n\tprivate handleClientClose(client: McpClient, stdio: StdioTransport | undefined): void {\n\t\tif (this.client !== client || this.closed) return;\n\t\tthis.client = undefined;\n\t\tthis.state = \"disconnected\";\n\t\tconst stderr = stdio?.stderr.trim().slice(-STDERR_TAIL_CHARS);\n\t\tthis.error = stderr ? `Connection closed\\n${stderr}` : \"Connection closed\";\n\t\tthis.changed();\n\t}\n\n\tprivate async refreshTools(client: McpClient): Promise<void> {\n\t\ttry {\n\t\t\tconst tools = await client.listTools();\n\t\t\tif (this.client !== client || this.closed) return;\n\t\t\tthis.tools = tools;\n\t\t\tthis.onTools(this);\n\t\t} catch (error) {\n\t\t\tthis.error = `Failed to refresh tools: ${errorMessage(error)}`;\n\t\t}\n\t\tthis.changed();\n\t}\n\n\tprivate async refreshResources(client: McpClient): Promise<void> {\n\t\tconst { resources, resourceTemplates } = await fetchResources(client);\n\t\tif (this.client !== client || this.closed) return;\n\t\tthis.resources = resources;\n\t\tthis.resourceTemplates = resourceTemplates;\n\t\tthis.onTools(this);\n\t\tthis.changed();\n\t}\n\n\tasync close(): Promise<void> {\n\t\tthis.closed = true;\n\t\tthis.state = \"closed\";\n\t\tthis.changed();\n\t\tconst client = this.client;\n\t\tthis.client = undefined;\n\t\tawait client?.close().catch(() => undefined);\n\t\t// A refresh the server already answered may have rotated the refresh token; exiting before the\n\t\t// new tokens are saved would lose the grant.\n\t\tawait this.authProvider?.settled();\n\t}\n}\n"]}
1
+ {"version":3,"file":"runtime.js","sourceRoot":"","sources":["../../../src/extensions/mcp/runtime.ts"],"names":[],"mappings":"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","sourcesContent":["/**\n * The part of the MCP integration that talks to servers: connections, transports, and OAuth\n * sign-in. It pulls in the MCP client, so index.ts loads it through runtime.lazy.ts only when a\n * server is configured.\n */\n\nimport { homedir } from \"node:os\";\nimport { basename, join, resolve } from \"node:path\";\nimport { setTimeout as sleep } from \"node:timers/promises\";\nimport { pathToFileURL } from \"node:url\";\nimport {\n\ttype AuthProvider,\n\ttype CallToolResult,\n\tJSON_RPC_ERROR_CODES,\n\ttype ListResourcesResult,\n\ttype ListResourceTemplatesResult,\n\tMcpAuthRequiredError,\n\tMcpClient,\n\tMcpError,\n\tMcpHttpError,\n\ttype McpRequestOptions,\n\tMcpSessionExpiredError,\n\ttype Tool as McpTool,\n\ttype McpTransport,\n\ttype ReadResourceResult,\n\ttype Resource,\n\ttype ResourceTemplate,\n\tStdioTransport,\n\tStreamableHttpTransport,\n} from \"@earendil-works/pi-mcp\";\nimport { McpOAuthAuthorizationRequiredError, type OAuthChallenge } from \"@earendil-works/pi-mcp/oauth\";\nimport { VERSION } from \"../../config.ts\";\nimport { resolveConfigValueOrThrow, resolveHeadersOrThrow } from \"../../core/resolve-config-value.ts\";\nimport type { McpServerEntry } from \"./config.ts\";\nimport type { McpServerLog } from \"./log.ts\";\nimport {\n\tcreateMcpAuthProvider,\n\ttype McpAuthProvider,\n\ttype McpOAuthCredentialStore,\n\ttype McpOAuthSettings,\n} from \"./oauth.ts\";\nimport { isMcpAppResource, type McpResourceServer } from \"./resources.ts\";\nimport type { McpToolCaller } from \"./tools.ts\";\n\nexport { McpServerLog } from \"./log.ts\";\nexport { McpOAuthCredentialStore, McpSignInCancelledError, signInMcpServer } from \"./oauth.ts\";\n\nconst DEFAULT_TIMEOUT_SECONDS = 60;\nconst STDERR_TAIL_CHARS = 2_000;\n/** Delays between attempts to connect to an HTTP server that failed with a transient error. */\nconst CONNECT_RETRY_DELAYS_MS = [250, 1_000];\n\n/**\n * `disconnected`: the connection dropped (for example the stdio server exited); the next call\n * reconnects.\n */\ntype ServerState = \"connecting\" | \"connected\" | \"disconnected\" | \"needs-auth\" | \"failed\" | \"closed\";\n\nexport type McpTransportFactory = (\n\tentry: McpServerEntry,\n\tcwd: string,\n\tauthProvider: AuthProvider | undefined,\n) => McpTransport;\n\nfunction errorMessage(error: unknown): string {\n\treturn error instanceof Error ? error.message : String(error);\n}\n\n/** Network failures and overloaded or restarting servers, which are worth another attempt. */\nfunction isTransientError(error: unknown): boolean {\n\tif (error instanceof McpHttpError) {\n\t\treturn error.status === 408 || error.status === 429 || (error.status >= 500 && error.status !== 501);\n\t}\n\treturn error instanceof TypeError;\n}\n\nfunction signInRequiredMessage(entry: McpServerEntry): string {\n\tconst provider = \"url\" in entry.config ? entry.config.auth?.provider : undefined;\n\treturn `MCP server \"${entry.name}\" requires sign-in. Run ${provider ? `/login ${provider}` : \"/mcp\"} to sign in.`;\n}\n\n/** HTTP servers authenticate with OAuth unless the config supplies an `Authorization` header or `auth`. */\nfunction usesOAuth(entry: McpServerEntry): boolean {\n\tconst { config } = entry;\n\tif (!(\"url\" in config) || config.auth) return false;\n\treturn !Object.keys(config.headers ?? {}).some((header) => header.toLowerCase() === \"authorization\");\n}\n\n/** `~` and `~/…` (also `~\\…` on Windows) name the home directory, like in a shell. */\nfunction expandHome(value: string): string {\n\tif (value === \"~\") return homedir();\n\tif (value.startsWith(\"~/\") || (process.platform === \"win32\" && value.startsWith(\"~\\\\\"))) {\n\t\treturn join(homedir(), value.slice(2));\n\t}\n\treturn value;\n}\n\nexport function createDefaultTransport(\n\tentry: McpServerEntry,\n\tcwd: string,\n\tauthProvider: AuthProvider | undefined,\n): McpTransport {\n\tconst { config, name } = entry;\n\tif (\"url\" in config) {\n\t\treturn new StreamableHttpTransport({\n\t\t\turl: config.url,\n\t\t\theaders: resolveHeadersOrThrow(config.headers, `MCP server \"${name}\"`),\n\t\t\tauthProvider,\n\t\t});\n\t}\n\tconst env: Record<string, string> = {};\n\tfor (const [key, value] of Object.entries(config.env ?? {})) {\n\t\tenv[key] = resolveConfigValueOrThrow(value, `MCP server \"${name}\" env \"${key}\"`);\n\t}\n\treturn new StdioTransport({\n\t\tcommand: expandHome(config.command),\n\t\targs: config.args?.map(expandHome),\n\t\tcwd: resolve(cwd, expandHome(config.cwd ?? \".\")),\n\t\tenv,\n\t\tstderr: \"pipe\",\n\t});\n}\n\n/** Servers that do not implement `resources/templates/list` have no templates. */\nasync function withoutTemplates<T>(list: () => Promise<T>, empty: T): Promise<T> {\n\ttry {\n\t\treturn await list();\n\t} catch (error) {\n\t\tif (error instanceof McpError && error.code === JSON_RPC_ERROR_CODES.methodNotFound) return empty;\n\t\tthrow error;\n\t}\n}\n\nfunction listTemplates(client: McpClient, options: McpRequestOptions = {}): Promise<ResourceTemplate[]> {\n\treturn withoutTemplates(() => client.listResourceTemplates(options), []);\n}\n\n/**\n * Resources and templates at connect time, for the counts in `/mcp` and `pi mcp list`. A server\n * whose lists fail still connects: the resource tools list and read its resources on demand.\n */\nasync function fetchResources(\n\tclient: McpClient,\n): Promise<{ resources: Resource[]; resourceTemplates: ResourceTemplate[] }> {\n\tconst [resources, resourceTemplates] = await Promise.all([\n\t\tclient.listResources().catch(() => []),\n\t\tlistTemplates(client).catch(() => []),\n\t]);\n\treturn {\n\t\tresources: resources.filter((resource) => !isMcpAppResource(resource)),\n\t\tresourceTemplates: resourceTemplates.filter((template) => !isMcpAppResource(template)),\n\t};\n}\n\n/** One configured server. Reconnects lazily when a call finds the connection gone. */\nexport class McpServerConnection implements McpToolCaller, McpResourceServer {\n\treadonly entry: McpServerEntry;\n\tstate: ServerState = \"connecting\";\n\terror: string | undefined;\n\ttools: McpTool[] = [];\n\t/**\n\t * Whether the server offers resources. The lists below are what it listed at the last connect or\n\t * change, without MCP App resources.\n\t */\n\thasResources = false;\n\tresources: Resource[] = [];\n\tresourceTemplates: ResourceTemplate[] = [];\n\t/** Server instructions from `initialize`, describing its tools as a group. */\n\tinstructions: string | undefined;\n\t/** Last OAuth challenge from the server; sign-in uses its resource metadata URL and scope. */\n\tchallenge: OAuthChallenge | undefined;\n\tprivate client: McpClient | undefined;\n\tprivate opening: Promise<McpClient> | undefined;\n\t/** Aborted by `close()`; cancels a connect in progress, including the wait between retries. */\n\tprivate readonly shutdown = new AbortController();\n\t/** Stderr of the last stdio server that failed to connect. */\n\tprivate stderrTail: string | undefined;\n\tprivate readonly cwd: string;\n\tprivate readonly createTransport: McpTransportFactory;\n\tprivate readonly authProvider: McpAuthProvider | undefined;\n\tprivate readonly onTools: (connection: McpServerConnection) => void;\n\tprivate readonly onChange: ((connection: McpServerConnection) => void) | undefined;\n\tprivate readonly log: McpServerLog | undefined;\n\n\tconstructor(options: {\n\t\tentry: McpServerEntry;\n\t\tcwd: string;\n\t\tcreateTransport: McpTransportFactory;\n\t\tcredentials: McpOAuthCredentialStore;\n\t\t/** The current token of a pi provider, for servers with `auth.provider`. */\n\t\tproviderToken?: (provider: string) => Promise<string | undefined>;\n\t\tonTools: (connection: McpServerConnection) => void;\n\t\t/** Called when `state`, `error`, or `tools` change. */\n\t\tonChange?: (connection: McpServerConnection) => void;\n\t\t/** Receives the server's log messages (`notifications/message`). */\n\t\tlog?: McpServerLog;\n\t}) {\n\t\tthis.entry = options.entry;\n\t\tthis.cwd = options.cwd;\n\t\tthis.createTransport = options.createTransport;\n\t\tthis.onTools = options.onTools;\n\t\tthis.onChange = options.onChange;\n\t\tthis.log = options.log;\n\t\tconst url = this.oauthUrl;\n\t\tconst provider = \"url\" in this.entry.config ? this.entry.config.auth?.provider : undefined;\n\t\tthis.authProvider = url\n\t\t\t? createMcpAuthProvider({\n\t\t\t\t\tserverUrl: url,\n\t\t\t\t\tstore: options.credentials.forServer(this.entry.name, url),\n\t\t\t\t\tsettings: () => this.oauthSettings(),\n\t\t\t\t\tonChallenge: (challenge) => {\n\t\t\t\t\t\tthis.challenge = challenge;\n\t\t\t\t\t},\n\t\t\t\t})\n\t\t\t: provider\n\t\t\t\t? // Read on every request, so the provider's refreshes apply; MCP stores no copy.\n\t\t\t\t\t{ token: async () => options.providerToken?.(provider), settled: async () => {} }\n\t\t\t\t: undefined;\n\t}\n\n\tget name(): string {\n\t\treturn this.entry.name;\n\t}\n\n\tprivate get closed(): boolean {\n\t\treturn this.shutdown.signal.aborted;\n\t}\n\n\tget timeoutMs(): number {\n\t\treturn (this.entry.config.timeout ?? DEFAULT_TIMEOUT_SECONDS) * 1000;\n\t}\n\n\t/** Server URL when the server authenticates with OAuth. */\n\tget oauthUrl(): string | undefined {\n\t\treturn usesOAuth(this.entry) && \"url\" in this.entry.config ? this.entry.config.url : undefined;\n\t}\n\n\toauthSettings(): McpOAuthSettings {\n\t\tconst oauth = \"url\" in this.entry.config ? this.entry.config.oauth : undefined;\n\t\tif (!oauth) return {};\n\t\treturn {\n\t\t\tclientId: oauth.clientId,\n\t\t\tclientSecret:\n\t\t\t\toauth.clientSecret === undefined\n\t\t\t\t\t? undefined\n\t\t\t\t\t: resolveConfigValueOrThrow(oauth.clientSecret, `MCP server \"${this.entry.name}\" oauth.clientSecret`),\n\t\t\tcallbackPort: oauth.callbackPort,\n\t\t\tcallbackUrl: oauth.callbackUrl,\n\t\t\tscope: oauth.scope,\n\t\t\tclientName: oauth.clientName,\n\t\t\tclientRegistration: oauth.clientRegistration,\n\t\t\tauthServerMetadataUrl: oauth.authServerMetadataUrl ? new URL(oauth.authServerMetadataUrl) : undefined,\n\t\t};\n\t}\n\n\tgetClient(): Promise<McpClient> {\n\t\tif (this.closed) return Promise.reject(new Error(`MCP server \"${this.entry.name}\" is shut down`));\n\t\tif (this.client?.connectionState === \"connected\") return Promise.resolve(this.client);\n\t\tthis.opening ??= this.open().finally(() => {\n\t\t\tthis.opening = undefined;\n\t\t});\n\t\treturn this.opening;\n\t}\n\n\tcallTool(name: string, args: Record<string, unknown>, options: McpRequestOptions): Promise<CallToolResult> {\n\t\treturn this.withClient((client) => client.callTool(name, args, options));\n\t}\n\n\treadResource(uri: string, options: McpRequestOptions): Promise<ReadResourceResult> {\n\t\treturn this.withClient((client) => client.readResource(uri, options), true);\n\t}\n\n\tresourcesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourcesResult> {\n\t\treturn this.withClient((client) => client.listResourcesPage(cursor, options), true);\n\t}\n\n\tresourceTemplatesPage(cursor: string | undefined, options: McpRequestOptions): Promise<ListResourceTemplatesResult> {\n\t\treturn this.withClient(\n\t\t\t(client) =>\n\t\t\t\twithoutTemplates(() => client.listResourceTemplatesPage(cursor, options), { resourceTemplates: [] }),\n\t\t\ttrue,\n\t\t);\n\t}\n\n\tallResources(options: McpRequestOptions): Promise<Resource[]> {\n\t\treturn this.withClient((client) => client.listResources(options), true);\n\t}\n\n\tallResourceTemplates(options: McpRequestOptions): Promise<ResourceTemplate[]> {\n\t\treturn this.withClient((client) => listTemplates(client, options), true);\n\t}\n\n\t/**\n\t * Run a request, reconnecting when needed. `readOnly` requests are retried once after a transient\n\t * HTTP error; tool calls are not, since they may have run.\n\t */\n\tprivate async withClient<T>(run: (client: McpClient) => Promise<T>, readOnly = false): Promise<T> {\n\t\tfor (let attempt = 1; ; attempt++) {\n\t\t\tconst client = await this.getClient();\n\t\t\ttry {\n\t\t\t\treturn await run(client);\n\t\t\t} catch (error) {\n\t\t\t\tif (readOnly && attempt === 1 && error instanceof McpHttpError && isTransientError(error)) {\n\t\t\t\t\tawait new Promise((resolve) => setTimeout(resolve, CONNECT_RETRY_DELAYS_MS[0]));\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (error instanceof McpSessionExpiredError && attempt === 1) {\n\t\t\t\t\t// The server no longer knows the session (restart, deploy), so it did not run the request.\n\t\t\t\t\t// Retry once on a new session. The old client is detached but not closed: closing would\n\t\t\t\t\t// fail its other in-flight calls, which instead get the same 404 and retry the same way.\n\t\t\t\t\tif (this.client === client) this.client = undefined;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (!this.needsSignIn(error)) throw error;\n\t\t\t\tawait this.dropClient(client);\n\t\t\t\tthis.markNeedsAuth();\n\t\t\t\tthrow new Error(signInRequiredMessage(this.entry));\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Connect again with fresh credentials, for example after signing in. */\n\tasync reconnect(): Promise<void> {\n\t\tawait this.opening?.catch(() => undefined);\n\t\tif (this.client) await this.dropClient(this.client);\n\t\tawait this.getClient();\n\t}\n\n\t/** Disconnect after the stored credentials were removed. */\n\tasync signOut(): Promise<void> {\n\t\tawait this.opening?.catch(() => undefined);\n\t\tif (this.client) await this.dropClient(this.client);\n\t\tif (!this.closed) this.markNeedsAuth();\n\t}\n\n\t/** OAuth servers that still reject the request after a refresh need the user to sign in again. */\n\tprivate needsSignIn(error: unknown): boolean {\n\t\treturn (\n\t\t\terror instanceof McpOAuthAuthorizationRequiredError ||\n\t\t\t(this.authProvider !== undefined && error instanceof McpAuthRequiredError)\n\t\t);\n\t}\n\n\tprivate markNeedsAuth(): void {\n\t\tthis.state = \"needs-auth\";\n\t\tthis.error = undefined;\n\t\tthis.changed();\n\t}\n\n\tprivate changed(): void {\n\t\tthis.onChange?.(this);\n\t}\n\n\tprivate async dropClient(client: McpClient): Promise<void> {\n\t\tif (this.client === client) this.client = undefined;\n\t\tawait client.close().catch(() => undefined);\n\t}\n\n\tprivate async open(): Promise<McpClient> {\n\t\tthis.state = \"connecting\";\n\t\tthis.changed();\n\t\tconst retries = \"url\" in this.entry.config ? CONNECT_RETRY_DELAYS_MS : [];\n\t\tfor (let attempt = 0; ; attempt++) {\n\t\t\tthis.stderrTail = undefined;\n\t\t\ttry {\n\t\t\t\treturn await this.connectOnce();\n\t\t\t} catch (error) {\n\t\t\t\tconst delay = retries[attempt];\n\t\t\t\tif (this.closed || delay === undefined || !isTransientError(error)) {\n\t\t\t\t\tthrow this.connectFailed(error);\n\t\t\t\t}\n\t\t\t\tawait sleep(delay, undefined, { signal: this.shutdown.signal }).catch(() => undefined);\n\t\t\t\tif (this.closed) throw this.connectFailed(error);\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate async connectOnce(): Promise<McpClient> {\n\t\tconst client = new McpClient({\n\t\t\tname: \"pi\",\n\t\t\tversion: VERSION,\n\t\t\trequestTimeoutMs: this.timeoutMs,\n\t\t\troots: [{ uri: pathToFileURL(this.cwd).href, name: basename(this.cwd) }],\n\t\t});\n\t\tconst log = this.log;\n\t\tif (log) client.onNotification(\"notifications/message\", (params) => log.write(this.entry.name, params));\n\t\t// Closing the client fails its pending initialize or discovery requests and closes the transport.\n\t\t// Memoized: a second `client.close()` returns before the first finished closing the transport.\n\t\tlet closing: Promise<void> | undefined;\n\t\tconst closeClient = () => {\n\t\t\tclosing ??= client.close().catch(() => undefined);\n\t\t\treturn closing;\n\t\t};\n\t\tthis.shutdown.signal.addEventListener(\"abort\", closeClient, { once: true });\n\t\tlet transport: McpTransport | undefined;\n\t\ttry {\n\t\t\ttransport = this.createTransport(this.entry, this.cwd, this.authProvider);\n\t\t\tawait client.connect(transport);\n\t\t\tclient.onNotification(\"notifications/tools/list_changed\", () => {\n\t\t\t\tvoid this.refreshTools(client);\n\t\t\t});\n\t\t\tclient.onNotification(\"notifications/resources/list_changed\", () => {\n\t\t\t\tvoid this.refreshResources(client);\n\t\t\t});\n\t\t\tconst stdio = transport instanceof StdioTransport ? transport : undefined;\n\t\t\tclient.onClose(() => this.handleClientClose(client, stdio));\n\t\t\t// Servers without the tools capability (prompts or resources only) do not answer tools/list.\n\t\t\tconst hasResources = client.serverCapabilities?.resources !== undefined;\n\t\t\tconst [tools, resources] = await Promise.all([\n\t\t\t\tclient.serverCapabilities?.tools ? client.listTools() : [],\n\t\t\t\thasResources ? fetchResources(client) : { resources: [], resourceTemplates: [] },\n\t\t\t]);\n\t\t\tif (this.closed) throw new Error(\"shut down while connecting\");\n\t\t\tif (client.connectionState !== \"connected\") throw new Error(\"connection closed during setup\");\n\t\t\tthis.client = client;\n\t\t\tthis.tools = tools;\n\t\t\tthis.hasResources = hasResources;\n\t\t\tthis.resources = resources.resources;\n\t\t\tthis.resourceTemplates = resources.resourceTemplates;\n\t\t\tthis.instructions = client.instructions?.trim() || undefined;\n\t\t\tthis.state = \"connected\";\n\t\t\tthis.error = undefined;\n\t\t\tthis.onTools(this);\n\t\t\tthis.changed();\n\t\t\treturn client;\n\t\t} catch (error) {\n\t\t\tawait closeClient();\n\t\t\tif (transport instanceof StdioTransport) {\n\t\t\t\tthis.stderrTail = transport.stderr.trim().slice(-STDERR_TAIL_CHARS) || undefined;\n\t\t\t}\n\t\t\tthrow error;\n\t\t} finally {\n\t\t\tthis.shutdown.signal.removeEventListener(\"abort\", closeClient);\n\t\t}\n\t}\n\n\tprivate connectFailed(error: unknown): Error {\n\t\tif (this.needsSignIn(error) && !this.closed) {\n\t\t\tthis.markNeedsAuth();\n\t\t\treturn new Error(signInRequiredMessage(this.entry));\n\t\t}\n\t\tthis.state = this.closed ? \"closed\" : \"failed\";\n\t\tthis.error = this.stderrTail ? `${errorMessage(error)}\\n${this.stderrTail}` : errorMessage(error);\n\t\tthis.changed();\n\t\treturn new Error(`MCP server \"${this.entry.name}\" failed to connect: ${this.error}`);\n\t}\n\n\t/** The transport dropped. The next call reconnects; until then the status shows why. */\n\tprivate handleClientClose(client: McpClient, stdio: StdioTransport | undefined): void {\n\t\tif (this.client !== client || this.closed) return;\n\t\tthis.client = undefined;\n\t\tthis.state = \"disconnected\";\n\t\tconst stderr = stdio?.stderr.trim().slice(-STDERR_TAIL_CHARS);\n\t\tthis.error = stderr ? `Connection closed\\n${stderr}` : \"Connection closed\";\n\t\tthis.changed();\n\t}\n\n\tprivate async refreshTools(client: McpClient): Promise<void> {\n\t\ttry {\n\t\t\tconst tools = await client.listTools();\n\t\t\tif (this.client !== client || this.closed) return;\n\t\t\tthis.tools = tools;\n\t\t\tthis.onTools(this);\n\t\t} catch (error) {\n\t\t\tthis.error = `Failed to refresh tools: ${errorMessage(error)}`;\n\t\t}\n\t\tthis.changed();\n\t}\n\n\tprivate async refreshResources(client: McpClient): Promise<void> {\n\t\tconst { resources, resourceTemplates } = await fetchResources(client);\n\t\tif (this.client !== client || this.closed) return;\n\t\tthis.resources = resources;\n\t\tthis.resourceTemplates = resourceTemplates;\n\t\tthis.onTools(this);\n\t\tthis.changed();\n\t}\n\n\t/** Resolves once no transport of this server is open, including one that was still connecting. */\n\tasync close(): Promise<void> {\n\t\tthis.shutdown.abort();\n\t\tthis.state = \"closed\";\n\t\tthis.changed();\n\t\tconst client = this.client;\n\t\tthis.client = undefined;\n\t\tawait Promise.all([client?.close().catch(() => undefined), this.opening?.catch(() => undefined)]);\n\t\t// A refresh the server already answered may have rotated the refresh token; exiting before the\n\t\t// new tokens are saved would lose the grant.\n\t\tawait this.authProvider?.settled();\n\t}\n}\n"]}
@@ -14,6 +14,7 @@ import type { ImageContent, TextContent } from "@earendil-works/pi-ai";
14
14
  import { type CallToolResult, type ContentBlock, type McpRequestOptions, type Tool as McpTool } from "@earendil-works/pi-mcp";
15
15
  import type { TSchema } from "typebox";
16
16
  import type { ToolDefinition, ToolExposure, ToolNamespace, ToolRenderers } from "../../core/extensions/types.ts";
17
+ import { READ_MCP_RESOURCE_TOOL } from "../../core/mcp-servers.ts";
17
18
  import type { McpExposure } from "./config.ts";
18
19
  /**
19
20
  * Tool exposure of an MCP exposure. `codemode` and `deferred` both leave tools out of the codemode
@@ -23,7 +24,7 @@ export declare function toToolExposure(exposure: McpExposure): ToolExposure;
23
24
  /** Model-facing text of an MCP result beyond this is cut in the middle. */
24
25
  export declare const MCP_OUTPUT_MAX_BYTES: number;
25
26
  /** Tool that reads the resources named by resource links. */
26
- export declare const READ_MCP_RESOURCE_TOOL = "read_mcp_resource";
27
+ export { READ_MCP_RESOURCE_TOOL };
27
28
  export interface McpToolDetails {
28
29
  server: string;
29
30
  tool: string;
@@ -1 +1 @@
1
- {"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../../../src/extensions/mcp/tools.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"tools.d.ts","sourceRoot":"","sources":["../../../src/extensions/mcp/tools.ts"],"names":[],"mappings":"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"}
@@ -9,16 +9,15 @@
9
9
  * the tool's `structuredContent`, and every MCP tool declares a `CallToolResult` output schema. MCP
10
10
  * errors (`isError`) are error results for the model, but scripts still resolve to the result.
11
11
  */
12
- import { createHash, randomBytes } from "node:crypto";
13
- import { writeFile } from "node:fs/promises";
14
- import { tmpdir } from "node:os";
15
- import { join } from "node:path";
12
+ import { createHash } from "node:crypto";
16
13
  import { toLlmContent, } from "@earendil-works/pi-mcp";
17
14
  import { Container, Spacer, Text } from "@earendil-works/pi-tui";
15
+ import { READ_MCP_RESOURCE_TOOL } from "../../core/mcp-servers.js";
18
16
  import { formatToolCallWithArgs, getTextOutput, replaceTabs } from "../../core/tools/render-utils.js";
19
17
  import { formatSize, truncateMiddle } from "../../core/tools/truncate.js";
20
18
  import { keyHint } from "../../modes/interactive/components/keybinding-hints.js";
21
19
  import { VisualLinePreview } from "../../modes/interactive/components/visual-truncate.js";
20
+ import { writeOutputFile } from "../../utils/output-files.js";
22
21
  /**
23
22
  * Tool exposure of an MCP exposure. `codemode` and `deferred` both leave tools out of the codemode
24
23
  * description; they differ only in which tool the MCP extension activates to reach them.
@@ -33,12 +32,9 @@ export const MCP_OUTPUT_MAX_BYTES = 20 * 1024;
33
32
  /** Visual (wrapped) result lines shown before the output is expanded. */
34
33
  const OUTPUT_PREVIEW_LINES = 5;
35
34
  /** Tool that reads the resources named by resource links. */
36
- export const READ_MCP_RESOURCE_TOOL = "read_mcp_resource";
37
- export async function saveToTempFile(data, extension) {
38
- const path = join(tmpdir(), `pi-mcp-${randomBytes(8).toString("hex")}${extension}`);
39
- // Results can carry private data, so only the user may read the file.
40
- await writeFile(path, data, { mode: 0o600 });
41
- return path;
35
+ export { READ_MCP_RESOURCE_TOOL };
36
+ export function saveToTempFile(data, extension) {
37
+ return writeOutputFile("pi-mcp", extension, data);
42
38
  }
43
39
  /**
44
40
  * `mcp__<server>__<tool>`, sanitized and shortened with a hash suffix when too long. Like Codex,