diff --git a/backend/agent/coding_agent.py b/backend/agent/coding_agent.py index dbdcfab..a802a4e 100644 --- a/backend/agent/coding_agent.py +++ b/backend/agent/coding_agent.py @@ -20,6 +20,7 @@ import os import subprocess import sys from pathlib import Path +import asyncio import requests import httpx @@ -29,6 +30,9 @@ from backend.agent.mcp_server_adapter import MCPToolAdapter # ── mcp server initialization ──────────────────────────────────────────────────────────────── adapter = MCPToolAdapter() +print("MCPToolAdapter created. Listing all tools from servers...") +asyncio.run(adapter.initialize_all_servers()) +print("listed tools from all servers") load_dotenv() @@ -197,10 +201,11 @@ MAX_HISTORY_CHARS = 80_000 def build_all_tool_description() -> str: """Get relevant tools from the MCP servers based on the query.""" - relevant_tools = adapter.get_all_tools() + all_tools = adapter.get_all_tools() + print(f"Building tool description for {len(all_tools)} tools.") descriptions = [] - for tool in relevant_tools: + for tool in all_tools: params = tool.inputSchema.get("properties", {}) if params: param_lines = [] diff --git a/backend/agent/mcp_server_adapter.py b/backend/agent/mcp_server_adapter.py index 03124e3..dbe7fe5 100644 --- a/backend/agent/mcp_server_adapter.py +++ b/backend/agent/mcp_server_adapter.py @@ -9,8 +9,8 @@ from mcp.client.stdio import stdio_client class MCPToolAdapter: def __init__(self, config_path: str = "mcp_server_config.json"): self.config_path = config_path - self.sessions: Dict[str, ClientSession] = {} - self.exit_stack: Dict[str, Any] = {} + self.servers: Dict[str, Dict] = {} + #self.exit_stack: Dict[str, Any] = {} self.tool_registry: List[Dict[str, Any]] = [] def _load_config(self) -> Dict[str, Any]: @@ -27,46 +27,62 @@ class MCPToolAdapter: print(f"Error decoding JSON config: {e}") return {} - async def initialize_all_sessions(self): - """Initialisiert alle konfigurierten MCP-Sessions und registriert die Tools.""" + async def initialize_all_servers(self): + """Lädt die Konfiguration und fragt alle Server ab, um die Tools zu registrieren.""" + print("Initializing MCP sessions...") config = self._load_config() - + print(f"Loaded config for servers: {list(config.keys())}") + for server_name, params in config.items(): - print(f"Initializing session for {server_name}...") + print(f"Testing connection to {server_name}...") + + self.servers[server_name] = params server_params = StdioServerParameters( command=params["command"], - args=params.get("args", []), - env=params.get("env", None), + args=params.get("args", []) ) try: - # Verbindung aufbauen - transport_gen = stdio_client(server_params) - read, write = await transport_gen.__aenter__() - session = ClientSession(read, write) - await session.__aenter__() - await session.initialize() - - self.sessions[server_name] = session - # Speichern für den Shutdown - self.exit_stack[server_name] = (transport_gen, session) - - # Tools abrufen und registrieren - result = await session.list_tools() - # result ist oft ein Objekt, wir greifen auf das .tools Attribut zu - tools = getattr(result, 'tools', []) + # Verbindung aufbauen + async with stdio_client(server_params) as (read_stream, write_stream): + print(f"Connected to {server_name}. Initializing session...") + #print(f"read_stream: {read_stream}\nwrite_stream: {write_stream}") + async with ClientSession(read_stream, write_stream) as session: + await session.initialize() + print(f"Session initialized for {server_name}. Requesting tools...") + result = await session.list_tools() + print(f"Tools received from {server_name}: {result}") + tools = result.tools + print(f"Tools received from {server_name}: {result}") + #tools = getattr(result, 'tools', []) for tool in tools: - # 'tool' ist hier meist ein Tool-Objekt vom MCP SDK + t_params = tool.inputSchema.get("properties", {}) + if t_params: + param_lines = [] + for pname, pinfo in params.items(): + ptype = pinfo.get("type", "any") + pdesc = pinfo.get("description", "") + param_lines.append(f" - {pname} ({ptype}): {pdesc}") + param_str = "\n".join(param_lines) + else: + param_str = " (none)" + + t_definition = f"- {tool.name}: {tool.description}\nParameters:\n{param_str}" + + self.tool_registry.append({ "server": server_name, - "name": tool.name, - "definition": tool + "tool_name": tool.name, + "tool_description": t_definition }) + + print(f"Registered tool '{tool.name}' from {server_name}.") print(f"Session for {server_name} ready. {len(tools)} tools found.") + except Exception as e: print(f"Failed to initialize {server_name}: {e}") @@ -83,11 +99,19 @@ class MCPToolAdapter: return f"Error: Tool '{tool_name}' not found in registry." server_name = tool_entry["server"] - session = self.sessions.get(server_name) + server = self.servers.get(server_name) + + if server: + server_params = StdioServerParameters( + command=server["command"], + args=server.get("args", []) + ) - if session: try: - result = await session.call_tool(tool_name, arguments) + async with stdio_client(server_params) as (read_stream, write_stream): + async with ClientSession(read_stream, write_stream) as session: + await session.initialize() + result = await session.call_tool(tool_name, arguments) return result except Exception as e: return f"Error calling tool '{tool_name}' on server '{server_name}': {str(e)}" @@ -102,4 +126,15 @@ class MCPToolAdapter: await transport_gen.__aexit__(None, None, None) print(f"Session for {server_name} shut down.") except Exception as e: - print(f"Error during shutdown of {server_name}: {e}") \ No newline at end of file + print(f"Error during shutdown of {server_name}: {e}") + +def main(): + adapter = MCPToolAdapter() + asyncio.run(adapter.initialize_all_servers()) + print("All servers initialized. Registered tools:") + for tool in adapter.get_all_tools(): + print(f"- {tool['name']} (from {tool['server']})") + + +if __name__ == "__main__": + main() \ No newline at end of file diff --git a/backend/agent/mcp_server_config.json b/backend/agent/mcp_server_config.json index 057cd45..9d0fc15 100644 --- a/backend/agent/mcp_server_config.json +++ b/backend/agent/mcp_server_config.json @@ -1,10 +1,10 @@ {"FileSearchServer": { - "command": "python", + "command": "python3", "args": ["servers/mcp_server_file_search.py"] }, "WebSearchServer": { - "command": "python", + "command": "python3", "args": ["servers/mcp_server_web_search.py"], "env": { "DDGS_API_KEY": "your_ddgs_api_key_here" @@ -12,7 +12,7 @@ }, "CodeExecutionServer": { - "command": "python", + "command": "python3", "args": ["servers/mcp_server_code_execution.py"] }