mirror of
https://github.com/danny-avila/LibreChat.git
synced 2025-12-23 20:00:15 +01:00
🧩 refactor: Decouple MCP Config from Startup Config (#10689)
* Decouple mcp config from start up config * Chore: Work on AI Review and Copilot Comments - setRawConfig is not needed since the private raw config is not needed any more - !!serversLoading bug fixed - added unit tests for route /api/mcp/servers - copilot comments addressed * chore: remove comments * chore: rename data-provider dir for MCP * chore: reorganize mcp specific query hooks * fix: consolidate imports for MCP server manager * chore: add dev-staging branch to frontend review workflow triggers * feat: add GitHub Actions workflow for building and pushing Docker images to GitHub Container Registry and Docker Hub * fix: update label for tag input in BookmarkForm tests to improve clarity --------- Co-authored-by: Atef Bellaaj <slalom.bellaaj@external.daimlertruck.com> Co-authored-by: Danny Avila <danny@librechat.ai>
This commit is contained in:
parent
98b188f26c
commit
ef1b7f0157
36 changed files with 548 additions and 301 deletions
|
|
@ -228,6 +228,7 @@ export const agents = ({ path = '', options }: { path?: string; options?: object
|
|||
|
||||
export const mcp = {
|
||||
tools: `${BASE_URL}/api/mcp/tools`,
|
||||
servers: `${BASE_URL}/api/mcp/servers`,
|
||||
};
|
||||
|
||||
export const revertAgentVersion = (agent_id: string) => `${agents({ path: `${agent_id}/revert` })}`;
|
||||
|
|
|
|||
|
|
@ -6,6 +6,7 @@ import * as ag from './types/agents';
|
|||
import * as m from './types/mutations';
|
||||
import * as q from './types/queries';
|
||||
import * as f from './types/files';
|
||||
import * as mcp from './types/mcpServers';
|
||||
import * as config from './config';
|
||||
import request from './request';
|
||||
import * as s from './schemas';
|
||||
|
|
@ -538,6 +539,18 @@ export const deleteAgentAction = async ({
|
|||
}),
|
||||
);
|
||||
|
||||
/**
|
||||
* MCP Servers
|
||||
*/
|
||||
|
||||
/**
|
||||
*
|
||||
* Ensure and List loaded mcp server configs from the cache Enriched with effective permissions.
|
||||
*/
|
||||
export const getMCPServers = async (): Promise<mcp.MCPServersListResponse> => {
|
||||
return request.get(endpoints.mcp.servers);
|
||||
};
|
||||
|
||||
/**
|
||||
* Imports a conversations file.
|
||||
*
|
||||
|
|
|
|||
|
|
@ -57,6 +57,8 @@ export enum QueryKeys {
|
|||
resourcePermissions = 'resourcePermissions',
|
||||
effectivePermissions = 'effectivePermissions',
|
||||
graphToken = 'graphToken',
|
||||
/* MCP Servers */
|
||||
mcpServers = 'mcpServers',
|
||||
}
|
||||
|
||||
// Dynamic query keys that require parameters
|
||||
|
|
|
|||
|
|
@ -180,3 +180,32 @@ export const MCPOptionsSchema = z.union([
|
|||
export const MCPServersSchema = z.record(z.string(), MCPOptionsSchema);
|
||||
|
||||
export type MCPOptions = z.infer<typeof MCPOptionsSchema>;
|
||||
|
||||
/**
|
||||
* Helper to omit server-managed fields that should not come from UI
|
||||
*/
|
||||
const omitServerManagedFields = <T extends z.ZodObject<z.ZodRawShape>>(schema: T) =>
|
||||
schema.omit({
|
||||
startup: true,
|
||||
timeout: true,
|
||||
initTimeout: true,
|
||||
chatMenu: true,
|
||||
serverInstructions: true,
|
||||
requiresOAuth: true,
|
||||
customUserVars: true,
|
||||
oauth_headers: true,
|
||||
});
|
||||
|
||||
/**
|
||||
* MCP Server configuration that comes from UI input only
|
||||
* Omits server-managed fields like startup, timeout, customUserVars, etc.
|
||||
* Allows: title, description, url, iconPath, oauth (user credentials)
|
||||
*/
|
||||
export const MCPServerUserInputSchema = z.union([
|
||||
omitServerManagedFields(StdioOptionsSchema),
|
||||
omitServerManagedFields(WebSocketOptionsSchema),
|
||||
omitServerManagedFields(SSEOptionsSchema),
|
||||
omitServerManagedFields(StreamableHTTPOptionsSchema),
|
||||
]);
|
||||
|
||||
export type MCPServerUserInput = z.infer<typeof MCPServerUserInputSchema>;
|
||||
|
|
|
|||
|
|
@ -1,4 +1,5 @@
|
|||
import type { MCPOptions } from '../mcp';
|
||||
import { PermissionBits } from '../accessPermissions';
|
||||
import type { MCPOptions, MCPServerUserInput } from '../mcp';
|
||||
|
||||
/**
|
||||
* Base MCP Server interface
|
||||
|
|
@ -19,3 +20,33 @@ export interface IMCPServerDB {
|
|||
* Similar to Agent type - includes populated author fields
|
||||
*/
|
||||
export type MCPServerDB = IMCPServerDB;
|
||||
|
||||
/**
|
||||
* Parameters for creating a new user-managed MCP server
|
||||
* Note: Only UI-editable fields are allowed (excludes server-managed fields)
|
||||
*/
|
||||
export type MCPServerCreateParams = {
|
||||
config: MCPServerUserInput; // UI fields only (title, description, url, oauth, iconPath)
|
||||
};
|
||||
|
||||
/**
|
||||
* Parameters for updating an existing user-managed MCP server
|
||||
* Note: Only UI-editable fields are allowed (excludes server-managed fields)
|
||||
*/
|
||||
export type MCPServerUpdateParams = {
|
||||
config?: MCPServerUserInput; // UI fields only (title, description, url, oauth, iconPath)
|
||||
};
|
||||
|
||||
/**
|
||||
* Response for MCP server list endpoint
|
||||
*/
|
||||
export type MCPServerDBObjectResponse = {
|
||||
_id?: string;
|
||||
mcp_id?: string;
|
||||
author?: string | null;
|
||||
createdAt?: Date;
|
||||
updatedAt?: Date;
|
||||
effectivePermissions?: PermissionBits;
|
||||
} & MCPOptions;
|
||||
|
||||
export type MCPServersListResponse = Record<string, MCPServerDBObjectResponse>;
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue