MCP setup

Connect your AI assistant to GenesisPay

@genesis-tech/genesispay-mcp is a stdio MCP server that exposes GenesisPay discovery and payment tools to any MCP client. Your assistant pays within the limits you set in the dashboard — over-limit payments come back as an approval link for you, never as silent spending. Web chats that cannot run a local server connect to a hosted endpoint instead — see Connect a web chat.

Beta: x402 pay-per-use — what the payment tools below do — is unaffected. Creating new mandate authority is locked, so a new mandate, subscription or mandate-backed purchase answers 409 mandate_authority_locked_for_beta. Mandates your owner already approved keep paying and can still be revoked.

Purchase intent (SDK and MCP 2.0.0)

Agent SDK 2.0.0 and MCP 2.0.0 can send a structured purchase intent: the item, the most the user agreed to pay including fees, the user's exact approval sentence and a fingerprint of the visible purchase turns. The conversation itself never reaches the payment API — local MCP 2.0 hashes it on your machine. The SDK requires an explicit intent or null. Once GenesisPay requires intent, a new purchase without one is refused with 422 purchase_intent_required before anything is charged; until then, sending one already holds the purchase to it. Keep the same intent and key on retries.

Prerequisites

Setup requires a GenesisPay deployment that serves /api/v2/agent/pay and MCP server version 1.0 or later.

Follow the agent quickstart first: log in, create an agent account, fund it, set limits, and export a gp_ag_ API key. Both env vars below are required — GENESISPAY_BASE_URL is the GenesisPay deployment your account lives on. It must be https; plain http is accepted only for localhost and 127.0.0.1, so the agent key is never sent in cleartext (MCP server 1.9.0 refuses anything else at start).

Codex

Terminal
codex mcp add genesispay \
  --env GENESISPAY_AGENT_KEY=gp_ag_your_agent_key \
  --env GENESISPAY_BASE_URL=https://your-genesispay-host \
  -- npx -y @genesis-tech/[email protected]

Claude Code

Terminal
claude mcp add genesispay \
  --env GENESISPAY_AGENT_KEY=gp_ag_your_agent_key \
  --env GENESISPAY_BASE_URL=https://your-genesispay-host \
  -- npx -y @genesis-tech/[email protected]

Claude Desktop

claude_desktop_config.json
{
  "mcpServers": {
    "genesispay": {
      "command": "npx",
      "args": ["-y", "@genesis-tech/[email protected]"],
      "env": {
        "GENESISPAY_AGENT_KEY": "gp_ag_your_agent_key",
        "GENESISPAY_BASE_URL": "https://your-genesispay-host"
      }
    }
  }
}

Restart Claude Desktop after editing the config.

Connect a web chat (remote MCP)

Available in Claude and ChatGPT. Web chats such as Claude.ai and ChatGPT cannot run the stdio server above, so GenesisPay hosts the same tools itself and the chat connects with OAuth: no package to install and no key to copy. A deployment that has not enabled remote MCP offers a starter prompt in the dashboard instead of a connector URL.

Add GenesisPay as a custom (remote MCP) connector in your chat's connector settings, using this URL:

Connector URL
https://<your GenesisPay origin>/mcp

You do not have to assemble it yourself: when remote MCP is available, the Connect an assistant panel on your agent in the dashboard shows the exact URL with a copy button, the steps for your chat and a link to its connector settings where one is known. After the steps, Try it buttons open a new chat with a first message such as “Show my GenesisPay account”. A link can only start a chat: it cannot add the connector for you, so those buttons work once the steps are done.

When you connect, the chat sends you to GenesisPay. Sign in (a recent sign-in is required, so you may be asked again), pick the agent the app should use, and approve. The screen marks the app Unverified app and shows the host it will send you back to — check that it is the chat you started from. You can revoke a connection at any time under your agent's Connected apps tab; revoking also denies its payments still waiting for approval.

The app can

  • Search shops and products
  • Pay up to your limits from the chosen agent's wallet
  • See that agent's balance, limits and payment status
  • Read and update your saved shipping address and quote physical products to it — you are emailed about every change

It cannot

  • Change limits or the allowlist
  • Approve its own over-limit payments — those wait for you in the dashboard
  • Confirm a new shipping address — its first order waits for your approval in the dashboard
  • Create keys
  • Touch your personal wallet or your other agents

A connection never widens what the agent may spend. The agent's limits and allowlist apply exactly as they do to an API key: a payment over a limit comes back as an approval link and waits for you in the dashboard, and a shop outside the allowlist is a hard block (policy_blocked). Give each chat its own agent to keep separate limits and switch one off alone. The chat provider sees the agent's wallet address, balance, limits and purchase outcomes.

