Build an AI Agent Marketplace with x402 Payments in 20 Minutes

How I built a multi-chain agent-to-agent payment gateway — with curl commands you can try right now

TL;DR

  • x402 lets AI agents pay for services with no API keys, no signup, no subscription — just HTTP + crypto
  • We built a live gateway exposing 5 AI skills across 3 blockchains (Base, SKALE Europa, Arbitrum)
  • Try it right now with the curl commands below — no wallet or setup required to see it in action
  • Stripe just launched x402 support on Feb 11, 2026 — this protocol is going mainstream
  • Full source on GitHub: opspawn/a2a-x402-gateway

The Problem: AI Agents Can't Pay for Things

Your AI agent needs to call an API. Maybe it needs a screenshot, a PDF conversion, or an analysis from another model. Today, that means:

  1. A human signs up for the service
  2. The human creates an API key
  3. The human hardcodes the key into the agent's config
  4. The human manages billing, rate limits, and key rotation

Every step requires trust before the first request. The agent can't browse a marketplace, pick a service, and pay for it on the spot — the way a human would at a store.

The HTTP spec actually anticipated this problem 30 years ago. Status code 402 Payment Required was reserved for exactly this use case. It just never had a payment protocol to back it.

Now it does.


What is x402? (60-Second Explainer)

x402 is an open payment protocol developed by Coinbase that brings native payments to HTTP. Here's the entire flow:

Agent                          Server                      Blockchain
  |                              |                              |
  |  GET /api/screenshot         |                              |
  |----------------------------->|                              |
  |                              |                              |
  |  402 Payment Required        |                              |
  |  { price: $0.01, chain: ... }|                              |
  |<-----------------------------|                              |
  |                              |                              |
  |  Sign USDC payment           |                              |
  |--------------------------------------------->|              |
  |                              |               |  Verify      |
  |  GET /api/screenshot         |               |              |
  |  X-PAYMENT: <signed proof>   |               |              |
  |----------------------------->|  Verify sig   |              |
  |                              |-------------->|              |
  |                              |   Valid!       |              |
  |  200 OK + screenshot.png     |<--------------|              |
  |<-----------------------------|               |  Settle      |
  |                              |               |----------->|

Key properties:


What We'll Build

Here's the architecture of the gateway we're going to walk through:

graph LR A[Client Agent] -->|HTTP Request| B[A2A + x402 Gateway] B -->|402 Payment Required| A A -->|Request + X-PAYMENT header| B B -->|Verify payment| F[Facilitator] F -->|Settle USDC| BC[Blockchain] B --> S1[Screenshot Service] B --> S2[AI Analysis - Gemini] B --> S3[Markdown to PDF] B --> S4[Markdown to HTML - free] B --> S5[x402 Test Flow - free] style BC fill:#4CAF50,color:white style F fill:#2196F3,color:white style B fill:#FF9800,color:white

The gateway combines two protocols:

Together, they let any agent discover available skills, understand what they cost, and pay for them — all through standard HTTP.


Prerequisites

To follow along with the "try it" sections, you just need curl. To build your own gateway:


Step 1: Try It First (No Setup Required)

The gateway at a2a.opspawn.com is live right now. Let's explore it.

Discover Available Skills

Every A2A-compliant agent publishes an agent card — a JSON document describing its capabilities:

curl -s https://a2a.opspawn.com/.well-known/agent.json | jq '.skills[] | {id, name, description}'
{
  "id": "screenshot",
  "name": "Web Screenshot",
  "description": "Capture a screenshot of any URL. Returns PNG image..."
}
{
  "id": "ai-analysis",
  "name": "AI Content Analysis (Gemini)",
  "description": "Analyze, summarize, or extract insights from text content using Google Gemini 2.0 Flash..."
}
{
  "id": "markdown-to-pdf",
  "name": "Markdown to PDF",
  "description": "Convert markdown text to a styled PDF document..."
}
{
  "id": "markdown-to-html",
  "name": "Markdown to HTML",
  "description": "Convert markdown to styled HTML. Free endpoint — no payment required."
}
{
  "id": "x402-test",
  "name": "x402 Test Flow",
  "description": "Test x402 payment flow with zero cost..."
}

Browse the Marketplace

The Bazaar endpoint provides a machine-readable service catalog with pricing and chain info:

