Command Palette

Search for a command to run...

UnylyUnyly
Browse all

Mcpd

FreeNot checked

An MCP daemon for automated tool registration.

GitHubEmbed

About

An MCP daemon for automated tool registration.

README

A daemon that aggregates multiple MCP (Model Context Protocol) servers into one. Implements the MCP spec (2025-11-25).

Register any MCP server once with mcpd, then point your MCP client at mcpd. Add or remove servers at any time — agents discover new tools, resources, and prompts in realtime.

Installation

cargo install mcpd

or for local:

cargo install --path .

Usage

Register a server

mcpd register <name> <command> [args...]

Examples:

# Register a Node.js MCP server
mcpd register filesystem npx -y @anthropic/mcp-filesystem /home/user/documents

# Register a Python server
mcpd register mytools python -m my_mcp_server

# Register with environment variables
mcpd register api-tools node server.js -e API_KEY=sk-xxx -e DEBUG=1

List registered servers

mcpd list

Remove a server

mcpd unregister <name>

Run the daemon

mcpd serve

This starts mcpd in stdio mode, ready to accept MCP connections.

Client Configuration

Point your MCP client at mcpd instead of individual servers.

Claude Code (~/.claude/settings.json):

{
  "mcpServers": {
    "mcpd": {
      "command": "mcpd",
      "args": ["serve"]
    }
  }
}

Claude Desktop (claude_desktop_config.json):

{
  "mcpServers": {
    "mcpd": {
      "command": "mcpd",
      "args": ["serve"]
    }
  }
}

VSCode (Ctrl+Shift+P, search 'MCP', click 'MCP: Add Server', select 'stdio', type mcpd serve)

How It Works

mcpd aggregates all three MCP primitives — tools, resources, and prompts — from every registered backend into a single server.

Tools (dual-layer)

mcpd exposes exactly two meta-tools to the MCP client, regardless of how many backend servers are registered:

  • list_tools — Queries all registered backends and returns their tools (names, descriptions, input schemas).
  • use_tool — Invokes a backend tool by its fully-qualified name (server__tool) with the given arguments.

The agent naturally calls list_tools first (it's the only way to know what's available), then calls use_tool to invoke what it needs. You can register or unregister backends at any time — the agent just calls list_tools again to see the latest.

Resources

mcpd natively proxies resources/list and resources/read. Resources from all backends are aggregated and namespaced:

  • URIs are prefixed: mcpd://servername/original-uri
  • Names are prefixed: servername__resourcename

Backends that don't support resources are silently skipped.

Prompts

mcpd natively proxies prompts/list and prompts/get. Prompts from all backends are aggregated and namespaced:

  • Names are prefixed: servername__promptname

Backends that don't support prompts are silently skipped.

┌─────────────────┐
│   MCP Client    │
│ (Claude, etc.)  │
└────────┬────────┘
         │ tools, resources, prompts
         ▼
┌─────────────────┐
│      mcpd       │
└──┬─────┬─────┬──┘
   │     │     │ stdio (spawned on-demand)
   ▼     ▼     ▼
┌─────┐┌─────┐┌─────┐
│ srv1││ srv2││ srv3│
└─────┘└─────┘└─────┘

Workflow

  1. You register MCP servers with mcpd (stored in ~/.config/mcpd/registry.json)
  2. Your MCP client connects to mcpd and sees two meta-tools (list_tools, use_tool) plus aggregated resources and prompts
  3. Agent calls list_tools to discover available backend tools
  4. Agent calls use_tool(tool_name="server__tool", arguments={...}) to invoke them
  5. Client can also call resources/list, resources/read, prompts/list, prompts/get directly
  6. mcpd spawns backend servers on-demand and proxies the call

Example

After registering a filesystem server:

Agent calls: list_tools()
Returns:
  [{"name": "filesystem__read_file", "description": "Read a file", "input_schema": {...}},
   {"name": "filesystem__write_file", "description": "Write a file", "input_schema": {...}}]

Agent calls: use_tool(tool_name="filesystem__read_file", arguments={"path": "/tmp/hello.txt"})
Returns: contents of the file

Resources and prompts work via standard MCP methods:

Client calls: resources/list
Returns:
  [{"uri": "mcpd://myserver/file:///docs/readme.md", "name": "myserver__readme", ...}]

Client calls: resources/read(uri="mcpd://myserver/file:///docs/readme.md")
Returns: resource contents

Client calls: prompts/list
Returns:
  [{"name": "myserver__summarize", "description": "Summarize a document", ...}]

Client calls: prompts/get(name="myserver__summarize", arguments={"text": "..."})
Returns: prompt messages

Why mcpd?

  • Register once: Add servers to mcpd, not to every client
  • Full MCP proxy: Aggregates tools, resources, and prompts from all backends
  • Hot reload: Register/unregister servers while mcpd is running — the registry is re-read on every request, and clients are notified via list_changed notifications
  • Stable interface: Clients always see exactly two meta-tools, no matter how many backends exist
  • Namespace isolation: Tools, resources, and prompts from different servers can't collide (server__name format)
  • On-demand: Backend servers only spawn when actually needed
  • Graceful degradation: Backends that don't support resources or prompts are silently skipped

License

MIT

from github.com/xandwr/mcpd

Installing Mcpd

This server has no published package — it is built from source. Open the repository and follow its README.

▸ github.com/xandwr/mcpd

FAQ

Is Mcpd MCP free?

Yes, Mcpd MCP is free — one-click install via Unyly at no cost.

Does Mcpd need an API key?

No, Mcpd runs without API keys or environment variables.

Is Mcpd hosted or self-hosted?

Self-hosted: the server runs locally on your machine via the install command above.

How do I install Mcpd in Claude Desktop, Claude Code or Cursor?

Open Mcpd on unyly.org, pick your client tab (Claude Desktop, Claude Code, Cursor) and press Install — the config is generated automatically, no JSON editing.

Related MCPs

Compare Mcpd with

Not sure what to pick?

Find your stack in 60 seconds

Author?

Embed badge for your README

Browse similar

All development MCPs