Skip to content

MCP servers

MCP connects the Wuu engine to tools provided by a local process or remote service. After connecting, ask the agent to use the server by name and describe the task. Wuu discovers and calls tools; it does not currently provide a resource or prompt browser, and MCP requests for an additional user-input exchange are unsupported.

Type @ or open + to search the same panel of plugins, skills, and actions. Connected MCP services and active plugins with conversation tools can be selected; themes and service-only packages do not appear as conversation plugins. Unavailable connections offer connection or management controls. The panel retains attachment actions.

Selecting a plugin inserts an inline reference at the cursor. Continue writing, select more plugins, or remove a reference with Backspace/Delete. Drafts, queued messages, and sent messages retain the plugin and server identities, including the authorization. Names alone are not identities. Separate MCP definitions can represent different accounts; selecting the same canonical definition in another project still shares its login.

References are supported by Wuu, Codex, and Claude Code. Other engine adapters must explicitly advertise conversation-plugins; the composer blocks unsupported selection and submission. A message with references submitted during an active turn is queued for the next turn. Tool permissions still apply. Before execution, Wuu checks that the server and its authorization still match; a replaced login requires selecting the server again. An older running connection cannot borrow the replacement login.

Connection management opens the plugin catalog while preserving the draft. Return to the conversation after authorization and select the connected server.

Open Plugins → Add → Add custom MCP server. Enter a server URL or a local executable with its arguments, or choose Import JSON to paste an mcpServers or mcp_servers object. Advanced options accept headers, environment variables, transport, OAuth registration values, and tool timeouts as JSON.

Saved definitions use the selected configuration provider and apply immediately. Running turns keep the servers they started with; new turns use the saved definitions. Editing and removal check the configuration revision; reopen the editor if another window has changed it. Imports reject duplicate names and unsupported connection fields. Imported values are literal, including ${VAR} placeholders.

You can also add definitions to mcp_servers in the user configuration, normally ~/.wuu/config.json, and restart Wuu after editing on disk.

This fragment configures a local server and a remote one. Replace the executable, script path, and URL with your server’s values:

{
"mcp_servers": {
"project-tools": {
"command": "node",
"args": ["/absolute/path/mcp-server.js"],
"env": { "PROJECT_ID": "demo" }
},
"docs": {
"url": "https://mcp.example.com/mcp",
"transport": "http"
}
}
}

For stdio, Wuu starts the executable directly with args, not through a shell. The child inherits the process environment, with env overriding named values. The server must reserve stdout for protocol messages and write logs to stderr.

For remote servers, http and streamable-http select streamable HTTP, while sse selects legacy SSE. Omitting transport enables HTTP probing with SSE fallback for an incompatible endpoint, not for an unreachable network. An explicitly selected transport does not fall back.

Each streamable HTTP POST response belongs to its call. Completing or cancelling a call closes its response stream. If the stream ends before a result arrives, or sends an invalid or oversized message, that call fails promptly. Wuu does not replay a tool call after a broken stream because its effects may already have occurred. Other calls and the server notification stream stay connected. A POST response with another call’s ID is rejected without resolving that other call. Server-initiated requests use a separate ID namespace.

Replies to server-initiated requests use a separate bounded lane: up to four sends and 32 waiting replies per connection, with a five-second budget including queue time. A stalled reply does not block tool results or notifications. Completing or cancelling the originating POST call cancels its queued and active replies; a server cancellation targets the exact numeric or string request ID. Disconnect cancels reply work and waits for the senders to stop. Failed or excess replies fail their originating call without replaying it. An unsolicited request flood that fills the queue closes the connection with a capacity error; individual unsolicited send failures are logged. A reply rejected with an expired session is not resent into a new session. Queued replies and authentication retries stay bound to the session that received the request; replacing that session invalidates them without sending them with the new session ID.