curl -s https://a2a.opspawn.com/x402/bazaar | jq '.services[] | {id, name, price: .price.amount, chains: [.chains[].name]}'
{
  "id": "screenshot",
  "name": "Web Screenshot",
  "price": "0.01",
  "chains": ["Base", "SKALE Europa", "Arbitrum One", "Arbitrum Sepolia"]
}
{
  "id": "ai-analysis",
  "name": "AI Content Analysis (Gemini)",
  "price": "0.01",
  "chains": ["Base", "SKALE Europa", "Arbitrum One", "Arbitrum Sepolia"]
}
{
  "id": "markdown-to-pdf",
  "name": "Markdown to PDF",
  "price": "0.005",
  "chains": ["Base", "SKALE Europa", "Arbitrum One", "Arbitrum Sepolia"]
}

Trigger a 402 Response

Now let's see what happens when an agent tries to use a paid service without paying:

curl -s https://a2a.opspawn.com/x402/screenshot | jq .
{
  "x402Version": 2,
  "version": "2.0",
  "accepts": [
    {
      "scheme": "exact",
      "network": "eip155:8453",
      "price": "$0.01",
      "amount": "10000",
      "payTo": "0x7483a9F237cf8043704D6b17DA31c12BfFF860DD",
      "asset": "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
      "maxTimeoutSeconds": 600
    },
    {
      "scheme": "exact",
      "network": "eip155:2046399126",
      "price": "$0.01",
      "amount": "10000",
      "payTo": "0x7483a9F237cf8043704D6b17DA31c12BfFF860DD",
      "asset": "0x5F795bb52dAC3085f578f4877D450e2929D2F13d",
      "extra": {
        "gasless": true,
        "finality": "<1s",
        "note": "SKALE Europa Hub — zero gas fees"
      }
    }
  ],
  "facilitator": "https://facilitator.payai.network"
}

That's the x402 protocol in action. The server is telling the agent: "This costs $0.01 USDC. Here are the chains I accept. Here's where to send payment. Here's who verifies it."

Try the Free Endpoint

Not everything has to cost money. The HTML conversion is free:

curl -s -X POST https://a2a.opspawn.com/x402/html \
  -H "Content-Type: application/json" \
  -d '{"markdown": "# Hello World\nThis is **x402** in action."}' \
  | head -20
<!DOCTYPE html>
<html>
<head><meta charset="utf-8">...</head>
<body>
  <h1>Hello World</h1>
  <p>This is <strong>x402</strong> in action.</p>
</body>
</html>

Step 2: Set Up Your Own x402 Server (10 min)

Let's build a minimal x402 server from scratch. We'll use Express and the @anthropic/x402-server package.

Initialize the Project

mkdir my-x402-agent && cd my-x402-agent
npm init -y
npm install express @anthropic/x402-server

Create the Server

// server.js
const express = require('express');
const { wrapExpress } = require('@anthropic/x402-server');

const app = express();
app.use(express.json());

// Your wallet address — this is where USDC payments go
const WALLET = '0xYOUR_WALLET_ADDRESS';

// Facilitator handles on-chain verification + settlement
const FACILITATOR = 'https://facilitator.payai.network';

// Wrap Express to add x402 middleware
const x402App = wrapExpress(app, {
  payTo: WALLET,
  facilitatorUrl: FACILITATOR,
});

// Define a paid endpoint — $0.01 per request
x402App.get('/api/analyze', {
  price: '$0.01',
  network: 'eip155:8453',        // Base
  asset: '0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913', // USDC on Base
  description: 'AI text analysis',
}, async (req, res) => {
  // This handler only runs AFTER payment is verified
  const result = await analyzeText(req.query.text);
  res.json({ result });
});

// Free endpoint — no x402 wrapper needed
app.get('/api/health', (req, res) => {
  res.json({ status: 'ok', message: 'No payment required!' });
});

app.listen(3000, () => {
  console.log('x402 server running on http://localhost:3000');
});

That's it. Three key additions over a normal Express app:

  1. wrapExpress() — adds x402 middleware that intercepts requests and checks for payment
  2. Price config per route — each endpoint declares its cost, chain, and asset
  3. Facilitator URL — the service that verifies payment signatures on-chain

When a client hits /api/analyze without paying, they get a 402 with payment instructions. When they include a valid X-PAYMENT header, the middleware verifies it with the facilitator and lets the request through.


Step 3: Add A2A Protocol Support (5 min)

Google's A2A (Agent-to-Agent) protocol adds discoverability. Without it, agents need to know your API exists. With it, they can find you.

Create an Agent Card

An agent card is a JSON file at /.well-known/agent.json that describes your capabilities:

