hanzo-mcp 0.8.2__py3-none-any.whl → 0.8.4__py3-none-any.whl

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.

Potentially problematic release.


This version of hanzo-mcp might be problematic. Click here for more details.

@@ -8,16 +8,26 @@ from mcp.server import FastMCP
8
8
 
9
9
  from hanzo_mcp.tools.common.base import BaseTool, ToolRegistry
10
10
 
11
+ # Import unified CLI tools (single source of truth)
12
+ from hanzo_mcp.tools.agent.cli_tools import (
13
+ GrokCLITool,
14
+ AiderCLITool,
15
+ ClineCLITool,
16
+ CodexCLITool,
17
+ ClaudeCLITool,
18
+ GeminiCLITool,
19
+ HanzoDevCLITool,
20
+ OpenHandsCLITool,
21
+ ClaudeCodeCLITool, # cc alias
22
+ OpenHandsShortCLITool, # oh alias
23
+ register_cli_tools,
24
+ )
25
+
11
26
  # Import the main implementations (using hanzo-agents SDK)
12
27
  from hanzo_mcp.tools.agent.agent_tool import AgentTool
13
- from hanzo_mcp.tools.agent.swarm_tool import SwarmTool
14
28
  from hanzo_mcp.tools.agent.network_tool import NetworkTool
15
29
  from hanzo_mcp.tools.common.permissions import PermissionManager
16
- from hanzo_mcp.tools.agent.grok_cli_tool import GrokCLITool
17
30
  from hanzo_mcp.tools.agent.code_auth_tool import CodeAuthTool
18
- from hanzo_mcp.tools.agent.codex_cli_tool import CodexCLITool
19
- from hanzo_mcp.tools.agent.claude_cli_tool import ClaudeCLITool
20
- from hanzo_mcp.tools.agent.gemini_cli_tool import GeminiCLITool
21
31
 
22
32
 
