Skip to main content
Glama
metaphorprojects

eidograph-mcpb

Eidograph MCP bundle

A .mcpb bundle that lets Claude Desktop drive the Eidograph desktop app.

Claude Desktop installs MCP bundles as stdio servers, and Eidograph speaks Streamable HTTP on a local port. server/index.js is the shim between them: it reads newline-delimited JSON-RPC on stdin, POSTs each message to the app's /mcp endpoint, and writes the reply back. Nothing leaves this machine.

Building

npm run validate          # schema-check manifest.json
npm run pack              # → eidograph.mcpb

Install the resulting file by opening it, or via Claude Desktop's Settings › Extensions › Install extension.

Related MCP server: Figma Console MCP Server

Finding the app

The port is a user setting, so the bundle is never told it. Instead the desktop app publishes a discovery file for as long as its listener is up, and removes it when the listener stops or the app quits:

Platform

Path

Windows

%LOCALAPPDATA%\eidograph.metaphor.projects\server.json

macOS

~/Library/Application Support/eidograph.metaphor.projects/server.json

Linux

$XDG_DATA_HOME/eidograph.metaphor.projects/server.json

{
  "version": "0.2.19",
  "pid": 24680,
  "updatedAt": 1757000000000,
  "bindAddress": "127.0.0.1",
  "port": 14159,
  "mcp": "http://127.0.0.1:14159/mcp",
  "api": "http://127.0.0.1:14159/api/v1",
  "token": "3f9c…",
  "lanAddresses": []
}

The published URLs always stay on loopback, even when the app is bound to 0.0.0.0 for LAN clients — every reader of this file is on the same machine. The exact path is shown, and can be copied, under Settings › MCP / REST server in the app.

The file is re-read on every request, so starting Eidograph, enabling its server, changing its port or rotating its token all take effect without reinstalling or restarting anything. Its absence simply means "not running": tools/list then returns an error naming the setting to turn on, and the bundle emits notifications/tools/list_changed once the app appears.

Authentication

Eidograph's server is unauthenticated by default and loopback-only. Turning on Settings › MCP / REST server › Require an access token generates a secret that every request must carry as Authorization: Bearer <token>; it is written to the discovery file (mode 0600 on Unix), so this bundle picks it up with no configuration.

Extension settings

All three are optional, and all three exist for cases the discovery file cannot cover — a listener it does not describe, or an app on another machine.

Setting

Environment variable

Effect

Endpoint override

EIDOGRAPH_ENDPOINT

Dial this address instead; the discovery file is not read at all. Accepts http://host:port or a full …/mcp URL.

Access token override

EIDOGRAPH_TOKEN

Send this token instead of the published one.

Discovery file override

EIDOGRAPH_DISCOVERY_FILE

Read the handshake from this path.

Notes on the bridge

Two things are deliberately not passed straight through:

  • initialize is answered locally. The extension therefore installs and stays healthy while Eidograph is closed, instead of failing its handshake and never retrying. The client's negotiated protocol version is echoed back; the app pins its own, which would strand a client that negotiated a different one.

  • No MCP-Protocol-Version header is forwarded. This shim terminates the client's transport, so the version negotiated there says nothing about the HTTP hop — and the app rejects any value but its own.

ping is also answered locally so a keepalive does not fail when the app is closed, and lifecycle notifications are dropped rather than forwarded: the app's endpoint is stateless and has nothing to update.

Tests live in tests/mcpbBundle.test.js and run with npm test; they exercise the discovery order on all three platforms and drive the bundle over real stdio against a stub of the app's endpoint.

License

MIT © Metaphor Projects. See LICENSE.

Related MCP Connectors

Related MCP Servers