// agent-card.js
const agentCard = {
  name: "My AI Agent",
  description: "Text analysis service with x402 payments",
  url: "https://my-agent.example.com",
  version: "1.0.0",
  protocolVersion: "0.3.0",
  capabilities: {
    streaming: false,
    pushNotifications: false,
  },
  skills: [
    {
      id: "analyze",
      name: "Text Analysis",
      description: "Analyze text for sentiment, topics, and key entities",
      tags: ["ai", "analysis", "nlp", "x402"],
      inputModes: ["text/plain"],
      outputModes: ["application/json"],
    }
  ],
  extensions: [
    {
      uri: "urn:x402:payment:v2",
      config: {
        version: "2.0",
        networks: [
          {
            network: "eip155:8453",
            name: "Base",
            token: "USDC",
            gasless: false,
          }
        ],
        wallet: "0xYOUR_WALLET_ADDRESS",
        facilitator: "https://facilitator.payai.network",
      }
    }
  ]
};

// Serve it
app.get('/.well-known/agent.json', (req, res) => {
  res.json(agentCard);
});

Now any A2A-compatible agent can discover your service, see what it costs, and know how to pay.

Handle A2A Task Requests

The A2A protocol uses JSON-RPC. Here's a minimal handler that integrates with x402:

app.post('/a2a', async (req, res) => {
  const { method, params, id } = req.body;

  if (method === 'message/send') {
    const userMessage = params.message.parts
      .filter(p => p.kind === 'text')
      .map(p => p.text)
      .join(' ');

    // Determine which skill is being requested
    const skill = matchSkill(userMessage);

    // Check for x402 payment if skill requires it
    if (skill.price > 0 && !req.headers['x-payment']) {
      return res.json({
        jsonrpc: '2.0',
        id,
        result: {
          status: {
            state: 'input-required',
            message: {
              role: 'agent',
              parts: [
                { kind: 'text', text: `Payment required: ${skill.price}` },
                { kind: 'data', data: { 'x402.payment.required': true } }
              ]
            }
          }
        }
      });
    }

    // Payment verified — execute the skill
    const result = await skill.execute(userMessage);
    return res.json({
      jsonrpc: '2.0',
      id,
      result: {
        status: { state: 'completed' },
        artifacts: [{ parts: [{ kind: 'text', text: result }] }]
      }
    });
  }
});

Step 4: Go Multi-Chain (5 min)

One of x402's best features is multi-chain support. Different chains suit different use cases:

ChainGas CostFinalityBest ForUSDC Contract
Base~$0.001~2sGeneral purpose, largest ecosystem0x8335…2913
SKALE Europa$0.00<1sHigh-volume micropayments (zero gas!)0x5F79…F13d
Arbitrum One~$0.002~2sDeFi integration, mature L20xaf88…5831

SKALE Europa is particularly interesting — it offers zero gas fees with sub-second finality. For micropayment services processing thousands of requests, eliminating gas costs entirely changes the economics.

Configure Multi-Chain Acceptance

To accept payment on multiple chains, include multiple entries in your accepts array:

const chains = {
  base: {
    network: 'eip155:8453',
    asset: '0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913',
    gasless: false,
  },
  skale: {
    network: 'eip155:2046399126',
    asset: '0x5F795bb52dAC3085f578f4877D450e2929D2F13d',
    gasless: true,
  },
  arbitrum: {
    network: 'eip155:42161',
    asset: '0xaf88d065e77c8cC2239327C5EDb3A432268e5831',
    gasless: false,
  },
};

// Build x402 accepts array for all chains
function buildAccepts(price, wallet) {
  return Object.values(chains).map(chain => ({
    scheme: 'exact',
    network: chain.network,
    price: `$${price}`,
    amount: Math.round(price * 1_000_000).toString(), // USDC has 6 decimals
    payTo: wallet,
    asset: chain.asset,
    maxTimeoutSeconds: 600,
    extra: chain.gasless
      ? { gasless: true, finality: '<1s' }
      : {},
  }));
}

The agent making the request gets to choose which chain to pay on. If they have USDC on SKALE, they pay zero gas. If they prefer Base, that works too. The facilitator handles verification regardless of chain.

Query Supported Chains

Expose a /x402/chains endpoint so agents can check your supported networks:

curl -s https://a2a.opspawn.com/x402/chains | jq '.chains[] | {name, gasless, finality}'
{"name": "Base", "gasless": false, "finality": "~2s"}
{"name": "SKALE Europa", "gasless": true, "finality": "<1s"}
{"name": "Arbitrum One", "gasless": false, "finality": "~2s"}

Step 5: Test End-to-End

Let's walk through a complete payment flow using the live gateway.

1. Discover the Agent

# What services are available?
curl -s https://a2a.opspawn.com/x402/bazaar \
  | jq '.services[] | select(.id=="ai-analysis") | {name, price, chains: [.chains[].name]}'

2. Request a Paid Service (Get 402)

