LibreChat/packages/data-provider/src/mcp.ts
Danny Avila 7f6b32ff04
🖼️ refactor: Enhance Env Extraction & Agent Image Handling (#6131)
* refactor: use new image output format for agents using DALL-E tools

* refactor: Enhance image fetching with proxy support and adjust logging placement in DALL-E 3 integration

* refactor: Enhance StableDiffusionAPI to support agent-specific return values and display message for generated images

* refactor: Add unit test execution for librechat-mcp in backend review workflow

* refactor: Update environment variable extraction logic, export from serpate module to avoid circular refs, and remove deprecated tests

* refactor: Add unit tests for environment variable extraction and enhance StdioOptionsSchema to process env variables
2025-03-01 07:51:12 -05:00

86 lines
2.2 KiB
TypeScript

import { z } from 'zod';
import { extractEnvVariable } from './utils';
const BaseOptionsSchema = z.object({
iconPath: z.string().optional(),
});
export const StdioOptionsSchema = BaseOptionsSchema.extend({
type: z.literal('stdio').optional(),
/**
* The executable to run to start the server.
*/
command: z.string(),
/**
* Command line arguments to pass to the executable.
*/
args: z.array(z.string()),
/**
* The environment to use when spawning the process.
*
* If not specified, the result of getDefaultEnvironment() will be used.
* Environment variables can be referenced using ${VAR_NAME} syntax.
*/
env: z
.record(z.string(), z.string())
.optional()
.transform((env) => {
if (!env) {
return env;
}
const processedEnv: Record<string, string> = {};
for (const [key, value] of Object.entries(env)) {
processedEnv[key] = extractEnvVariable(value);
}
return processedEnv;
}),
/**
* How to handle stderr of the child process. This matches the semantics of Node's `child_process.spawn`.
*
* @type {import('node:child_process').IOType | import('node:stream').Stream | number}
*
* The default is "inherit", meaning messages to stderr will be printed to the parent process's stderr.
*/
stderr: z.any().optional(),
});
export const WebSocketOptionsSchema = BaseOptionsSchema.extend({
type: z.literal('websocket').optional(),
url: z
.string()
.url()
.refine(
(val) => {
const protocol = new URL(val).protocol;
return protocol === 'ws:' || protocol === 'wss:';
},
{
message: 'WebSocket URL must start with ws:// or wss://',
},
),
});
export const SSEOptionsSchema = BaseOptionsSchema.extend({
type: z.literal('sse').optional(),
url: z
.string()
.url()
.refine(
(val) => {
const protocol = new URL(val).protocol;
return protocol !== 'ws:' && protocol !== 'wss:';
},
{
message: 'SSE URL must not start with ws:// or wss://',
},
),
});
export const MCPOptionsSchema = z.union([
StdioOptionsSchema,
WebSocketOptionsSchema,
SSEOptionsSchema,
]);
export const MCPServersSchema = z.record(z.string(), MCPOptionsSchema);