@@ -90,7 +90,7 @@ function Introduction({ isExpanded, onToggle }: { isExpanded: boolean; onToggle:
9090
9191 < div className = "text-xs text-[var(--text-muted)] bg-[var(--bg-card)] px-3 py-2 rounded flex items-center gap-2" >
9292 < span > 📁</ span >
93- < code > packages/core/src/mcp/ </ code >
93+ < code > packages/core/src/tools/mcp-*.ts </ code >
9494 </ div >
9595 </ div >
9696 ) }
@@ -154,7 +154,7 @@ export function MCPIntegration() {
154154 </ div >
155155
156156 < div className = "bg-purple-400/20 border border-purple-400 rounded-lg px-6 py-3 w-full max-w-md text-center" >
157- < strong > MCPClientManager </ strong >
157+ < strong > McpClientManager </ strong >
158158 < div className = "text-xs text-gray-400" > 管理多个 MCP 服务器连接</ div >
159159 </ div >
160160
@@ -178,91 +178,105 @@ export function MCPIntegration() {
178178 </ div >
179179 </ Layer >
180180
181- { /* MCPClientManager */ }
182- < Layer title = "MCPClientManager " icon = "🔧" >
181+ { /* McpClientManager */ }
182+ < Layer title = "McpClientManager " icon = "🔧" >
183183 < CodeBlock
184- title = "packages/core/src/mcp/mcp-client-manager.ts"
185- code = { `class MCPClientManager {
186- private clients: Map<string, MCPClient> = new Map();
187- private discoveredTools: Map<string, DiscoveredMCPTool> = new Map();
188-
189- // 连接并发现工具
190- async connectAndDiscover(serverConfig: MCPServerConfig) {
191- // 1. 创建 MCP 客户端
192- const client = new MCPClient(serverConfig);
193-
194- // 2. 连接服务器
195- await client.connect();
196-
197- // 3. 发现可用工具
198- const tools = await client.listTools();
199-
200- // 4. 注册工具
201- for (const tool of tools) {
202- const wrappedTool = new DiscoveredMCPTool(tool, client);
203- this.discoveredTools.set(tool.name, wrappedTool);
204- }
205-
206- this.clients.set(serverConfig.name, client);
184+ title = "packages/core/src/tools/mcp-client-manager.ts"
185+ code = { `// 管理多个 MCP 客户端的生命周期
186+ export class McpClientManager {
187+ private clients: Map<string, McpClient> = new Map();
188+ private readonly toolRegistry: ToolRegistry;
189+ private readonly cliConfig: Config;
190+ private discoveryState: MCPDiscoveryState = MCPDiscoveryState.NOT_STARTED;
191+
192+ constructor(
193+ toolRegistry: ToolRegistry,
194+ cliConfig: Config,
195+ eventEmitter?: EventEmitter,
196+ ) { ... }
197+
198+ // 启动扩展的 MCP 服务器
199+ async startExtension(extension: GeminiCLIExtension) {
200+ await Promise.all(
201+ Object.entries(extension.mcpServers ?? {}).map(([name, config]) =>
202+ this.maybeDiscoverMcpServer(name, { ...config, extension }),
203+ ),
204+ );
207205 }
208206
209- // 获取所有发现的工具
210- getAllDiscoveredTools(): DiscoveredMCPTool[] {
211- return Array.from(this.discoveredTools.values());
207+ // 发现 MCP 服务器的工具
208+ async maybeDiscoverMcpServer(name: string, config: MCPServerConfig) {
209+ const client = new McpClient(name, config, ...);
210+ await client.connect();
211+ // 工具自动注册到 toolRegistry
212+ this.clients.set(name, client);
212213 }
213214
214- // 调用工具
215- async callTool(name: string, args: object): Promise<any> {
216- const tool = this.discoveredTools.get(name);
217- if (!tool) throw new Error(\`Tool not found: \${name}\`);
218-
219- return tool.invoke(args);
215+ // 获取客户端
216+ getClient(serverName: string): McpClient | undefined {
217+ return this.clients.get(serverName);
220218 }
221219}` }
222220 />
221+
222+ < HighlightBox title = "MCPDiscoveryState 状态" icon = "📊" variant = "blue" >
223+ < ul className = "pl-5 list-disc space-y-1 text-sm" >
224+ < li > < code className = "text-cyan-400" > NOT_STARTED</ code > - 发现尚未开始</ li >
225+ < li > < code className = "text-yellow-400" > IN_PROGRESS</ code > - 发现进行中</ li >
226+ < li > < code className = "text-green-400" > COMPLETED</ code > - 发现已完成</ li >
227+ </ ul >
228+ </ HighlightBox >
223229 </ Layer >
224230
225231 { /* MCP 配置 */ }
226232 < Layer title = "MCP 服务器配置" icon = "⚙️" >
227233 < JsonBlock
228- code = { `// ~/.gemini/mcp/servers .json
234+ code = { `// ~/.gemini/settings.json (或项目级 .gemini/settings .json)
229235{
230- "servers": [
231- {
232- "name": "filesystem",
236+ "mcpServers": {
237+ "filesystem": {
233238 "command": "npx",
234- "args": ["-y", "@anthropic/mcp- server-filesystem"],
239+ "args": ["-y", "@modelcontextprotocol/ server-filesystem"],
235240 "env": {
236241 "ALLOWED_PATHS": "/home/user/projects"
237242 }
238243 },
239- {
240- "name": "github",
244+ "github": {
241245 "command": "npx",
242- "args": ["-y", "@anthropic/mcp- server-github"],
246+ "args": ["-y", "@modelcontextprotocol/ server-github"],
243247 "env": {
244248 "GITHUB_TOKEN": "\${GITHUB_TOKEN}"
245249 }
246250 },
247- {
248- "name": "custom-api",
251+ "remote-api": {
249252 "url": "http://localhost:3000/mcp",
250- "auth": {
251- "type": "bearer",
252- "token": "\${API_TOKEN}"
253- }
253+ "type": "sse"
254254 }
255- ]
255+ }
256256}` }
257257 />
258258
259- < HighlightBox title = "配置选项" icon = "📋" variant = "green" >
260- < ul className = "pl-5 list-disc space-y-1" >
261- < li > < strong > command + args</ strong > : 本地进程方式启动 MCP 服务器</ li >
262- < li > < strong > url</ strong > : HTTP/WebSocket 远程连接</ li >
263- < li > < strong > env</ strong > : 传递给服务器的环境变量</ li >
264- < li > < strong > auth</ strong > : 认证配置(bearer、basic、oauth)</ li >
265- </ ul >
259+ < HighlightBox title = "MCPServerConfig 配置选项" icon = "📋" variant = "green" >
260+ < div className = "grid grid-cols-1 md:grid-cols-2 gap-4 text-sm" >
261+ < div >
262+ < h5 className = "font-semibold text-green-400 mb-2" > 传输方式</ h5 >
263+ < ul className = "space-y-1 text-gray-300" >
264+ < li > • < code className = "text-cyan-400" > command + args</ code > : stdio 本地进程</ li >
265+ < li > • < code className = "text-cyan-400" > url + type:'sse'</ code > : SSE 远程连接</ li >
266+ < li > • < code className = "text-cyan-400" > url + type:'http'</ code > : HTTP 流式传输</ li >
267+ < li > • < code className = "text-cyan-400" > tcp</ code > : WebSocket 连接</ li >
268+ </ ul >
269+ </ div >
270+ < div >
271+ < h5 className = "font-semibold text-green-400 mb-2" > 通用配置</ h5 >
272+ < ul className = "space-y-1 text-gray-300" >
273+ < li > • < code className = "text-cyan-400" > env</ code > : 环境变量</ li >
274+ < li > • < code className = "text-cyan-400" > timeout</ code > : 超时时间</ li >
275+ < li > • < code className = "text-cyan-400" > trust</ code > : 信任模式</ li >
276+ < li > • < code className = "text-cyan-400" > includeTools/excludeTools</ code > : 工具过滤</ li >
277+ </ ul >
278+ </ div >
279+ </ div >
266280 </ HighlightBox >
267281 </ Layer >
268282
0 commit comments