Remote headers are literal header values. Native mcp_servers does not expand ${VAR} placeholders. Keep secrets out of committed configuration and do not assume a placeholder is a credential reference. enabled: false retains a definition without connecting at startup.

Set tool_timeout_ms on a server to allow longer reports, exports, or builds:

{
"mcp_servers": {
"docs": {
"url": "https://mcp.example.com/mcp",
"transport": "http",
"tool_timeout_ms": 120000
}
}
}

The value is a whole number of milliseconds from 1 to 3600000 (one hour). Omit the field to keep the 30-second default. Zero, negative, fractional, null, string, and out-of-range values are rejected; there is no unlimited mode. The budget is a wall-clock limit for each tool call, including the wait for response headers. Progress notifications do not extend it. An earlier caller cancellation, turn deadline, or PTC deadline still wins. Timing out does not prove that a remote operation stopped or had no effect; Wuu does not replay a tool because it timed out.

This setting applies to native calls and calls nested in PTC. It is separate from connection and tool-discovery budgets. Use the same field in a trusted project .mcp.json server or a plugin’s mcpServers / mcp_servers declaration. A native preference entry containing only tool_timeout_ms (and optionally enabled or tool_overrides) overrides the budget of a same-named project server without replacing its definition. For a plugin server, use its qualified name, for example plugin.my-plugin.docs.

Restart after editing settings on disk. A newly loaded plugin generation or reconnection uses its loaded budget; calls retained by an older foreground generation keep that generation’s budget. The connection Refresh action does not reread configuration files.

Open Plugins to manage standalone MCP services. A plugin’s MCP services appear on that plugin’s detail page; a plugin requiring MCP authorization also shows a notice in the catalog. Disabling the plugin disables its services. Plugin and project definitions retain their original source and are not editable as standalone definitions.

Connection controls show state, tool count, and errors. For entries in MCP services, Disconnect ends only the current connection without deleting its definition or credentials. Refresh reconnects with the already-loaded configuration and discovers tools again. Edit changes the saved definition, including its startup preference. Remove deletes the standalone definition; a same-named project definition may become visible again. Removing a definition keeps its saved OAuth credentials; use Remove OAuth login first when you also want to sign out.

When a plugin-owned server and a manual configuration share a service name or endpoint, the catalog labels their sources separately; removing one does not disconnect the other. Removing a standalone definition does not wait for unrelated conversations. Once the removal is applied, retained connections reject new tool calls while accepted calls finish under their existing timeout. Other running Wuu hosts apply the change when they observe the saved configuration.

Restart Wuu after editing definitions on disk. Refresh is not a configuration-file reload. The older Settings MCP deep link remains available for compatibility; the main management entry is Plugins.

Tools receive model-visible names such as mcp_docs_search, with normalization for unsupported characters and long names. Large or infrequently used tool definitions can be deferred and found through tool search. The current tool surface and permission policy can still limit availability or execution.

For streamable HTTP servers, the optional GET notification stream follows the initialized session. Session expiry starts one shared recovery handshake even when several calls receive HTTP 404 together. A new session closes the old listener, clears its resume cursor, and starts listening after initialization completes. Queued notifications from obsolete sessions are discarded. HTTP 405 turns off GET listening only for that session.

With OAuth, a GET authentication failure refreshes credentials and retries once. A later successful POST credential refresh can restart the listener while preserving the same session’s resume cursor. Disconnecting cancels listening and any pending recovery. An unsuccessful recovery appears as a connection error; use Refresh after resolving the reported problem.

Recovery does not replay a tool because its response stream broke: the tool may already have taken effect. Wuu only retries requests explicitly rejected with HTTP 401 or a session-expiry HTTP 404, within the authentication and recovery limits. Other in-flight POST calls keep ownership of their own final responses.

Wuu reads Claude-style .mcp.json in the project configuration directory:

{
"mcpServers": {
"local-docs": {
"command": "node",
"args": ["/absolute/path/docs-server.js"],
"env": { "API_TOKEN": "${API_TOKEN}" }
}
}
}