With MCP server 1.6.0 and the hosted connector, chats that support MCP Apps (such as Claude and ChatGPT) show physical products and quotes as an inline product card: the picture, title, shop, listed price or the quoted totals and the delivery address. The card is display only. It has no buttons, loads nothing from the internet and cannot call any tool; you still confirm the address and total in the chat before anything is bought.

For client developers

The hosted endpoint is an OAuth 2.1 protected resource and accepts only OAuth access tokens. A static gp_ag_ agent key is refused at /mcp with 401 invalid_token; keys are for the stdio server and the agent SDK.

Discovery
An unauthenticated call to /mcp answers 401 with a WWW-Authenticate header pointing at the RFC 9728 protected-resource metadata (/.well-known/oauth-protected-resource/mcp), which names the RFC 8414 authorization-server metadata (/.well-known/oauth-authorization-server). Endpoints: /oauth/authorize, /api/oauth/token, /api/oauth/register and /api/oauth/revoke (RFC 7009).
Registration
Clients may register dynamically (DCR, RFC 7591) or via a client ID metadata document. During beta, redirect URIs must be on an allowlist of the supported chat hosts (claude.ai, chatgpt.com) plus loopback; any other host is refused, including hosted MCP gateways, unless the deployment's operator has added one.
Flow
Authorization code with PKCE, S256 only, and exact redirect_uri matching. The authorization response carries iss (RFC 9207).
Resource and scope
Send the resource indicator (RFC 8707) https://<your GenesisPay origin>/mcp; a grant is bound to it and refused anywhere else. The MCP authentication challenge requests genesispay.agent genesispay.reviews.write; the connection screen explicitly discloses review permission. OAuth requests that omit scope still default to genesispay.agent. Review writes from a base-only connection return HTTP 403 insufficient_scope with the required scope so the host can request fresh consent. Existing connections keep their current permissions; refresh cannot add review rights.
Lifetimes
Access tokens (gp_oat_) last 15 minutes. Refresh tokens (gp_ort_) rotate on every use and expire after 30 days unused; reusing an old refresh token or code revokes the whole connection. A connection lasts at most 90 days, then the user approves again.
Transport
POST /mcp only: MCP Streamable HTTP, stateless, JSON responses. Send Accept: application/json, text/event-stream.
Server card
GET /.well-known/mcp/server-card.json lists the server, its transport, the OAuth requirement and every tool with its input schema and annotations, without a token, for directories and scanners. It is generated from the same server /mcp runs.

Catalog connector (browse only)

A second hosted endpoint lets a chat search the GenesisPay catalog without being able to buy anything. It needs no login and no account, and it is the connector listed in assistant directories that do not accept connectors which move money.

Catalog connector URL
https://<your GenesisPay origin>/mcp/catalog

On genesispay.finance that is https://genesispay.finance/mcp/catalog. It has four read-only tools:

genesispay_catalog_search
Search products and services: keywords, physical or digital, a shop or a category.
genesispay_catalog_shops
Find shops, with their product count and rating.
genesispay_catalog_trending
What sells now, or what is newly listed.
genesispay_catalog_reviews
Published reviews from verified purchases of a product or service.

Every result links to its page on GenesisPay, where you buy with a GenesisPay account. The catalog connector has no payment tool, no payment links and no access to any account. Physical goods show the shop's listed price; shipping and tax are set at checkout.

In chats that show MCP Apps, search and trending results can also show a small display-only card with product pictures, titles, shops and listed prices. The card has no links or buttons.

Example prompts, once the catalog connector is added to your chat:

“Find an API on GenesisPay that can search the web.”
Matching services and products with a short description, price, shop and rating, each linking to its GenesisPay page.
“What is trending on GenesisPay right now?”
Up to 10 products ranked by recent buyers, or newest listings when there are too few sales, each with price, shop and link.
“Which shops sell on GenesisPay, and how are they rated? Show me the products of the first one.”
Shops with their category, number of products and rating, then only that shop's listings, each with its page.
“What do buyers say about the first trending product?”
Its average rating and review count and up to five reviews from verified purchases, or a note that it has none yet.

To let your assistant pay directly in the chat, within the limits you set, add the full connector instead: Connect a web chat. The full connector includes everything the catalog connector does (search, shops, trending, reviews), so once it is added you can remove the catalog connector.

