How TUUI Manages Remote MCP Servers with Cloudflare mcp-remote Integration
TUUI treats every MCP server as a client-side API object exposed through the preload bridge (window.mcpServers), using the Cloudflare mcp-remote package to establish SSE tunnels for remote connectivity.
The ai-ql/tuui repository implements a unified architecture where remote Model Context Protocol (MCP) servers are configured via JSON and proxied through Cloudflare's mcp-remote helper. This design allows the renderer process to interact with remote hosts without direct network access, abstracting all transport complexity behind a consistent JavaScript API.
Configuration Architecture
Remote MCP servers are defined in src/main/assets/config/mcp.json using a command-based configuration pattern. The MCP launcher reads these definitions and initializes the mcp-remote process to establish connectivity.
{
"mcpServers": {
"cloudflare": {
"command": "npx",
"args": ["-y", "mcp-remote", "https://YOURDOMAIN.com/sse"]
}
}
}
- The
commandandargsarray specify thatnpxshould execute themcp-remotepackage. - The MCP config loader (
src/main/mcp/config.ts) parses this configuration and spawns the process. mcp-remoteopens a Server-Sent Events (SSE) tunnel to the Cloudflare worker endpoint, proxying all subsequent MCP calls (tools, prompts, resources) through that secure channel.
The main process automatically watches mcp.json for changes using fs.watch and reloads the configuration dynamically without requiring an application restart.
Loading and Exposing Remote Servers
The integration relies on a preload bridge pattern to safely expose remote server capabilities to the renderer process.
In the main process, loadConfigFile (defined in src/main/mcp/config.ts) parses the JSON configuration and returns a map of McpServerConfig objects. The preload script (src/preload/index.ts) then constructs the window.mcpServers API by:
- Calling
listClientsvia IPC to retrieve locally-run MCP servers. - Merging these with the remote definitions from the configuration.
- Exposing the unified list through
window.mcpServers.get().
This approach ensures that remote servers appear as first-class citizens alongside local stdio-based servers, with both accessible through the same interface.
Store Integration and UI Consumption
The renderer-side state management handles server discovery and method invocation through src/renderer/store/mcp.ts.
getRawServers()retrieves the raw configuration object fromwindow.mcpServers?.get().getServers()merges remote definitions with any local stdio servers, returning the final map used by UI components.- Components like McpSideDrawer and the Prompt store consume this map to list available primitives and invoke remote methods.
When users select a remote server in the interface, useMcpStore persists the selection and makes the server's methods available for subsequent calls.
Remote Call Flow
When the UI initiates an MCP operation against a remote server, the request flows through several abstraction layers:
- Selection: The user chooses a remote server (e.g., "cloudflare") via the UI, stored in
useMcpStore. - Method Resolution:
getServerFunctionlocates the appropriate method (e.g.,prompts.list) on the server object. - Transport: The method execution is delegated to the
mcp-remoteprocess, which serializes the JSON-RPC request and transmits it over the Cloudflare SSE channel. - Response Handling: The remote worker's response returns through the same tunnel, is parsed by
mcp-remote, and passed back to the renderer as a standard JavaScript object.
Because all transport logic is encapsulated behind the MCPAPI interface, UI components remain agnostic to whether they are calling a local CLI tool or a remote Cloudflare worker.
Code Examples
Adding a Cloudflare Remote Server
Edit src/main/assets/config/mcp.json to include the remote endpoint:
{
"mcpServers": {
"cloudflare": {
"command": "npx",
"args": ["-y", "mcp-remote", "https://example.com/sse"]
}
}
}
The main process detects the file change automatically and reloads the server list.
Listing Primitives from a Remote Server
Access remote prompts or tools through the MCP store:
import { useMcpStore } from '@/renderer/store/mcp'
async function listRemotePrompts() {
const mcpStore = useMcpStore()
// Ensure the server list is current
await mcpStore.updateServers?.()
// Access the remote server by its configuration key
const server = mcpStore.getServers?.()['cloudflare']
if (!server) throw new Error('Remote server not found')
// Invoke the prompts.list primitive
const prompts = await server.prompts?.list({ method: 'prompts/list' })
console.log(prompts)
}
The call traverses the Cloudflare SSE tunnel managed by the mcp-remote process.
Refreshing the Server List
Trigger a configuration reload after manual edits:
await window.mcpServers?.refresh()
This invokes the preload script's refreshAPI function, which re-queries the main process for updated client lists and remote definitions.
Summary
- Configuration-driven: Remote servers are defined in
src/main/assets/config/mcp.jsonusingnpx mcp-remotecommands. - Unified API: The preload bridge (
src/preload/index.ts) exposes all servers throughwindow.mcpServers, hiding transport differences. - SSE Tunneling: Cloudflare's
mcp-remoteestablishes Server-Sent Events connections, proxying JSON-RPC traffic securely. - Dynamic Reloading: File watchers in
src/main/mcp/config.tsenable hot-reloading of server configurations without app restarts. - Store Abstraction:
src/renderer/store/mcp.tsmerges remote and local servers, providing a consistent interface for UI components.
Frequently Asked Questions
How does TUUI handle authentication for remote MCP servers?
TUUI delegates authentication to the mcp-remote process. Since mcp-remote manages the SSE connection to the Cloudflare worker, any authentication tokens or headers are handled at the Cloudflare layer or within the mcp-remote package configuration, keeping the TUUI renderer process unburdened by credential management.
Can TUUI mix local stdio servers with remote Cloudflare servers simultaneously?
Yes. The getServers() method in src/renderer/store/mcp.ts specifically merges remote definitions from window.mcpServers.get() with local stdio-based clients, allowing UI components to interact with both types through identical APIs without distinguishing between transport mechanisms.
What happens if the Cloudflare SSE connection drops?
The mcp-remote process manages connection lifecycle and reconnection logic. From TUUI's perspective, if the remote server becomes unreachable, the corresponding methods will throw errors that can be caught by the store or UI components, while the application continues functioning with other available servers.
Where is the server configuration cached in TUUI?
The raw configuration is read from src/main/assets/config/mcp.json by loadConfigFile in src/main/mcp/config.ts, but it is not persistently cached in the renderer. Each call to window.mcpServers.get() or refresh() retrieves the current state from the main process, ensuring the UI always reflects the latest configuration file contents.
Have a question about this repo?
These articles cover the highlights, but your codebase questions are specific. Give your agent direct access to the source. Share this with your agent to get started:
curl -s "https://instagit.com/install.md" Maintain an open-source project? Get it listed too →