Skip to content

feat(mcp): finish the per-config connection lookups (#5701) - #5817

Open
ntdatt812 wants to merge 1 commit into
tinyhumansai:mainfrom
ntdatt812:fix/5701-connections-for-config
Open

feat(mcp): finish the per-config connection lookups (#5701)#5817
ntdatt812 wants to merge 1 commit into
tinyhumansai:mainfrom
ntdatt812:fix/5701-connections-for-config

Conversation

@ntdatt812

@ntdatt812 ntdatt812 commented Aug 27, 2026

Copy link
Copy Markdown

Closes #5701.

The issue is right, but main has moved

connections::connect resolves per-config through host::for_config while the by-server-id lookups read the process-global host::try_service, so a host that connects through the facade can never see the connection it just made.

Since the issue was filed, main already grew two of the answers:

function added
all_connected_tools_for_config before the issue
disconnect_for_config e34226cb0, 2026-08-23 16:35 UTC

The issue was opened at 19:14 UTC the same day, ~2h40m after disconnect_for_config landed, and lists disconnect among the broken seven. That is not a mistake on the reporter's part — I checked git cat-file -p 523ef352a:src/openhuman/mcp/registry/mod.rs, the revision the issue names, and neither _for_config variant exists there. The issue is accurate for its base and stale against main.

That changes what needs doing. This is not one odd function out of eight; it is a migration with two of seven done. disconnect_for_config's own doc comment already spells out the trap the issue spends a page reconstructing:

the by-server-id form resolves through the process default, which stops answering once a second workspace is open

So the three resolutions the issue proposes — take a config on all eight, take a &McpHost on all eight, or make connect read the global — are all breaking, while the maintainers had already chosen a fourth: add variants, leave the ambient forms alone. This follows that.

What this adds

Five functions, each next to its ambient counterpart, same shape as the two that exist:

connected_overview_for_config    server_tools_for_config    is_connected_for_config
auth_hint_for_config             last_error_for_config

Purely additive — no existing signature changes and no caller moves.

Each Err arm now logs the workspace-resolution failure rather than folding it silently into false / None / Vec::new(). That is the issue's second ask: "the service is not up" and "the server is not connected" are different facts and currently share a return value.

One naming judgment call for you to overrule if you disagree: server_tools_for_config, not tools_for_config. The mechanical suffix would put tools_for_config directly beneath all_connected_tools_for_config, where it reads as that function's every-server sibling rather than as the one-server form.

Test

per_config_lookups_see_a_per_config_connection in tests/mcp_registry_e2e.rs.

Making it discriminate was the interesting part. With a single workspace open, try_service happily returns that lone host, so a wrong implementation routed through the global would still pass. The test therefore opens two workspaces first and asserts the precondition explicitly:

assert!(host::try_service().is_none(), ...);

With two open and no default, try_service refuses to guess — which is the state an embedder holding its own per-config service is in permanently. It then connects through the facade in workspace A and asserts the per-config lookups see it, that workspace B does not, and that disconnect_for_config drops it.

Verified red against the wrong implementation: reimplementing is_connected_for_config over try_service() (the way the ambient form does) turns it red — panicked at tests/mcp_registry_e2e.rs:723: the workspace that connected must see its own connection.

Verification

  • cargo test --features mcp --test mcp_registry_e2e — 17 passed.
  • cargo check --lib --features mcp — clean.
  • cargo check --lib --no-default-features — clean. stub.rs deliberately gets no additions: its docs say it mirrors only the surface always-compiled callers depend on, and these five have no such caller yet. The disabled build is the drift catcher and it is green.
  • cargo fmt --all — clean.

Summary by CodeRabbit

  • New Features

    • Added workspace-specific connection status and server lookup support.
    • Connection details, available tools, authentication hints, and recent errors can now be retrieved for a selected workspace.
    • Workspace connection actions remain isolated, even when no global connection is configured.
  • Bug Fixes

    • Improved connection lookups to consistently use the selected workspace rather than a process-wide default.

`connections::connect` resolves per-config via `host::for_config`, while the
by-server-id lookups read the process-global `host::try_service`. A host that
connects through the facade could never see the connection it just made.

`main` is already midway through the answer: `all_connected_tools_for_config`
and `disconnect_for_config` both exist, and `disconnect_for_config`'s own docs
describe this exact trap. Neither was present at `523ef352a`, the revision the
issue was written against, which is why the issue reads it as one odd function
out of eight rather than as a migration with two of seven done.

This finishes it — the same shape, next to each ambient counterpart:

  connected_overview_for_config
  server_tools_for_config
  is_connected_for_config
  auth_hint_for_config
  last_error_for_config

Additive, so nothing existing changes signature and no caller has to move.

Each `Err` arm logs the workspace-resolution failure instead of folding it
silently into `false` / `None` / `Vec::new()`, which is the issue's second ask:
"the service is not up" and "the server is not connected" should not be
indistinguishable.

`server_tools_for_config` breaks the mechanical `_for_config` suffix on purpose:
`tools_for_config` would sit directly below `all_connected_tools_for_config` and
read as its every-server sibling.

Test: `per_config_lookups_see_a_per_config_connection` opens two workspaces so
`try_service` has no honest answer, connects through the facade in one, and
asserts the per-config lookups see it and that the other workspace does not.
Verified discriminating — reimplementing one variant over `try_service` turns it
red.

`cargo test --features mcp --test mcp_registry_e2e` 17 passed.
`cargo check --lib --features mcp` and `--no-default-features` both clean.
@ntdatt812
ntdatt812 requested a review from a team August 27, 2026 03:03
@coderabbitai

coderabbitai Bot commented Aug 27, 2026

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: CHILL

Plan: Pro Plus

Run ID: 69dc8472-8262-4516-9efd-898b598db819

📥 Commits

Reviewing files that changed from the base of the PR and between 5630b00 and 330be8d.

📒 Files selected for processing (2)
  • src/openhuman/mcp/registry/mod.rs
  • tests/mcp_registry_e2e.rs

Included review availability: Your plan provides up to 10 included reviews per hour; 8 remain after this review.


📝 Walkthrough

Walkthrough

The MCP connections facade adds five configuration-scoped lookup functions. Each resolves the host for the supplied workspace configuration and returns a benign default when no host exists. An end-to-end test verifies isolation between two workspaces.

Changes

Per-config MCP connection lookups

Layer / File(s) Summary
Per-config lookup facade and validation
src/openhuman/mcp/registry/mod.rs, tests/mcp_registry_e2e.rs
Adds configuration-scoped overview, tools, connection, auth hint, and error lookups. Missing hosts produce logged default results. The test confirms workspace isolation and disconnect behavior.

Estimated code review effort: 3 (Moderate) | ~20 minutes

Merge Risk: ⚪ Minimal · up to 330be

This change adds per-configuration connection lookups without changing existing interfaces, with the supplied checks passing. No actionable merge-blocking risk remains beyond normal review.

Suggested reviewers: senamakel

Poem

A rabbit checks each workspace door
The right host answers, not one global store
Tools and hints stay safely in line
Errors remain where connections shine
Two burrows test the paths anew
Then every link is cleared from view

🚥 Pre-merge checks | ✅ 5
✅ Passed checks (5 passed)
Check name Status Explanation
Description Check ✅ Passed Check skipped - CodeRabbit’s high-level summary is enabled.
Title check ✅ Passed The title clearly identifies the MCP change and accurately summarizes the completion of per-config connection lookups.
Linked Issues check ✅ Passed The PR satisfies issue #5701 by providing per-config variants for the remaining connection lookups, matching the existing per-config connect, tools, and disconnect behavior. Missing-service branches a…
Out of Scope Changes check ✅ Passed The changes remain within scope. They add the requested per-config connection APIs, required logging, and focused end-to-end coverage for workspace isolation and disconnection.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%. Docstring coverage is scoped to functions touched by this diff. Analyzed 12 functions across 2 files.
Full details: Linked Issues check

Explanation

The PR satisfies issue #5701 by providing per-config variants for the remaining connection lookups, matching the existing per-config connect, tools, and disconnect behavior. Missing-service branches also log resolution failures, and the end-to-end test verifies workspace isolation.

Warning

Your free Security trial is over. An organization admin can activate billing to continue.


Comment @coderabbitai help to get the list of available commands.

@tinysweeper tinysweeper Bot added the priority: p3 Whenever. Cosmetic, a nicety, or a cleanup with no user visible effect. label Aug 27, 2026

@tinysweeper tinysweeper Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

tinysweeper found nothing blocking. Approving.

$0.0000 · 0 in / 0 out

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

Labels

priority: p3 Whenever. Cosmetic, a nicety, or a cleanup with no user visible effect.

Projects

None yet

Development

Successfully merging this pull request may close these issues.

mcp registry connections facade: connect() is per-config, the other seven read the process global

1 participant