Skip to content

Commit c3610ff

Browse files
authored
Chore/Close mcp connection (#4375)
* close mcp connection * update file types
1 parent df26e8a commit c3610ff

File tree

2 files changed

+79
-45
lines changed

2 files changed

+79
-45
lines changed

packages/components/nodes/tools/MCP/core.ts

Lines changed: 61 additions & 36 deletions
Original file line numberDiff line numberDiff line change
@@ -19,44 +19,61 @@ export class MCPToolkit extends BaseToolkit {
1919
this.serverParams = serverParams
2020
this.transportType = transportType
2121
}
22-
async initialize() {
23-
if (this._tools === null) {
24-
this.client = new Client(
25-
{
26-
name: 'flowise-client',
27-
version: '1.0.0'
28-
},
29-
{
30-
capabilities: {}
31-
}
32-
)
33-
if (this.transportType === 'stdio') {
34-
// Compatible with overridden PATH configuration
35-
this.serverParams.env = {
22+
23+
// Method to create a new client with transport
24+
async createClient(): Promise<Client> {
25+
const client = new Client(
26+
{
27+
name: 'flowise-client',
28+
version: '1.0.0'
29+
},
30+
{
31+
capabilities: {}
32+
}
33+
)
34+
35+
let transport: StdioClientTransport | SSEClientTransport | StreamableHTTPClientTransport
36+
37+
if (this.transportType === 'stdio') {
38+
// Compatible with overridden PATH configuration
39+
const params = {
40+
...this.serverParams,
41+
env: {
3642
...(this.serverParams.env || {}),
3743
PATH: process.env.PATH
3844
}
45+
}
3946

40-
this.transport = new StdioClientTransport(this.serverParams as StdioServerParameters)
41-
await this.client.connect(this.transport)
42-
} else {
43-
if (this.serverParams.url === undefined) {
44-
throw new Error('URL is required for SSE transport')
45-
}
47+
transport = new StdioClientTransport(params as StdioServerParameters)
48+
await client.connect(transport)
49+
} else {
50+
if (this.serverParams.url === undefined) {
51+
throw new Error('URL is required for SSE transport')
52+
}
4653

47-
const baseUrl = new URL(this.serverParams.url)
48-
try {
49-
this.transport = new StreamableHTTPClientTransport(baseUrl)
50-
await this.client.connect(this.transport)
51-
} catch (error) {
52-
this.transport = new SSEClientTransport(baseUrl)
53-
await this.client.connect(this.transport)
54-
}
54+
const baseUrl = new URL(this.serverParams.url)
55+
try {
56+
transport = new StreamableHTTPClientTransport(baseUrl)
57+
await client.connect(transport)
58+
} catch (error) {
59+
transport = new SSEClientTransport(baseUrl)
60+
await client.connect(transport)
5561
}
62+
}
63+
64+
return client
65+
}
66+
67+
async initialize() {
68+
if (this._tools === null) {
69+
this.client = await this.createClient()
5670

5771
this._tools = await this.client.request({ method: 'tools/list' }, ListToolsResultSchema)
5872

5973
this.tools = await this.get_tools()
74+
75+
// Close the initial client after initialization
76+
await this.client.close()
6077
}
6178
}
6279

@@ -69,7 +86,7 @@ export class MCPToolkit extends BaseToolkit {
6986
throw new Error('Client is not initialized')
7087
}
7188
return await MCPTool({
72-
client: this.client,
89+
toolkit: this,
7390
name: tool.name,
7491
description: tool.description || '',
7592
argsSchema: createSchemaModel(tool.inputSchema)
@@ -80,23 +97,31 @@ export class MCPToolkit extends BaseToolkit {
8097
}
8198

8299
export async function MCPTool({
83-
client,
100+
toolkit,
84101
name,
85102
description,
86103
argsSchema
87104
}: {
88-
client: Client
105+
toolkit: MCPToolkit
89106
name: string
90107
description: string
91108
argsSchema: any
92109
}): Promise<Tool> {
93110
return tool(
94111
async (input): Promise<string> => {
95-
const req: CallToolRequest = { method: 'tools/call', params: { name: name, arguments: input } }
96-
const res = await client.request(req, CallToolResultSchema)
97-
const content = res.content
98-
const contentString = JSON.stringify(content)
99-
return contentString
112+
// Create a new client for this request
113+
const client = await toolkit.createClient()
114+
115+
try {
116+
const req: CallToolRequest = { method: 'tools/call', params: { name: name, arguments: input } }
117+
const res = await client.request(req, CallToolResultSchema)
118+
const content = res.content
119+
const contentString = JSON.stringify(content)
120+
return contentString
121+
} finally {
122+
// Always close the client after the request completes
123+
await client.close()
124+
}
100125
},
101126
{
102127
name: name,

packages/ui/src/views/chatmessage/ChatMessage.jsx

Lines changed: 18 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -238,25 +238,34 @@ export const ChatMessage = ({ open, chatflowid, isAgentCanvas, isDialog, preview
238238
* {isImageUploadAllowed: boolean, imgUploadSizeAndTypes: Array<{ fileTypes: string[], maxUploadSize: number }>}
239239
*/
240240
let acceptFile = false
241+
242+
// Early return if constraints are not available yet
243+
if (!constraints) {
244+
console.warn('Upload constraints not loaded yet')
245+
return false
246+
}
247+
241248
if (constraints.isImageUploadAllowed) {
242249
const fileType = file.type
243250
const sizeInMB = file.size / 1024 / 1024
244-
constraints.imgUploadSizeAndTypes.map((allowed) => {
245-
if (allowed.fileTypes.includes(fileType) && sizeInMB <= allowed.maxUploadSize) {
246-
acceptFile = true
247-
}
248-
})
251+
if (constraints.imgUploadSizeAndTypes && Array.isArray(constraints.imgUploadSizeAndTypes)) {
252+
constraints.imgUploadSizeAndTypes.forEach((allowed) => {
253+
if (allowed.fileTypes && allowed.fileTypes.includes(fileType) && sizeInMB <= allowed.maxUploadSize) {
254+
acceptFile = true
255+
}
256+
})
257+
}
249258
}
250259

251260
if (fullFileUpload) {
252261
return true
253262
} else if (constraints.isRAGFileUploadAllowed) {
254263
const fileExt = file.name.split('.').pop()
255-
if (fileExt) {
256-
constraints.fileUploadSizeAndTypes.map((allowed) => {
257-
if (allowed.fileTypes.length === 1 && allowed.fileTypes[0] === '*') {
264+
if (fileExt && constraints.fileUploadSizeAndTypes && Array.isArray(constraints.fileUploadSizeAndTypes)) {
265+
constraints.fileUploadSizeAndTypes.forEach((allowed) => {
266+
if (allowed.fileTypes && allowed.fileTypes.length === 1 && allowed.fileTypes[0] === '*') {
258267
acceptFile = true
259-
} else if (allowed.fileTypes.includes(`.${fileExt}`)) {
268+
} else if (allowed.fileTypes && allowed.fileTypes.includes(`.${fileExt}`)) {
260269
acceptFile = true
261270
}
262271
})

0 commit comments

Comments
 (0)