23
33
  def register_agent_tools(
@@ -57,37 +67,48 @@ def register_agent_tools(
57
67
  max_tool_uses=agent_max_tool_uses,
58
68
  )
59
69
 
60
- # Create swarm tool
61
- swarm_tool = SwarmTool(
62
- permission_manager=permission_manager,
63
- model=agent_model,
64
- api_key=agent_api_key,
65
- base_url=agent_base_url,
66
- max_tokens=agent_max_tokens,
67
- agent_max_iterations=agent_max_iterations,
68
- agent_max_tool_uses=agent_max_tool_uses,
69
- )
70
-
71
- # Create CLI agent tools
72
- claude_cli_tool = ClaudeCLITool(
73
- permission_manager=permission_manager,
74
- model=agent_model, # Can override default Sonnet
75
- )
76
-
77
- codex_cli_tool = CodexCLITool(
78
- permission_manager=permission_manager,
79
- model=agent_model if agent_model and "gpt" in agent_model else None,
80
- )
81
-
82
- gemini_cli_tool = GeminiCLITool(
83
- permission_manager=permission_manager,
84
- model=agent_model if agent_model and "gemini" in agent_model else None,
85
- )
86
-
87
- grok_cli_tool = GrokCLITool(
88
- permission_manager=permission_manager,
89
- model=agent_model if agent_model and "grok" in agent_model else None,
90
- )
70
+ # Register a swarm alias that forwards to AgentTool with default concurrency
71
+ class SwarmAliasTool(BaseTool):
72
+ name = "swarm"
73
+ description = (
74
+ "Alias for agent with concurrency. swarm == agent:5 by default.\n"
75
+ "Use 'swarm' for parallel multi-agent runs; 'swarm:N' for N agents."
76
+ )
77
+
78
+ def __init__(self, agent_tool: AgentTool):
79
+ self._agent = agent_tool
80
+
81
+ async def call(self, ctx, **params): # type: ignore[override]
82
+ # Default to 5 agents unless explicitly provided
83
+ params = dict(params)
84
+ params.setdefault("concurrency", 5)
85
+ return await self._agent.call(ctx, **params)
86
+
87
+ def register(self, mcp_server: FastMCP): # type: ignore[override]
88
+ tool_self = self
89
+
90
+ @mcp_server.tool(name=self.name, description=self.description)
91
+ async def swarm(
92
+ ctx,
93
+ prompts: str | list[str], # forwarded
94
+ concurrency: int | None = None,
95
+ model: str | None = None,
96
+ use_memory: bool | None = None,
97
+ memory_backend: str | None = None,
98
+ ) -> str:
99
+ p = {
100
+ "prompts": prompts,
101
+ }
102
+ if concurrency is not None:
103
+ p["concurrency"] = concurrency
104
+ if model is not None:
105
+ p["model"] = model
106
+ if use_memory is not None:
107
+ p["use_memory"] = use_memory
108
+ if memory_backend is not None:
109
+ p["memory_backend"] = memory_backend
110
+ return await tool_self.call(ctx, **p)
111
+ return tool_self
91
112
 
92
113
  # Create auth management tool
93
114
  code_auth_tool = CodeAuthTool()
@@ -98,24 +119,14 @@ def register_agent_tools(
98
119
  default_mode="hybrid", # Prefer local, fallback to cloud
99
120
  )
100
121
 
101
- # Register tools
122
+ # Register core agent tools
102
123
  ToolRegistry.register_tool(mcp_server, agent_tool)
103
- ToolRegistry.register_tool(mcp_server, swarm_tool)
124
+ ToolRegistry.register_tool(mcp_server, SwarmAliasTool(agent_tool))
104
125
  ToolRegistry.register_tool(mcp_server, network_tool)
105
- ToolRegistry.register_tool(mcp_server, claude_cli_tool)
106
- ToolRegistry.register_tool(mcp_server, codex_cli_tool)
107
- ToolRegistry.register_tool(mcp_server, gemini_cli_tool)
108
- ToolRegistry.register_tool(mcp_server, grok_cli_tool)
109
126
  ToolRegistry.register_tool(mcp_server, code_auth_tool)
110
127
 
128
+ # Register all CLI tools (includes claude, codex, gemini, grok, etc.)
129
+ cli_tools = register_cli_tools(mcp_server, permission_manager)
130
+
111
131
  # Return list of registered tools
112
- return [
113
- agent_tool,
114
- swarm_tool,
115
- network_tool,
116
- claude_cli_tool,
117
- codex_cli_tool,
118
- gemini_cli_tool,
119
- grok_cli_tool,
120
- code_auth_tool,
121
- ]
132
+ return [agent_tool, network_tool, code_auth_tool] + cli_tools
@@ -109,6 +109,7 @@ class AgentToolParams(TypedDict, total=False):
109
109
  model: Optional[str]
110
110
  use_memory: Optional[bool]
111
111
  memory_backend: Optional[str]
112
+ concurrency: Optional[int]
112
113
 
113
114
 
114
115
  class MCPAgentState(State):
@@ -387,7 +388,17 @@ Usage notes:
387
388
  await tool_ctx.error("hanzo-agents SDK is required but not available")
388
389
  return "Error: hanzo-agents SDK is required for agent tool functionality. Please install it with: pip install hanzo-agents"
389
390
 
390
- # Use hanzo-agents SDK
391
+ # Determine concurrency (parallel agents)
392
+ concurrency = params.get("concurrency")
393
+ if concurrency is not None and isinstance(concurrency, int) and concurrency > 0:
394
+ # Expand prompt list to match concurrency
395
+ if len(prompt_list) == 1:
396
+ prompt_list = prompt_list * concurrency
397
+ elif len(prompt_list) < concurrency:
398
+ # Repeat prompts to reach concurrency
399
+ times = (concurrency + len(prompt_list) - 1) // len(prompt_list)
400
+ prompt_list = (prompt_list * times)[:concurrency]
401
+
391
402
  await tool_ctx.info(
392
403
  f"Launching {len(prompt_list)} agent(s) using hanzo-agents SDK"
393
404
  )