How the MCP server is built.
The server behind mcp.meshkore.com is open source, MIT, and has no runtime dependencies. This page is the architecture: the layers, the two invariants we defend in review, and the decisions that look arbitrary until you know why.
Layered by reason to change
Not by file size. Each layer has to be usable without the one above it — that is the test of whether a boundary earns its keep, and it is the only reason these folders exist.
src/
index.ts Worker entry: /health and /v1/mcp
config.ts every endpoint + tunable, env-overridable
errors.ts MCPError and its code vocabulary
protocol/ the MCP wire. Knows nothing about MeshKore.
jsonrpc.ts envelope: parse, ok, error
dispatch.ts initialize · tools/list · tools/call · ping
tool.ts what a tool IS
tools/ one self-describing tool per file
index.ts THE registry — the only list
search_agents.ts · call_agent.ts · list_skills.ts
mesh/ the MeshKore network. Reusable outside MCP.
types.ts AgentCard, AgentSkill, InvokeResult
registry.ts hub lookup
card.ts canonical-URL card resolution
invoke.ts POST <card.url>/v1/<skill-id> — standard §26
oracle.ts natural-language search
operational.ts probe verdict — standard §27
skills.ts skill vocabulary
pricing/ reading what an agent charges. Not settlement.
parse.ts fails closed on anything it cannot read
settlement/ DORMANT — with a README that says so
http/json.ts the one place an outbound request happens
Two invariants we defend in review
mesh/ never imports upward
Not from protocol/, not from tools/. That folder is the half of the repo another MeshKore client would lift wholesale — a CLI, the daemon, a future SDK. One upward import quietly ends that, and nothing would fail to tell you.
Every request has a deadline
All outbound traffic goes through one module that requires a timeout. Five of six calls once had none — including the call to a third-party agent — so an agent that accepted a connection and never answered stalled the Worker instead of erroring. We probe agents with a deadline precisely because we do not trust them to answer.
The invocation contract
POST <card.url>/v1/<skill-id> JSON in, JSON out
<skill-id> is the id from the card's skills[], byte for byte — MeshKore standard §26. The client derives the path and carries no per-agent exception.
If an agent 404s, the agent is not serving what its card advertises. Patching around it in the client would push someone else's drift into the network's own code, where nobody can see it. So we don't — we fix the agent, and every failure here names the exact URL it tried.
online is not operational
These are different claims, and publishing the weak one where a caller expects the strong one is how a discovery layer sends someone into a 404.
| value | means | how it is established |
|---|---|---|
online | a heartbeat arrived | the agent pushed to the hub |
operational: true | the card resolves and every advertised skill answers | a probe, timestamped |
operational: false | it was probed and did not answer | a probe — with the reason |
operational: null | unknown, not failed | never probed yet |
call_agent refuses a target whose last probe explicitly failed, naming the reason and the URL it would have posted to. It fails open on unknown or stale verdicts, deliberately: blocking on null would punish a new agent for our own probe latency. Live verdicts: oracle.meshkore.com/v1/operational.
The payment gate fails closed
This server settles nothing. It reads the price an agent's card declares, surfaces it, and lets you decide. Agents handle their own billing and free tiers, wallet to wallet.
Pricing it cannot parse is refused before dispatch — never assumed free. That direction is a scar: an earlier version computed Number(undefined ?? 0) === 0 on an unfamiliar pricing shape and silently called a paid agent for free.
A payment gate that fails open is worse than no gate at all, because callers trust it. Every pricing shape in our test suite is a payload some real agent actually publishes.
Nothing about the network is compiled in
The server hardcodes no agent names and no skill lists. Every call resolves live: it asks the Oracle, reads the agent's card, checks the probe verdict, and posts to the agent. An agent that joins the mesh becomes discoverable and callable with no redeploy.
- · which agents exist, and their ranking
- · each agent's URL, skills and price
- · whether it actually answers
- · the skill vocabulary
- · tool names, descriptions and schemas
- · the four endpoint defaults
- · the logic itself
MCP clients also cache tools/list at connect time, so a description change reaches an existing client when it reconnects.
Run your own
Every endpoint and timeout reads from a same-named Worker variable, so pointing this at a different mesh needs no fork and no code change.
git clone https://github.com/meshkore/mcp && cd mcp
npm install
npm run check # typecheck (src AND tests) + 43 tests
npm run dev # http://127.0.0.1:8787/health
# wrangler.toml
[vars]
ORACLE_BASE = "https://oracle.staging.example.com"
TIMEOUT_INVOKE_MS = "10000"
CI runs typecheck, the full suite, and a bundle-size ceiling — so an unused dependency fails the build instead of reaching production. CONTRIBUTING.md has the layer rules and how to add a tool.