19 Commits

Author SHA1 Message Date
Teknium ceaf622c6d fix(mcp): same-named MCP servers with different credentials connect per profile; owner /reload-mcp keeps adopters' tools
Under gateway.multiplex_profiles every connection ledger in tools/mcp_tool.py
(_servers, _server_scope_keys/_server_tool_scopes, connecting/error/cooldown
maps, the circuit breaker, lazy schema-cache configs, trust metadata) was keyed
by the bare server NAME. The common per-tenant layout — each profile names its
server `github`/`notion` with its own token — gave only the first profile a
connection: the second profile's register_mcp_servers saw the name as "already
connected", refused to adopt it (different credentials, 4ddbcbd35e), and left
the profile silently tool-less with a healthy-looking `configured` status
(#106005 Bug 1/2, #91654). Siblings of the same bug: profile A's failing `x`
put profile B's healthy `x` into A's 10-minute connect cooldown and A's open
circuit breaker short-circuited B's calls; toolsets._resolve_toolset_memo was
not scope-keyed, so B resolved A's `mcp-<server>` tool names.

Keys are now the connection key from the new tools/mcp_tool_scope.py: the bare
name outside a multiplexer (single-profile processes are unchanged) and
(owner_scope, name) under one. Call-time lookups (_resolve_server_key) prefer
the calling scope's own connection, then a shared connection it adopted, so
identical-route profiles still share one subprocess. _select_new_servers,
the cooldown/breaker/trust maps, lazy registration and get_mcp_status all read
and write through the composite key; teardown resolves a task's key by
identity (the MCP loop has no profile context). The toolset memo key includes
registry.current_scope_key().

An owner's scoped /reload-mcp tore down its connection and, with it, every
adopting profile's tool overlay; nothing re-ran the adopters' discovery until
they reloaded. shutdown_mcp_servers(scope=) now records the orphaned adopters
and register_mcp_servers re-registers them under their own home + secret scope
once the owner's rediscovery pass completes.

Docs: multi-profile-gateways.md states the per-profile connection rule.

Fixes #106005
Fixes #91654
Co-authored-by: Bergmann89 <info@bergmann89.de>
Co-authored-by: Izzy-Gottz <srulynj@gmail.com>
2026-09-11 15:27:23 -07:00
joaomarcos d02edc2cbc fix(gateway): register shared MCP tools per profile 2026-09-09 12:20:21 +05:30
Teknium f4d4831e70 simplify(compat): tools/mcp_tool facade — drop 13 re-export blocks (127 names) + shutil re-import; siblings read sibling-defined names directly (_core kept for facade state) 2026-09-03 13:28:47 -07:00
Teknium e83816a4d1 review-fix(comments): restore lost #NNNN rationale comments across non-test source (mechanical sweep, condensed, code unchanged)
For each issue anchor present in BASE 63279301bc non-test .py and absent on HEAD, the BASE comment/docstring block was re-attached at the HEAD location of the code it explained (matched by the distinctive code line / enclosing def). Sentences already covered by an existing HEAD comment were deduped; the issue number always survives. Insert-only: no code lines changed.
2026-09-03 09:44:26 -07:00
Teknium 35b3888fc5 refactor(tools): MCP _dispatch absorbs _invoke_with_recovery; oauth 401 recovery flattened; small predicate folds 2026-09-03 01:37:03 -07:00
Teknium bccfd1de26 refactor(tools): MCP handlers inline single-use render helpers, drop banners; registration foreign-owner log inlined; body blank squeeze 2026-09-03 01:31:18 -07:00
Teknium 58a993a54d refactor(tools): MCP group L docstring/comment compaction, >118-col fixes 2026-09-03 01:30:13 -07:00
Teknium 9458f4c27a refactor(tools): MCP group L docstring rewrap 2026-09-03 01:20:43 -07:00
Teknium 760ac0b609 refactor(tools): MCP handlers/errors/transport/config/health/registration/oauth-manager compaction — shared _dispatch, folded utility factory, auth-type cache tuple 2026-09-03 01:18:04 -07:00
Teknium d23f885c59 refactor(tools): drop section-banner comments in MCP health mixin 2026-09-02 23:51:58 -07:00
Teknium 5e5d1a3a33 refactor(tools): tighten MCP recycle deadlines, watchdog argv/kill loop, stdio liveness probe 2026-09-02 23:34:29 -07:00
Teknium 4efaf9ecd4 refactor(tools): fold single-use MCP helpers, collapse defensive layers, compact docstrings
_stdio_children_dead_impl/_refresh_tools_task folded into their methods,
_recover_401/_is_invalid_client_at_token_endpoint defensive getattr chains
collapsed, lifecycle pid ledgers and drain loop tightened, WHY-preserving
docstring compaction across the group. Schemas byte-identical.
2026-09-02 23:28:07 -07:00
Teknium ee81b1abdd refactor(tools): compact MCP oauth/config/health/lifecycle/agent/content modules
Dead-code removal (_make_hermes_provider_class factory -> direct class def,
_same_endpoint/_context_var_value inlined), image/audio cache unified into
_cache_mcp_media_block, match->isinstance chain, closer hugging, docstring
compaction keeping every invariant. Tool schemas byte-identical.
2026-09-02 22:45:12 -07:00
Teknium 5a8ffa5179 refactor(mcp): health — recycle reason via next(), change-list comprehension in _refresh_tools, docstrings compacted by hand (380 -> 316) 2026-09-02 17:07:08 -07:00
Teknium 546bb4eefc refactor(mcp): repack wrapped message literals (AST-identical) 2026-09-02 16:33:18 -07:00
Teknium 304118797b refactor(mcp): join short multi-line statements across the transport/handlers subset (AST-identical) 2026-09-02 16:29:53 -07:00
Teknium 7916d8e41c refactor(mcp): utility handlers become (rpc, render) pairs on one factory; join short multi-line statements 2026-09-02 16:27:05 -07:00
Teknium 3507382469 refactor(mcp): health — one recycle-deadline table, shared owned-deregister helper, module-level stdio liveness probe 2026-09-02 16:24:16 -07:00
Teknium c1f8af1e86 refactor(tools/mcp): split mcp_tool.py into transport/lifecycle/schema/handlers/... sibling modules; compact watchdog and schema cache 2026-09-02 14:44:15 -07:00