Loomal

Add x402 payments to your Node.js MCP server

Wrap the tools you want to charge for, leave the rest of the server alone. Agents pay in USDC before your handler runs — step by step.

You have a working Node.js MCP server and you want calls to cost money. The good news: monetizing it is a wrapping exercise, not a rewrite. Your tool handlers don't change — a payment layer in front of them returns HTTP 402 to unpaid requests, verifies the agent's USDC authorization, and only then lets execution proceed.

This guide takes you from a free remote server to a priced one in four steps: confirm the transport, choose what to charge, wrap the handlers, and verify the end-to-end flow.

Step 1 — confirm you're remote

Payment gating needs HTTP requests to gate, so the server must be running over Streamable HTTP at a public URL. Most Node MCP servers built on @modelcontextprotocol/sdk support both stdio and HTTP hosting; if yours is stdio-only, stand it up behind StreamableHTTPServerTransport in an Express (or similar) app first. You'll also need a wallet address to receive USDC — non-custodial, yours.

Step 2 — choose what to charge, and how much

Not every tool deserves a price. Charge the tools that do real work — the search, the conversion, the lookup with an upstream cost — and keep cheap utility tools free so agents can validate your server before spending. Discovery (initialize, tools/list) must always be free or clients can't even enumerate your tools.

Per-call prices start at $0.01. A sane opening move is to price near your marginal cost plus margin, then adjust; repricing later is a one-field change, not a migration.

Step 3 — wrap the handler

With the Loomal SDK, the gate is a higher-order function around the route serving your MCP endpoint. The wrapper issues the 402 with payment requirements, hands the retried request's X-PAYMENT header to the facilitator, and invokes your handler only after settlement clears on Base — about two seconds.

mcp-server.ts
import { requirePayment } from "@loomal/sdk";

const PRICED: Record<string, string> = {
  search_filings: "$0.05",
  extract_tables: "$0.02",
};

app.post("/mcp", (req, res, next) => {
  const tool = req.body?.method === "tools/call"
    ? req.body.params?.name : null;
  const price = tool && PRICED[tool];
  if (!price) return next(); // free tools + discovery
  return requirePayment({ price })(req, res, next);
}, mcpTransportHandler);

Step 4 — verify the flow end to end

Three checks before you announce anything. First, an unpaid tools/call to a priced tool returns 402 with an accepts array naming your price, USDC, and Base. Second, a paid retry executes the tool and returns the normal MCP result. Third, free tools and tools/list still respond with no payment header at all.

Every settled call comes back with an Ed25519-signed receipt — log it next to the request so your revenue records and your traffic logs reconcile exactly. There are no chargebacks to account for; a settled call stays settled.

Then make it discoverable

Agents won't find a priced endpoint by accident. Claim or create the server's listing on Loomal so the index serves your URL, tool list, and per-call prices to agents programmatically. The fee structure is simple: 5% on settled transactions, currently waived.

FAQ

Do my existing tool handlers need to change?

No. The payment check runs in middleware before the MCP transport handler sees the request. Your tool logic, schemas, and responses stay exactly as they are — the wrapper only controls whether the request reaches them.

What does the agent side need for this to work?

An x402-capable HTTP client and a funded wallet. When the agent's client sees your 402, it signs a USDC transfer authorization for the quoted amount and retries with the X-PAYMENT header automatically. There's no signup, key, or human step on their side.

Can I charge different prices per tool?

Yes, and you usually should. The middleware can read the tool name from the tools/call params and quote per-tool prices — cheap lookups at $0.01, expensive computations higher. One server, one endpoint, a price schedule.

Is there blockchain code anywhere in my server?

No. The facilitator verifies the payment signature and settles the transfer on Base; your Node process does HTTP and JSON. If you can write Express middleware, you have all the skills this integration needs.

Start accepting x402 payments.

Wrap your tools, set prices, and get paid per call in USDC.

Open the Loomal console