Create a custom MCP
A VibeKit MCP deployment is configuration: select tools, optional plugins,
networks, and a signing mode, then pass that deployment to a transport adapter.
Copy the executable examples in packages/vibekit/examples/ when starting a
real server. Everything ships as one package — bun add @initlabs/vibekit@alpha
— with subpath exports: . is the core contract, and ./tools, ./preset,
./mcp/stdio, ./mcp/http, ./signer-keystore, and ./plugins/<name> are
the rest.
Start with a focused stdio server
Section titled “Start with a focused stdio server”This server exposes only account and network reads on TestNet. Stdio is the normal local-agent transport.
import { serveMcpStdio } from '@initlabs/vibekit/mcp/stdio'import { accountQueries, networkQueries } from '@initlabs/vibekit/tools'
const handle = serveMcpStdio({ name: 'my-vibekit-mcp', network: 'testnet', mode: 'compose', tools: [...networkQueries, ...accountQueries],})
process.on('SIGINT', () => void handle.close())For the full stock tool surface, import defaultTools and defaultPlugins()
from @initlabs/vibekit/preset. Keep that selection in one plain factory if
more than one entry point needs it.
Choose compose before execute
Section titled “Choose compose before execute”Use compose unless the deployment owns a signer and a real approval boundary.
Compose mode returns unsigned transaction groups for an external signer to
review. It is the correct default for a new server and for public HTTP use.
The bundled vibekit mcp server is the exception: it defaults to execute
behind the local keystore daemon and degrades to compose when the daemon is
unreachable.
execute requires resolveSigner; startup rejects an execute deployment
without it. A local stdio deployment can use the VibeKit keystore pattern from
packages/vibekit/examples/stdio.ts. Do not put a signer behind an unauthenticated
HTTP endpoint.
Add a plugin
Section titled “Add a plugin”Instantiate plugins through the deployment rather than copying their tools:
import { nfdPlugin } from '@initlabs/vibekit/plugins/nfd'
const handle = serveMcpStdio({ name: 'my-vibekit-mcp', network: 'testnet', mode: 'compose', tools: [...networkQueries, ...accountQueries], plugins: [nfdPlugin()],})VibeKit validates duplicate plugin names and duplicate tool names when the
deployment starts. With multiple networks, it injects a network parameter
into every tool and requires it on writes.
HTTP is an adapter, not another architecture
Section titled “HTTP is an adapter, not another architecture”Use createMcpHttpHandler from @initlabs/vibekit/mcp/http when your own
application needs a stateless Streamable HTTP handler. The handler creates a
fresh MCP server per request; it does not retain client sessions. Bring your
own authentication, origin policy, and deployment model. The
MCP server documentation
covers those generic hosting concerns.