MCPorter: A TypeScript runtime and CLI for calling MCP servers without the ceremony
Call MCPs via TypeScript, masquerading as simple TypeScript API. Or package them as cli.
At a glance
- What is it?
- MCPorter wraps Model Context Protocol servers behind a TypeScript API and a CLI, with config import from other clients and a CLI generator. It suits developers and agents that want MCP tools in scripts, terminals, or standalone binaries.
- Who is it for?
- Adopt MCPorter if you write TypeScript scripts or agents that need direct, typed access to MCP tools, or if you want to generate a focused CLI from an MCP server. Skip it if you need a full MCP client with a GUI or if you rely on the `${env:VAR}` syntax that some clients use, since MCPorter rejects that form.
- Can I use it commercially?
- Yes. MIT is a permissive licence: you can use, modify and sell software built on it, as long as you keep its copyright and licence notices.
- Is it still maintained?
- Yes. The repository received new commits within the last day.
- What is it written in?
- Mainly TypeScript, according to GitHub's language statistics.
Answers come from the project's GitHub data, last synced on September 15, 2026, and from our analysis. They are not legal advice.
DEEP OPEN-SOURCE ANALYSIS
The problem: MCP tools are stuck in chat clients
Model Context Protocol servers expose tools, but most people interact with them through a chat client or an agent framework. If you want to call the same tool from a shell script, a Node script, or a generated CLI, you often need to write protocol-level code or wire up a separate client. MCPorter aims to remove that friction. It is a TypeScript runtime and a command-line tool that discovers and calls MCP servers. The README positions it for developers and coding agents that need the same MCP tools from a terminal, a script, or a standalone CLI. That is a specific niche: not a chat interface, not a server host, but a bridge that lets you treat MCP tools like ordinary functions.
How it works: runtime, proxy, and CLI
The core is a TypeScript runtime. You call `createRuntime()` with explicit server definitions, and it returns a runtime object that lets you list tools and call them. The README shows a minimal example: create a runtime with a server named `context7`, then `runtime.listTools('context7')` returns tool names. A `callOnce()` helper handles a single configured call and cleanup. There is also `createServerProxy()`, which maps MCP tool names to callable camelCase properties and wraps results with helpers for text, Markdown, JSON, image, and raw content. That proxy is the closest thing to "masquerading as a simple TypeScript API": you get a JavaScript object whose methods are the MCP tools. The CLI mirrors this. `mcporter list` prints tool signatures, `mcporter call` invokes a tool with named arguments. The CLI can also generate a focused CLI from a server via `mcporter generate-cli`, and emit TypeScript types or clients via `mcporter emit-ts`. So the same underlying discovery and calling logic powers both the runtime and the CLI.
Getting it running: install and first commands
The README gives three install paths. For a quick try without installing, run `npx mcporter --version`. For repeated command-line use, either `brew install steipete/tap/mcporter` or `npm install -g mcporter`. Node 24 or newer is required for npm installs. For the TypeScript runtime, you add `mcporter` to your project with your package manager. The quick start shows two commands. First, `npx mcporter list https://mcp.context7.com/mcp --brief` prints the server's TypeScript-style tool signatures. Second, `npx mcporter call https://mcp.context7.com/mcp.resolve-library-id query="React hooks docs" libraryName=react` calls a specific tool and returns matching IDs, without local config or credentials. That second command is notable: it demonstrates that you can call a remote MCP server directly by URL, no config file needed. For repeated use, you can define a server in `config/mcporter.json` with an `mcpServers` object, as shown with a single `url` field for the Context7 server.
Configuration and discovery: imports and environment placeholders
MCPorter reads project and user config, then imports MCP server definitions from Cursor, Claude Code and Desktop, Codex, Windsurf, OpenCode, and VS Code. That means if you already have MCP servers configured in one of those clients, MCPorter can pick them up. The config file accepts JSONC, environment placeholders like `${VAR}`, `${VAR:-fallback}`, or whole-value `$env:VAR`. There is a hard limitation here: the `${env:VAR}` form used by some MCP clients is not supported. The README says MCPorter rejects it with accepted alternatives instead of sending it literally. That is a deliberate fail-fast choice, but it means you cannot directly copy a config from a client that uses that syntax. The config also supports OAuth settings, tool filters, and lifecycle policy. Precedence and the full schema are documented in a separate guide, which is worth reading before you rely on imports.
Protocols and interactive requests: what works and what declines
MCPorter connects to stdio, Streamable HTTP, and legacy SSE servers. It negotiates the current `2026-07-28` protocol or a legacy revision per server, and legacy connections advertise client elicitation capabilities. Interactive CLI calls can answer form and URL requests. But headless and daemon-managed calls decline those requests with an actionable hint. That is a real limitation: if an MCP tool requires interactive input, you cannot use it in a script or a daemon. The README mentions a keep-alive daemon that pools servers and provides an MCP bridge, plus Chrome DevTools integration through an OpenClaw extension relay. The relay uses Browser Relay Authentication v2 over a retained loopback socket, keeps the host key out of the network, and gives `chrome-devtools-mcp` a credential-free loopback URL. If you need to drive Chrome via MCP, that path is specific and involved, not a generic feature.
Maintenance and upgrade cost
The repository shows active development: the latest release is v0.13.8 from 2026-08-28, with v0.13.7 and v0.13.6 from the same month. The v0.13.6 release note mentions "Relay-aware daemon startup", which suggests ongoing refinement of the daemon and relay features. The project is not archived. The README lists development commands: `pnpm install --frozen-lockfile`, `pnpm check`, `pnpm test`, and `pnpm docs:site`. It uses the Node and pnpm versions declared in `package.json`. Live hosted-server tests are opt-in, which means the default test suite does not hit external servers. That is a maintenance consideration: you may need to run live tests yourself to verify compatibility with a specific MCP server. The license is MIT, which is permissive, but you should read the LICENSE file if you plan to redistribute or modify.
Alternatives and when MCPorter is the wrong tool
The obvious alternative is writing your own MCP client using the official SDK, or using a framework like the Model Context Protocol TypeScript SDK directly. That gives you full control over protocol negotiation and interactive handling, but you have to write more code. Another alternative is to stay inside an existing client like Claude Code or Cursor, which already imports MCP servers and handles interactive requests. Those clients do not give you a scriptable API or a way to generate a standalone CLI. MCPorter sits in between: it is lighter than a full client but more structured than raw SDK calls. It is the wrong tool if you need interactive request handling in a headless context, because headless calls decline form and URL requests. It is also wrong if you cannot upgrade to Node 24, since npm installs require it. If you only need to call one tool once from a shell, the `npx` one-liner works, but for anything more complex you need the runtime or config.
What to verify before adopting
Before you commit to MCPorter, check three things against your actual MCP servers. First, confirm your Node version is 24 or newer if you plan to install via npm; the README states that requirement explicitly. Second, test whether your servers use the `${env:VAR}` environment syntax in their config, because MCPorter rejects that form. You will need to convert to `${VAR}` or `$env:VAR`. Third, if you rely on interactive tool calls, verify whether the CLI's interactive mode covers your use case, because headless and daemon calls decline those requests. The README points to a five-minute quickstart and a CLI reference for the full flag list. The project's own test suite covers stdio and Streamable HTTP over fixture servers, but live tests are opt-in, so run those if you need confidence against a specific hosted server.
Editorial conclusion
Adopt MCPorter if you write TypeScript scripts or agents that need direct, typed access to MCP tools, or if you want to generate a focused CLI from an MCP server. Skip it if you need a full MCP client with a GUI or if you rely on the `${env:VAR}` syntax that some clients use, since MCPorter rejects that form. Before adopting, verify that your Node version is 24 or newer if you install via npm, and test your target MCP servers against the current protocol negotiation, especially legacy SSE or interactive form requests that headless calls decline.
Community notes