@@ -6,14 +6,20 @@ import { StreamableHTTPServerTransport } from '@modelcontextprotocol/sdk/server/
6
6
import express from 'express' ;
7
7
import { fromError } from 'zod-validation-error/v3' ;
8
8
import { McpOptions , parseQueryOptions } from './options' ;
9
- import { initMcpServer , newMcpServer } from './server' ;
9
+ import { ClientOptions , initMcpServer , newMcpServer } from './server' ;
10
10
import { parseAuthHeaders } from './headers' ;
11
11
12
- const newServer = (
13
- defaultMcpOptions : McpOptions ,
14
- req : express . Request ,
15
- res : express . Response ,
16
- ) : McpServer | null => {
12
+ const newServer = ( {
13
+ clientOptions,
14
+ mcpOptions : defaultMcpOptions ,
15
+ req,
16
+ res,
17
+ } : {
18
+ clientOptions : ClientOptions ;
19
+ mcpOptions : McpOptions ;
20
+ req : express . Request ;
21
+ res : express . Response ;
22
+ } ) : McpServer | null => {
17
23
const server = newMcpServer ( ) ;
18
24
19
25
let mcpOptions : McpOptions ;
@@ -35,10 +41,8 @@ const newServer = (
35
41
initMcpServer ( {
36
42
server : server ,
37
43
clientOptions : {
44
+ ...clientOptions ,
38
45
...authOptions ,
39
- defaultHeaders : {
40
- 'X-Stainless-MCP' : 'true' ,
41
- } ,
42
46
} ,
43
47
mcpOptions,
44
48
} ) ;
@@ -56,17 +60,19 @@ const newServer = (
56
60
return server ;
57
61
} ;
58
62
59
- const post = ( defaultOptions : McpOptions ) => async ( req : express . Request , res : express . Response ) => {
60
- const server = newServer ( defaultOptions , req , res ) ;
61
- // If we return null, we already set the authorization error.
62
- if ( server === null ) return ;
63
- const transport = new StreamableHTTPServerTransport ( {
64
- // Stateless server
65
- sessionIdGenerator : undefined ,
66
- } ) ;
67
- await server . connect ( transport ) ;
68
- await transport . handleRequest ( req , res , req . body ) ;
69
- } ;
63
+ const post =
64
+ ( options : { clientOptions : ClientOptions ; mcpOptions : McpOptions } ) =>
65
+ async ( req : express . Request , res : express . Response ) => {
66
+ const server = newServer ( { ...options , req, res } ) ;
67
+ // If we return null, we already set the authorization error.
68
+ if ( server === null ) return ;
69
+ const transport = new StreamableHTTPServerTransport ( {
70
+ // Stateless server
71
+ sessionIdGenerator : undefined ,
72
+ } ) ;
73
+ await server . connect ( transport ) ;
74
+ await transport . handleRequest ( req , res , req . body ) ;
75
+ } ;
70
76
71
77
const get = async ( req : express . Request , res : express . Response ) => {
72
78
res . status ( 405 ) . json ( {
@@ -88,20 +94,26 @@ const del = async (req: express.Request, res: express.Response) => {
88
94
} ) ;
89
95
} ;
90
96
91
- export const streamableHTTPApp = ( options : McpOptions ) : express . Express => {
97
+ export const streamableHTTPApp = ( {
98
+ clientOptions = { } ,
99
+ mcpOptions = { } ,
100
+ } : {
101
+ clientOptions ?: ClientOptions ;
102
+ mcpOptions ?: McpOptions ;
103
+ } ) : express . Express => {
92
104
const app = express ( ) ;
93
105
app . set ( 'query parser' , 'extended' ) ;
94
106
app . use ( express . json ( ) ) ;
95
107
96
108
app . get ( '/' , get ) ;
97
- app . post ( '/' , post ( options ) ) ;
109
+ app . post ( '/' , post ( { clientOptions , mcpOptions } ) ) ;
98
110
app . delete ( '/' , del ) ;
99
111
100
112
return app ;
101
113
} ;
102
114
103
115
export const launchStreamableHTTPServer = async ( options : McpOptions , port : number | string | undefined ) => {
104
- const app = streamableHTTPApp ( options ) ;
116
+ const app = streamableHTTPApp ( { mcpOptions : options } ) ;
105
117
const server = app . listen ( port ) ;
106
118
const address = server . address ( ) ;
107
119
0 commit comments