Entries are not loaded by default. After reviewing the server, approve its name in your uncommitted .wuu/settings.local.json:

{
"mcp_json": { "enabled": ["local-docs"] }
}

enable_all: true enables all entries except those in disabled; explicit disabled names always win. Prefer individual names when only some servers are needed.

Unlike native definitions, .mcp.json expands ${VAR} and ${VAR:-default} in commands, arguments, environment values, URLs, and headers. Missing variables without a default remain literal and produce a warning. Supported types are stdio, http, and sse. A same-named native mcp_servers entry takes precedence.

Remote URL servers can use OAuth discovery, PKCE, scopes, and dynamic client registration. An ordinary definition does not need an oauth section in advance: after an authentication challenge, choose OAuth login on the service.

Desktop Wuu opens the authorization page and listens on an HTTP loopback callback. After authorization it saves credentials and connects automatically. The listener uses an available port unless the definition specifies a fixed loopback redirect URI. The callback validates the state and stays bound to the initiating window and app-server across workspace changes. Canceling, closing the login dialog, closing the window, or reaching the ten-minute limit closes the listener and invalidates the pending attempt.

Browser clients and services with a non-loopback callback use manual completion: paste the callback URL or authorization code into the dialog. Fixed clients must register the actual callback URI with their service. Tokens go to Wuu’s credential store rather than the server definition.

Saved credentials are bound to the resource URL used for login. Reusing a server name with a different URL requires another login; a path or query change also counts. Credentials from older versions without a saved resource URL require login again. Wuu keeps mismatched credentials until you explicitly replace or remove them. Logging in to the new resource replaces the credentials for that server name.

Logging out invalidates older login attempts and in-flight credential refreshes across Wuu processes. Their late responses cannot restore the removed credentials. Starting another login supersedes earlier login attempts for that server name; complete the newest authorization flow. Browser or token-exchange failures do not clear an existing credential. Signing in again after logout remains available.

Desktop MCP OAuth credentials remain in macOS Keychain or Linux Secret Service. Linux requires a running session D-Bus and an available, unlocked Secret Service keyring, such as GNOME Keyring. If the keyring is unavailable or access fails, Wuu reports the error and does not fall back to a credential file.

Owner-only lock files and credential-version records coordinate local access independently of project data directories; these files contain no tokens or client secrets. Keep these version records alongside your local Wuu state. Storage failures or a backend command that outlives a crashed Wuu process can make a credential unavailable and require another login; a stale or uncommitted credential is not accepted. All Wuu processes sharing credentials must use this version or newer for these guarantees.

Requests carrying OAuth credentials or configured headers cannot redirect across origins (scheme, host, or port). Legacy SSE message endpoints must share the stream’s origin; same-origin paths and session queries remain supported.

If the service requires a fixed client, callback, or scopes, add an oauth object to that server:

{
"redirect_uri": "http://127.0.0.1:8765/callback",
"client_id": "your-client-id",
"scopes": ["tools:read"]
}

Use the service’s actual registration values; a service may also require client_secret. Configured resource headers are not forwarded to a cross-origin authorization server.

A server definition can use tool_overrides to correct a tool’s read_only, concurrency_safe, or capability metadata, or attach a guidance usage contract that host-capability surfaces show to external engines when the tool is exposed to them. Only set these when you know the operation’s semantics. Mislabeling a write as a safe read can bypass protections that rely on those declarations.

If a server is absent, check configuration spelling, restart Wuu, and verify .mcp.json approval where applicable. For local connection errors, check executable discovery, dependencies, environment, and stdout discipline. For remote errors, check URL, transport, network, headers, and the server’s OAuth requirements.

A connected server with tools may still have deferred definitions; ask the agent to search for the required tool. Server descriptions and results are external content, not system instructions. Local MCP processes run trusted code with their inherited environment, and remote services receive the arguments sent to them. Review the security model before connecting an unfamiliar service.