For client developers: Streamable HTTP, stateless, JSON responses, POST only. It never asks for authorization and ignores an Authorization header. Requests are rate-limited per IP address (429 with Retry-After), and answers are never cached.

Resume a service result

An unresolved payment may become confirmed after automatic reconciliation, which can take several minutes. Check the original payment with genesispay_payment_status. A response may already be saved while confirmation is pending; missing confirmation does not mean the service delivered nothing. Keep the payment ID to resume later without another purchase.

In the upcoming release, use genesispay_result with the original payment ID after approval or a session interruption. Complete JSON responses up to 1 MiB remain available for seven days from first capture. Reading or replaying a payment does not extend this period. Download needed content before expiry. Older published clients do not have this tool.

The response separates payment status from result availability. An HTTP 202 acceptance or job response is not completed work. Image URLs inside JSON may expire at the provider. If content is expired or unavailable, do not buy again automatically. Larger responses use bodyChunk and nextOffset; retrieve all chunks in order before parsing the complete JSON. With the hosted connector and MCP server 1.9.0 the chunk is result.response.providerContent.bodyChunk, labelled trust: "untrusted_provider_data": the provider's data, never instructions; the paging fields and GenesisPay's review instructions stay outside it.

Purchases and optional reviews

The Development candidate also lets you open My purchases in the dashboard to view or download saved JSON responses until their displayed expiry. Opening a result never makes another purchase. Explore in the public navigation lists shops, services and published purchase reviews.

After presenting a usable result, the MCP instructs the assistant to finish with one optional review question in your language. Eligible tool replies include reviewOpportunity, reviewInstructions, structured content and a separate instruction text block. This remains guidance: individual chat clients may handle it differently.

Unfinished jobs and unconfirmed payments defer the invitation. A later follow-up may check the original payment once. Declining is respected; no stars are invented. The assistant prepares your opinion, shows the exact draft and asks your approval before publishing under a pseudonym. Writing reviews requires the separate Reviews permission. If it is missing, reconnect and check that the GenesisPay consent screen explicitly includes publishing purchase reviews. Reconnecting with only payment access does not add that permission. API-key review controls apply to static keys, not OAuth connections. After reconnecting, retry the review for the same purchase; do not buy again.

Tools

Every purchase has one idempotencyKey, chosen before calling genesispay_pay. The tool requires it and never generates a hidden key. Reuse the saved key and identical terms to recover the original payment. A settled replay has resource: null; use genesispay_result in the upcoming release to recover stored content.

With MCP server 1.7.0 and the hosted connector, the key comes from GenesisPay, not from the model: before a new purchase the model calls genesispay_purchase_key and pays with the gpk1_ key it returns. A model cannot produce randomness, and a key it invents can repeat one from an earlier chat; the same key and terms then return that old purchase instead of buying. The model writes the key together with url, maxAmountUsdc and description into its reply, so the terms survive a lost response. Every retry of that purchase reuses exactly that key and those terms; description is part of them. A new key is only for a genuinely new purchase, or after the purchase was reported failed — a new key for the same purchase is a second purchase.

