@@ -5,19 +5,26 @@ import { requireGlobalAdmin } from '../../../middleware/roleMiddleware';
55import { McpCatalogService } from '../../../services/mcpCatalogService' ;
66import { getDb } from '../../../db' ;
77
8+ // Claude Desktop configuration schema
9+ const claudeDesktopConfigSchema = z . object ( {
10+ mcpServers : z . record ( z . object ( {
11+ command : z . string ( ) . min ( 1 , 'Command is required' ) ,
12+ args : z . array ( z . string ( ) ) ,
13+ env : z . record ( z . string ( ) ) . optional ( )
14+ } ) )
15+ } ) . refine (
16+ ( config ) => Object . keys ( config . mcpServers ) . length === 1 ,
17+ { message : "Claude Desktop config must contain exactly one MCP server" }
18+ ) ;
19+
820// Request schema for creating global MCP servers
921const createGlobalServerRequestSchema = z . object ( {
1022 // Required fields
1123 name : z . string ( ) . min ( 1 , 'Name is required' ) . max ( 255 , 'Name must be 255 characters or less' ) ,
1224 description : z . string ( ) . min ( 1 , 'Description is required' ) ,
1325 language : z . string ( ) . min ( 1 , 'Language is required' ) ,
1426 runtime : z . string ( ) . min ( 1 , 'Runtime is required' ) ,
15- installation_methods : z . array ( z . object ( {
16- type : z . string ( ) . min ( 1 , 'Installation method type is required' ) ,
17- command : z . string ( ) . optional ( ) ,
18- image : z . string ( ) . optional ( ) ,
19- description : z . string ( ) . optional ( )
20- } ) ) . min ( 1 , 'At least one installation method is required' ) ,
27+ claude_desktop_config : claudeDesktopConfigSchema ,
2128 tools : z . array ( z . object ( {
2229 name : z . string ( ) . min ( 1 , 'Tool name is required' ) ,
2330 description : z . string ( ) . min ( 1 , 'Tool description is required' )
@@ -41,19 +48,48 @@ const createGlobalServerRequestSchema = z.object({
4148 author_contact : z . string ( ) . optional ( ) ,
4249 organization : z . string ( ) . optional ( ) ,
4350 license : z . string ( ) . optional ( ) ,
44- default_config : z . record ( z . any ( ) ) . optional ( ) ,
45- environment_variables : z . array ( z . object ( {
46- name : z . string ( ) . min ( 1 , 'Environment variable name is required' ) ,
47- description : z . string ( ) . min ( 1 , 'Environment variable description is required' ) ,
48- required : z . boolean ( ) . default ( false ) ,
49- default_value : z . string ( ) . optional ( )
50- } ) ) . optional ( ) ,
5151 dependencies : z . record ( z . any ( ) ) . optional ( ) ,
5252 category_id : z . string ( ) . optional ( ) ,
5353 tags : z . array ( z . string ( ) ) . optional ( ) ,
5454 featured : z . boolean ( ) . default ( false )
5555} ) ;
5656
57+ // Utility function to extract MCP configuration data from Claude Desktop config
58+ function extractMcpConfigData ( claudeConfig : z . infer < typeof claudeDesktopConfigSchema > ) {
59+ const serverKey = Object . keys ( claudeConfig . mcpServers ) [ 0 ] ;
60+ const serverConfig = claudeConfig . mcpServers [ serverKey ] ;
61+
62+ // Extract installation_methods (Claude Desktop format)
63+ const installation_methods = [ {
64+ client : "claude-desktop" ,
65+ command : serverConfig . command ,
66+ args : serverConfig . args ,
67+ env : serverConfig . env || { }
68+ } ] ;
69+
70+ // Extract environment_variables metadata
71+ const environment_variables = Object . keys ( serverConfig . env || { } ) . map ( envKey => ( {
72+ name : envKey ,
73+ description : `${ envKey } environment variable` ,
74+ required : true ,
75+ type : "password" ,
76+ validation : "" ,
77+ placeholder : serverConfig . env ! [ envKey ]
78+ } ) ) ;
79+
80+ // Extract default_config
81+ const default_config = {
82+ base_command : serverConfig . command ,
83+ base_args : serverConfig . args ,
84+ transport_type : "stdio" ,
85+ required_env : Object . keys ( serverConfig . env || { } ) ,
86+ optional_args : [ ] ,
87+ working_directory : null
88+ } ;
89+
90+ return { installation_methods, environment_variables, default_config } ;
91+ }
92+
5793// Response schema for successful creation
5894const createGlobalServerResponseSchema = z . object ( {
5995 success : z . boolean ( ) ,
@@ -162,10 +198,51 @@ export default async function createGlobalServer(server: FastifyInstance) {
162198 const db = getDb ( ) ;
163199 const mcpService = new McpCatalogService ( db , request . log ) ;
164200
165- // Force global visibility and no team ownership for global servers
201+ // Extract MCP configuration data from Claude Desktop config
202+ request . log . debug ( {
203+ operation : 'create_global_mcp_server' ,
204+ userId : request . user ?. id ,
205+ claudeConfig : requestData . claude_desktop_config
206+ } , 'Extracting MCP configuration data from Claude Desktop config' ) ;
207+
208+ const { installation_methods, environment_variables, default_config } = extractMcpConfigData ( requestData . claude_desktop_config ) ;
209+
210+ request . log . debug ( {
211+ operation : 'create_global_mcp_server' ,
212+ userId : request . user ?. id ,
213+ extractedData : {
214+ installation_methods,
215+ environment_variables,
216+ default_config
217+ }
218+ } , 'Successfully extracted MCP configuration data' ) ;
219+
220+ // Prepare server data with extracted configuration
166221 const serverData = {
167- ...requestData ,
168- visibility : 'global' as const
222+ name : requestData . name ,
223+ description : requestData . description ,
224+ long_description : requestData . long_description ,
225+ github_url : requestData . github_url ,
226+ git_branch : requestData . git_branch ,
227+ homepage_url : requestData . homepage_url ,
228+ language : requestData . language ,
229+ runtime : requestData . runtime ,
230+ runtime_min_version : requestData . runtime_min_version ,
231+ installation_methods,
232+ tools : requestData . tools ,
233+ resources : requestData . resources ,
234+ prompts : requestData . prompts ,
235+ visibility : 'global' as const ,
236+ author_name : requestData . author_name ,
237+ author_contact : requestData . author_contact ,
238+ organization : requestData . organization ,
239+ license : requestData . license ,
240+ default_config,
241+ environment_variables,
242+ dependencies : requestData . dependencies ,
243+ category_id : requestData . category_id ,
244+ tags : requestData . tags ,
245+ featured : requestData . featured
169246 } ;
170247
171248 const newServer = await mcpService . createServer (
0 commit comments