Skip to content

feat: add supports_parallel_tool_calls for MCP servers#9944

Closed
teknium1 wants to merge 1 commit into
mainfrom
codex-port/mcp-parallel-tool-calls
Closed

feat: add supports_parallel_tool_calls for MCP servers#9944
teknium1 wants to merge 1 commit into
mainfrom
codex-port/mcp-parallel-tool-calls

Conversation

@teknium1

Copy link
Copy Markdown
Contributor

Summary

Port of openai/codex#17667: MCP servers can now opt-in to parallel tool execution via a per-server config flag.

Problem

All MCP tools were forced to run sequentially because they weren't in the static _PARALLEL_SAFE_TOOLS set in run_agent.py. This was unnecessarily slow for MCP servers whose tools are safe to run concurrently (e.g. read-only query servers, independent API endpoints).

Solution

Add supports_parallel_tool_calls: true config option for MCP servers:

mcp_servers:
  docs:
    command: "docs-server"
    supports_parallel_tool_calls: true

When set, tools from that server are eligible for concurrent execution in the same tool-call batch, matching the behavior already available for built-in read-only tools (web_search, read_file, etc.).

Implementation

  • tools/mcp_tool.py: New _parallel_safe_servers set tracks sanitized server names with the flag enabled. Populated during register_mcp_servers() (idempotent, handles toggling on/off). New public API is_mcp_tool_parallel_safe(tool_name) checks if a tool belongs to a parallel-safe server.
  • run_agent.py: New _is_mcp_tool_parallel_safe() lazy-import wrapper. _should_parallelize_tool_batch() now checks MCP tools against server config when they're not in the static parallel-safe set.
  • Tests: 7 unit tests for is_mcp_tool_parallel_safe() and register_mcp_servers tracking, plus 4 integration tests for _should_parallelize_tool_batch() with MCP tools.
  • Docs: Updated MCP feature docs, config reference, and module docstring.

Architectural differences from Codex

Codex is Rust and threads the config through ToolRouter at the crate level. Hermes uses a module-level set (_parallel_safe_servers) populated during MCP server registration, queried via a function that does server name extraction from tool names. The server name matching handles underscores in sanitized server names by checking all registered parallel-safe prefixes.

Test plan

  • 11 new tests all passing
  • All 172 existing MCP tests still pass
  • All 15 parallel-related run_agent tests still pass

Port from openai/codex#17667: MCP servers can now opt-in to parallel
tool execution by setting supports_parallel_tool_calls: true in their
config. This allows tools from the same server to run concurrently
within a single tool-call batch, matching the behavior already available
for built-in tools like web_search and read_file.

Previously all MCP tools were forced sequential because they weren't in
the _PARALLEL_SAFE_TOOLS set. Now _should_parallelize_tool_batch checks
is_mcp_tool_parallel_safe() which looks up the server's config flag.

Config example:
  mcp_servers:
    docs:
      command: "docs-server"
      supports_parallel_tool_calls: true

Changes:
- tools/mcp_tool.py: Track parallel-safe servers in _parallel_safe_servers
  set, populated during register_mcp_servers(). Add is_mcp_tool_parallel_safe()
  public API.
- run_agent.py: Add _is_mcp_tool_parallel_safe() lazy-import wrapper. Update
  _should_parallelize_tool_batch() to check MCP tools against server config.
- 11 new tests covering the feature end-to-end.
- Updated MCP docs and config reference.
@alt-glitch alt-glitch added type/feature New feature or request P3 Low — cosmetic, nice to have tool/mcp MCP client and OAuth comp/agent Core agent loop, run_agent.py, prompt builder labels Apr 26, 2026
@teknium1

Copy link
Copy Markdown
Contributor Author

Closing in favor of #26825, which salvages this PR onto current main with the cherry-pick conflict (circuit breaker block landed on main after this PR's branch point) resolved and two stale test mocks of the removed _sync_mcp_toolsets helper fixed. Your authorship preserved via rebase-merge.

@teknium1 teknium1 closed this May 16, 2026
@teknium1

Copy link
Copy Markdown
Contributor Author

Correction on the earlier close comment: #26825 was squash-merged (not rebase-merged). Authorship is preserved in either case since both PRs were authored by you.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

comp/agent Core agent loop, run_agent.py, prompt builder P3 Low — cosmetic, nice to have tool/mcp MCP client and OAuth type/feature New feature or request

Projects

None yet

Development

Successfully merging this pull request may close these issues.

2 participants