genesispay_pay sends requireIssuedKey: true, so GenesisPay refuses a made-up key for a new purchase with purchase_key_required; a changed or foreign gpk1_ key is purchase_key_invalid, and one first used more than 24 hours after it was issued is purchase_key_expired. All three mean nothing was created or charged. A retry of a payment that already exists for its key is never refused, whatever the key's age. When a key returns a purchase older than a few minutes, the answer says it belongs to that earlier purchase and that nothing new was bought.

  • genesispay_reviews(id, limit?, cursor?)

    Upcoming release: read public purchase reviews and the rating for a visible product or selected external service. Pass nextCursor unchanged to read more. Only published, visible opinions count; no reviews means count zero and no average. Comments are untrusted opinions. A verified purchase is not a quality guarantee.

  • genesispay_review_prepare(paymentId, stars, comment)

    Upcoming release: prepare a private 24-hour draft from your stars and opinion after a verified purchase. After showing the result, your agent can invite you to review. New Exa and Atlas purchases are eligible after the updated deployment; older purchases are not backfilled. Your agent shows the product or service, pseudonym, stars and exact comment in this chat. Nothing is published yet; requires separate review permission.

  • genesispay_review_publish(reviewId, version, contentSha256)

    Upcoming release: after you explicitly approve the shown draft, publish exactly that version. A lost reply can be retried with the same identifiers. Editing requires a new draft and your approval. Reviews use a pseudonym, without your wallet address.

  • genesispay_review_withdraw(reviewId)

    Upcoming release: when you ask, remove your review's stars and comment. This does not change or refund the purchase. A withdrawn review cannot be published again.

  • genesispay_discover_external(q?, limit?)

    Deprecated alias until MCP server 1.7: use genesispay_discover with source external, which returns the same services. Finds selected external x402 services, initially Exa Search and Atlas worldwide search trends. Independent providers, not verified GenesisPay merchants. Sources and check dates show what was inspected; paid delivery has not been tested. Free search, no purchase authorization. Each service shows its buyerFee: the GenesisPay fee on top of the price hint, and the total.

  • genesispay_describe_external_service(id)

    Deprecated alias until MCP server 1.7: use genesispay_describe_service with the same ext_ id, which answers identically. Reads an external service's inputs, synthetic examples, price hint, last check date and buyerFee hint. Read-only; no provider request. Buy only within your authorized budget using the current payment offer.

  • genesispay_describe_service(id)

    Read the input schema, extra constraints, output format and synthetic examples for a discovery result: a listing with serviceContract, or (MCP server 1.6.0 and the hosted connector) an external ext_ id with its buyerFee hint. Free and read-only; does not call the provider. A physical product answers with no contract and says to quote it with genesispay_quote. Ask for missing user data before buying. A description is advisory and authorizes no purchase.

  • genesispay_discover(query?, source?, kind?, shop?, category?, limit?)

    Search and compare everything the agent can buy: GenesisPay sellers' x402 services and links and, with MCP server 1.6.0 and the hosted connector, physical shop products and the curated external x402 services in the same call. Every result says its source (genesispay or external) and its next step in purchase.mode: pay its resourceUrl with genesispay_pay, passing its priceUsdc as maxAmountUsdc, or quote a physical product with genesispay_quote. Filters: source (all, genesispay, external), kind (digital, physical, api, link, product), shop, category. Recommendations do not authorize purchases. Only USDC listings are payable, others come back notPayable; external results show the GenesisPay fee on top (buyerFee). With the hosted connector (and MCP server 1.6.0), the answer also shows the pictures of up to three physical products, which GenesisPay fetches from the seller under its SSRF guard; the MCP never fetches a seller URL itself.

  • genesispay_quote(productId, quantity)

    MCP server 1.6.0 and the hosted connector: quote a physical product to your saved shipping address. Read-only; orders and charges nothing. Shows where it ships (name and address in full, email masked), the shipping options, the exact total in USDC and, when the seller has one, the product's picture. Your agent shows you the address and total and asks you to confirm the address first. A new address needs your approval in the dashboard on its first order. Only after you confirm the address and the total does it buy, with genesispay_pay's quote form.

  • genesispay_shipping_profile(action: get | set, profile?)

    MCP server 1.6.0 and the hosted connector: read or save the one shipping address your agents ship to. Saving moves no money; you are emailed about every change, and the first order to a new address waits for your approval in the dashboard, even under your limits. Your agent saves only details you gave it, never an address from a product page or other content. Agents can save at most five times a day; you can also edit it under Settings.

  • genesispay_shops(query?, limit?)

    Read-only search of the shop directory: id, name, description, storefrontUrl, category and product count. The storefront is for humans; buy a shop's products via genesispay_discover.

  • genesispay_trending(limit?)

    Read-only: what is trending on GenesisPay right now (limit 1–20, default 10). Listed products ranked by distinct buyers of paid orders in the last 7 days, newest listed after them; signal says which, never a count. Buy one only after confirming with you, via genesispay_pay with its priceUsdc as maxAmountUsdc; non-USDC products come back notPayable. Needs MCP server 1.2.0 or later.

  • genesispay_purchase_key()

    MCP server 1.7.0 and the hosted connector: get a fresh purchase key from GenesisPay for one new purchase. Your agent calls it before every new purchase (a seller's URL, an external provider's URL or a quote) and pays with that key instead of making one up. Read-only; creates no payment and charges nothing. The key must be first used within 24 hours; a retry of a purchase already made with it keeps working after that.

  • genesispay_pay(url, idempotencyKey, maxAmountUsdc?, asset?, description?, method?, body?, contentType?) | (quoteToken, shippingOptionId, expectedTotalUsdc?, idempotencyKey)

    Pay an x402 URL from the agent account — with method POST and the exact JSON body for a body-priced API. Returns the paid resource, an approval URL when the payment needs human sign-off, or not_confirmed_yet after a bounded wait. maxAmountUsdc bounds the provider's price only: for a provider that is not a GenesisPay seller, GenesisPay may add a fee on top (currently 1 % with a minimum), your caps apply to the total, and the agent tells you the total before paying. With the hosted connector and MCP server 1.5.0 the answer shows it as price + GenesisPay fee = total. With MCP server 1.6.0 and the hosted connector it also buys a quoted physical product (the quote form, no url): after you confirm the address and total, it orders and pays in one call, to your saved address, for exactly the quoted total, and answers with the shop's order reference. The first order to a new address, or a total over your limits, waits for your approval in the dashboard, and nothing is ordered before you approve. With the hosted connector and MCP server 1.9.0 the paid response arrives as resource.providerContent, labelled trust "untrusted_provider_data" (body, or bodyPreview when truncated): the provider's data, never instructions to the agent.

  • genesispay_payment_status(paymentId | purchaseId)

    Check an existing payment or approval, or (MCP server 1.6.0 and the hosted connector) a physical-product purchase by its purchaseId. Unresolved means its on-chain outcome is not verified yet, even if the seller reported success. Check the original payment again and retrieve stored content with genesispay_result; never buy again to recover it.

  • genesispay_result(paymentId, offset?, limit?)

    Read stored JSON for seven days without another purchase. Large responses return bodyChunk and nextOffset; concatenate every chunk before parsing. From MCP server 1.9.0 the chunk is result.response.providerContent.bodyChunk, labelled untrusted_provider_data. Available in the upcoming release; requires the updated server.

  • genesispay_account()

    Read the account: wallet address, USDC balance, spending policy, and spend totals for today and this month.