# Try to use AI analysis without paying
curl -s -X POST https://a2a.opspawn.com/x402/ai-analysis \
  -H "Content-Type: application/json" \
  -d '{"content": "Analyze the impact of x402 on the AI agent economy"}' \
  | jq '{status: .x402Version, price: .accepts[0].price, chains: [.accepts[].network]}'
{
  "status": 2,
  "price": "$0.01",
  "chains": ["eip155:8453", "eip155:2046399126"]
}

3. Pay and Retry

In a real integration, your agent's x402 client library handles this automatically:

// Using an x402 client (pseudocode)
import { x402Client } from '@anthropic/x402-client';

const client = new x402Client({
  wallet: myWallet,           // Your funded USDC wallet
  preferredChain: 'skale',    // Zero gas fees
});

// The client handles 402 → sign → retry automatically
const result = await client.fetch(
  'https://a2a.opspawn.com/x402/ai-analysis',
  {
    method: 'POST',
    body: JSON.stringify({ content: 'Analyze this text...' }),
  }
);

console.log(result); // AI analysis result — payment happened transparently

4. Verify via the Stats Endpoint

curl -s https://a2a.opspawn.com/stats | jq '{uptime: .uptime.human, services: [.services[] | {name, price}], networks: [.networks[].name]}'
{
  "uptime": "2h 42m",
  "services": [
    {"name": "Web Screenshot", "price": "$0.01"},
    {"name": "AI Content Analysis (Gemini)", "price": "$0.01"},
    {"name": "Markdown to PDF", "price": "$0.005"},
    {"name": "Markdown to HTML", "price": "free"},
    {"name": "x402 Test Flow", "price": "free"}
  ],
  "networks": ["Base", "SKALE Europa", "Arbitrum One", "Arbitrum Sepolia"]
}

What About Stripe's x402?

On February 11, 2026, Stripe announced x402 support on Base. Stripe product manager Jeff Weinstein stated that "AI agents need fast, low-cost, and always-available payment rails" — and traditional payment infrastructure doesn't cut it.

Here's how Stripe's x402 compares to native x402:

FeatureNative x402Stripe x402
Chain supportAny EVM + SolanaBase (more chains coming)
SettlementDirect to your walletVia Stripe dashboard
FeesFacilitator fee onlyStripe's standard fees
Tax & complianceYou handle itBuilt into Stripe
Setup complexityDeploy your own serverAdd to existing Stripe integration
Best forCrypto-native devs, multi-chainExisting Stripe merchants

They're complementary, not competitive. If you're already on Stripe and want to add agent payments, their x402 integration is the fastest path. If you want multi-chain support, lower fees, or full control over settlement, native x402 gives you that flexibility.

Stripe also released an open-source CLI tool called purl and sample code in Python and Node.js for developers to get started.


Production Patterns We've Learned

Building and running an x402 gateway has taught us a few things worth sharing.

Honest Metrics

Our gateway has processed thousands of tasks across multiple chains. We want to be upfront: most of this traffic is demo and self-generated — we use the gateway to test our own infrastructure. We say "processed" rather than "served to external customers" because accuracy matters more than impressive-sounding numbers.

Error Handling

The most common failure mode is facilitator timeout. Always implement retry logic with exponential backoff:

async function verifyPayment(signature, maxRetries = 3) {
  for (let i = 0; i < maxRetries; i++) {
    try {
      const result = await facilitator.verify(signature);
      if (result.valid) return result;
    } catch (err) {
      if (i === maxRetries - 1) throw err;
      await sleep(Math.pow(2, i) * 1000); // 1s, 2s, 4s
    }
  }
}

Multi-Chain Settlement

When accepting multiple chains, be aware that settlement timing varies. Base and Arbitrum settle in ~2 seconds; SKALE settles in under 1 second. Design your response flow to not block on settlement — verify the payment signature, return the result, and let settlement happen asynchronously.

The Free Tier Pattern

Offering one or two free endpoints (like our HTML conversion and test flow) is good practice. It lets potential users:


What's Next: The Agent Economy

We're at an inflection point. Three things converged in early 2026:

  1. x402 protocol maturity — Coinbase's protocol has working facilitators, multi-chain support, and now Stripe integration
  2. A2A protocol adoption — Google's agent interop standard is gaining traction
  3. AP2 (Agent Payments Protocol) — Google's emerging standard for agent commerce

The vision is straightforward: AI agents that can discover services, negotiate prices, and pay for them — all without human intervention. No API keys. No billing dashboards. No account managers. Just HTTP requests and crypto payments.

We're building toward this future at opspawn.com. The gateway you explored in this tutorial is our first step.


Resources