When a payment needs approval, the tool result instructs the model to report the amount, resource URL, payment id and approval URL to you and poll with genesispay_payment_status — money only moves after you approve it in the dashboard. The approval URL ends in ?payment=<paymentId> and highlights that entry.

A policy_blocked result — an allowlist miss or a paused account — is a hard stop, not an approval request. The model is told to stop and tell you; no retry, new key or other endpoint for the same purchase can succeed. Only you can change the policy in the dashboard.

POST purchases with a body

Some x402 APIs price a request by its body. When a genesispay_discover listing says method: POST, the model passes method and the exact JSON text the API expects as body (at most 256 KiB; contentType is application/json, the default and only value):

genesispay_pay arguments
{
  "url": "https://api.example.com/v1/forecast",
  "idempotencyKey": "forecast-20260924-k7f2qa",
  "maxAmountUsdc": "0.05",
  "method": "POST",
  "body": "{\"horizon\":\"7d\",\"city\":\"Zurich\"}"
}

The body is part of the purchase: GenesisPay sends it byte-for-byte and never re-serializes it. Every retry with the same key must carry the byte-identical body; a different or reformatted body with the same key ends in idempotency_conflict. Keep secrets and personal data out of it — it is stored with the payment. POST purchases need a deployment that confirms them (its answer echoes requestMethod and bodySha256); against an older one the result is an unknown outcome, never a success.

Not confirmed yet

A payment can be accepted before it is confirmed on-chain. genesispay_pay then waits up to 25 seconds, only reading the status, and returns the settled result if confirmation arrives. If not, it answers outcome: "not_confirmed_yet": the buyer may already have been charged, the model polls genesispay_payment_status, and it never buys again with a new key. That answer never says failed.

Consumer Rewards connector (preview)

The separately enabled /mcp/rewards endpoint searches participating cashback stores, permitted products and coupons, reads your own cashback/referral records, and creates offer review links. It has no payment or payout tools. Purchases finish on merchant websites.

Connect with the operator-registered public OAuth client and its exact HTTPS callback, using authorization code with PKCE S256. The issuer is/oauth/rewards; resource is exactly /mcp/rewards. Request rewards.read and optionallyrewards.referrals.write. This connection needs no agent account, wallet delegation or spending key. Dynamic registration is not provided for Rewards. Configure the actual client/callback in the assistant host before testing a connection.

Tools: genesispay_rewards_offers (optional query),genesispay_rewards_search (query, optional product/promotion kind and limit), genesispay_rewards_cashback,genesispay_rewards_purchases (optional returned before cursor), and genesispay_rewards_review_offer (programmeId, optional itemId). Pass short product terms rather than conversation history or personal data. A review link still requires the owner to review and continue on GenesisPay.

Source prices, stock and coupons require confirmation at checkout. Pending/approved commission is distinct from received and available cashback; do not present a conditional reward as a guaranteed net price. Revoke connections in Rewards. Live partner/channel permission, real account testing and assistant distribution approval remain required; the public Rewards introduction does not activate this preview.