Skip to content
Back to blog
developer-guide14 min

Building Agentic Commerce #4: x402 Stablecoin Payments — When Agents Pay in USDC

How AI agents make on-chain USDC payments using the x402 protocol — multi-chain settlement, EIP-712 signatures, and production-ready stablecoin checkout.

Executive summary

Part 4 of 'Building Agentic Commerce' explains the x402 stablecoin payment protocol — how AI agents discover x402-enabled merchants, sign EIP-712 authorizations, settle on-chain via facilitators, and handle retries with exponential backoff. Covers 5 supported chains, USDC amount conversion, SSRF protection, and 197 tests.

Published

2026-04-06

14 min

Author

Trusteed Engineering

Core Protocol Team

Category

developer-guide

x402stablecoinUSDCcrypto paymentsEIP-712Baseagentic commerceMCPsettlementmulti-chain

In the first three parts of this series, we covered <a href='/en/blog/building-agentic-commerce-multi-protocol-checkout'>multi-protocol checkout</a>, <a href='/en/blog/building-agentic-commerce-agent-discovery-nlweb'>agent discovery via NLWeb</a>, and <a href='/en/blog/building-agentic-commerce-trust-scores'>trust scores</a>. Now we tackle the protocol that makes agents truly autonomous: <strong>x402 — stablecoin payments where agents pay directly on-chain in USDC</strong>.

Why Stablecoin Payments Matter for Agents

Traditional payment protocols (card networks, PayPal) require human identity — a cardholder, a PayPal account, a billing address. AI agents don't have these. The x402 protocol solves this by using wallet-based authentication: an agent proves it can pay by signing a cryptographic authorization, and settlement happens on-chain without any human identity requirement.

The HTTP 402 status code ("Payment Required") was reserved in the original HTTP specification but never standardized. The x402 protocol finally gives it a concrete implementation: when a server returns HTTP 402, it includes a machine-readable payment requirement that an agent can fulfill autonomously.

How x402 Works: The Complete Flow

The x402 payment flow involves three parties: the <strong>agent</strong> (buyer with a crypto wallet), the <strong>merchant</strong> (seller with a receiving wallet), and the <strong>facilitator</strong> (signature verifier and on-chain settler). Here's the step-by-step flow:

Step 1: Agent Requests a Resource

The agent sends an HTTP request to the merchant's checkout endpoint. The protocol detector identifies x402 via headers — <code>PAYMENT-SIGNATURE</code> (V2 format, confidence 0.95) or <code>X-PAYMENT</code> (V1 legacy, confidence 0.90). An explicit <code>X-Protocol: X402</code> header yields confidence 1.0. <pre><code>POST /api/v1/agent/checkout HTTP/1.1 Host: api.trusteed.xyz Content-Type: application/json PAYMENT-SIGNATURE: eyJzaWduYXR1cmUiOiIweGFiYy4uLiIsImF1dGhvcml6YXRpb24iOnsiZnJvbSI6IjB4MTExMSIsInRvIjoiMHgyMjIyIiwidmFsdWUiOiI1MDAwMDAwIiwidmFsaWRBZnRlciI6IjE3MTI1MDAwMDAiLCJ2YWxpZEJlZm9yZSI6IjE3MTI1MDM2MDAiLCJub25jZSI6IjB4ZGVhZGJlZWYifSwic2NoZW1lIjoiZXhhY3QiLCJuZXR3b3JrIjoiYmFzZSJ9 {"items": [{"productId": "prod_001", "quantity": 1}]}</code></pre>

Step 2: Server Returns HTTP 402

If the merchant has x402 enabled, the outbound adapter builds a <code>PaymentRequired</code> object with the merchant's wallet, network, and USDC token address. This is base64-encoded into the <code>PAYMENT-REQUIRED</code> header: <pre><code>HTTP/1.1 402 Payment Required PAYMENT-REQUIRED: eyJzY2hlbWUiOiJleGFjdCIsIm5ldHdvcmsiOiJiYXNlIi4uLn0= { "paymentRequired": { "scheme": "exact", "network": "base", "maxAmountRequired": "5000000", "payTo": "0x2222...merchant_wallet", "maxTimeoutSeconds": 1800, "extra": { "tokenAddress": "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913", "name": "USDC", "version": "2" } }, "facilitator": { "verifyUrl": "https://x402.org/facilitator/verify", "settleUrl": "https://x402.org/facilitator/settle" } }</code></pre>

The amount <code>5000000</code> represents 5 USDC. USDC uses 6 decimal places, so 1 USDC = 1,000,000 smallest units. The conversion: USD cents × 10,000 = USDC smallest units.

Essential insight

Step 3: Agent Signs and Settles

The agent reads the <code>PaymentRequired</code>, signs an EIP-712 typed data authorization with its private key, and submits to the settlement endpoint. The V2 authorization includes replay protection (<code>nonce</code>), time bounds (<code>validAfter</code>, <code>validBefore</code>), and the exact amount:
<pre><code>// V2 PAYMENT-SIGNATURE payload (base64-decoded) { "signature": "0xabc123...eip712_sig", "authorization": { "from": "0x1111...agent_wallet", "to": "0x2222...merchant_wallet", "value": "5000000", "validAfter": "1712500000", "validBefore": "1712503600", "nonce": "0xdeadbeef" }, "scheme": "exact", "network": "base" }</code></pre>

Step 4: Settlement with Exponential Backoff

The settlement service orchestrates a multi-phase process: (1) mark the order as <code>x402_pending_payment</code>, (2) verify the signature via the facilitator's <code>/verify</code> endpoint — if invalid, the order fails immediately with no retry, (3) attempt settlement via <code>/settle</code> with up to 5 retries using exponential backoff (5s → 10s → 20s → 40s), and (4) update the order to <code>completed</code> with the on-chain transaction hash, or <code>x402_failed</code> if all retries are exhausted.
<pre><code>// Settlement retry logic (simplified) for (let attempt = 0; attempt < 5; attempt++) { if (attempt > 0) { await sleep(5000 * Math.pow(2, attempt - 1)); // 5s, 10s, 20s, 40s } const result = await fetch(facilitator.settleUrl, { method: "POST", body: JSON.stringify({ paymentPayload, paymentRequired }), signal: AbortSignal.timeout(15_000) // 15s per-request timeout }); if (result.success) { return { status: "COMPLETED", txHash: result.txHash }; } } return { status: "FAILED" };</code></pre>

Supported Chains and Tokens

Trusteed's x402 configuration schema accepts 5 blockchain networks, all settling in USDC. This is what the platform is built to accept — see the sandbox-status callout below before treating any of them as production-ready:

  • 1
    <strong>Base</strong> — USDC at <code>0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913</code> (lowest fees on this network)
  • 2
    <strong>Ethereum</strong> — USDC at <code>0xA0b86991c6218b36c1d19D4a2e9Eb0cE3606eB48</code>
  • 3
    <strong>Polygon</strong> — USDC at <code>0x3c499c542cEF5E3811e1192ce70d8cC03d5c3359</code>
  • 4
    <strong>Arbitrum</strong> — USDC at <code>0xaf88d065e77c8cC2239327C5EDb3A432268e5831</code>
  • 5
    <strong>Solana</strong> — USDC at <code>EPjFWdd5AufqSSqeM2qN1xzybapC8G4wEGGkZwyTDt1v</code>

Merchants can override the default USDC address with a custom <code>tokenAddress</code> in their protocol configuration. A <code>maxTransactionAmount</code> safety cap is also supported. Sandbox status as of this writing: the schema above accepts mainnet only, no merchant has a settleable configuration yet, and there are no known real x402 settlements on any network — check <a href="/en/protocol-coverage">/en/protocol-coverage</a> before planning a production flow.

Essential insight

Amount Conversion: USDC ↔ USD Cents

The bridge converts between USD cents (used internally for multi-protocol compatibility) and USDC smallest units (on-chain representation). The math is straightforward: <pre><code>// Inbound: USDC smallest units → USD cents // 1 USDC (1,000,000 units) = 100 cents → divide by 10,000 const cents = parseInt(usdcSmallestUnit) / 10_000; // Example: "5000000" (5 USDC) → 500 cents ($5.00) // Outbound: USD cents → USDC smallest units const usdc = String(Math.round(cents * 10_000)); // Example: 500 cents → "5000000" (5 USDC)</code></pre>

Safety checks prevent sub-cent precision errors (values must be divisible by 10,000), reject negative amounts, and enforce IEEE-754 safe integer bounds (~$9 billion max).

Protocol Detection: How x402 Is Identified

x402 is one of 9 payment protocols in the Trusteed detection system. The multi-protocol detector assigns confidence scores to determine which adapter handles each request:

  • 1
    <code>X-Protocol: X402</code> header → confidence <strong>1.0</strong> (explicit declaration)
  • 2
    <code>PAYMENT-SIGNATURE</code> header (V2) → confidence <strong>0.95</strong>
  • 3
    <code>X-PAYMENT</code> header (V1 legacy) → confidence <strong>0.90</strong>
  • 4
    Body shape match (<code>paymentPayload</code>, <code>x402</code>, or <code>paymentRequired</code> fields) → confidence <strong>0.85</strong>
  • 5
    No match → falls back to ACP at confidence 0.5

This means x402 coexists with ACP, UCP, PayPal, Visa VIC, Mastercard Agent Pay, and other protocols. The highest-confidence adapter wins, and the protocol bridge routes the payment to the correct settlement path.

Merchant Configuration

Merchants enable x402 by adding a protocol configuration with their wallet address and preferred network: <pre><code>// Stored in MerchantProtocol.config (database) { "protocol": "X402", "enabled": true, "priority": 100, "config": { "walletAddress": "0xAbCd...merchant_wallet", "network": "base", "facilitatorUrl": "https://x402.org/facilitator", "supportedTokens": ["USDC"], "maxTransactionAmount": 100000000 // 100 USDC safety cap } }</code></pre>
The configuration validator enforces SSRF protection — private/internal URLs (127.0.0.1, 10.x.x.x, localhost) are rejected for the <code>facilitatorUrl</code>. Wallet addresses are validated for both EVM (0x + 40 hex chars) and Solana formats.

Security Model

  • 1
    <strong>No sensitive data in audit logs</strong> — wallet addresses, signatures, and nonces are never stored in OrderEvent records. Only protocol name, network, and transaction hash references are logged.
  • 2
    <strong>Facilitator-delegated verification</strong> — the bridge never validates EIP-712 signatures locally (no key material on the server). Verification is delegated to the facilitator's <code>/verify</code> endpoint.
  • 3
    <strong>Atomic state transitions</strong> — order status updates use database-level atomicity. The expiration job double-checks status before updating to prevent race conditions.
  • 4
    <strong>SSRF protection</strong> — merchant-provided facilitator URLs are validated against private IP ranges and internal hostnames.
  • 5
    <strong>15-second fetch timeout</strong> — all facilitator requests have a hard timeout to prevent hanging connections.

Order Status State Machine

x402 orders follow a strict state machine: <pre><code>┌──────────┐ verify ┌──────────────────────┐ │ PENDING │ ──────────────→ │ x402_pending_payment │ └──────────┘ └──────────┬───────────┘ │ ┌─────────────┼─────────────┐ ↓ ↓ ↓ ┌───────────┐ ┌───────────┐ ┌─────────┐ │ completed │ │ x402_failed│ │ expired │ └───────────┘ └───────────┘ └─────────┘ Terminal states cannot be overwritten. Expiration: 30-minute background job catches stuck payments.</code></pre>

V1 vs V2 Header Format

The x402 implementation supports two header formats. <strong>V2 (PAYMENT-SIGNATURE)</strong> is the current standard with full security: replay protection via <code>nonce</code>, time-bounded validity (<code>validAfter</code>/<code>validBefore</code>), and structured EIP-712 typed data. <strong>V1 (X-PAYMENT)</strong> is maintained for backward compatibility but lacks nonce and time bounds, making it less secure. New integrations should always use V2.

Production Tips

  • 1
    <strong>Choose Base for lowest fees</strong> — L2 transaction costs are a fraction of Ethereum mainnet. Most agent-to-merchant payments are small (<$100), making Base the optimal default.
  • 2
    <strong>Set maxTransactionAmount</strong> — a per-merchant safety cap prevents accidental large settlements. Start conservative (e.g., 100 USDC) and increase as trust builds.
  • 3
    <strong>Monitor the expiration job</strong> — orders stuck in <code>x402_pending_payment</code> for >30 minutes indicate facilitator issues or network congestion. Set up alerts on the <code>x402_payment_expired</code> OrderEvent.
  • 4
    <strong>Use V2 headers exclusively</strong> — V1 lacks replay protection. Disable V1 support in production if your agent ecosystem supports V2.
  • 5
    <strong>Handle 402 responses gracefully</strong> — when building agent clients, parse the <code>PAYMENT-REQUIRED</code> header, extract the facilitator URLs, and implement the sign-and-settle flow. The facilitator handles all on-chain complexity.

Test Coverage

The x402 implementation is backed by 197 test cases across 6 test files (~2,554 lines of test code). Coverage includes: detection (8 tests), normalization (12 tests), settlement with backoff (45+ tests), configuration validation with SSRF (18 tests), end-to-end integration (22 tests), and 92+ edge cases covering precision errors, timeouts, network failures, and concurrent state updates.

What's Next

In <strong>Part 5</strong>, we'll explore <strong>UCP — Shopify's Universal Commerce Protocol</strong> and how it enables agent-driven commerce across the Shopify ecosystem. Stay tuned.

Frequently asked questions

What is x402 and how does it relate to HTTP 402?

x402 is a payment protocol that implements the long-reserved HTTP 402 (Payment Required) status code. When a server returns 402, it includes a machine-readable PaymentRequired object that AI agents can fulfill autonomously using USDC stablecoin payments on-chain.

Which blockchains does x402 support?

Trusteed's x402 schema accepts configuration on 5 networks — Base, Ethereum, Polygon, Arbitrum, and Solana — all settling in USDC with well-known contract addresses per chain. As of this writing the rail is sandbox-only: no merchant has a settleable configuration and there are no known real settlements on any of them, so none is 'recommended' in production terms yet.

How does x402 handle failed settlements?

The settlement service uses exponential backoff with up to 5 retry attempts (delays of 5s, 10s, 20s, 40s). Each facilitator request has a 15-second timeout. If all retries fail, the order is marked x402_failed. A background job expires stuck orders after 30 minutes.

Is x402 secure? How are signatures verified?

Yes. x402 V2 uses EIP-712 typed data signatures with replay protection (nonce) and time bounds. Signature verification is delegated to the facilitator — no private key material exists on the server. Wallet addresses and signatures are never stored in audit logs.

Can x402 work alongside other payment protocols?

Absolutely. x402 is one of 9 payment protocols in the Trusteed detection system. The multi-protocol detector assigns confidence scores, and the highest-confidence adapter wins. If a merchant doesn't have x402 enabled, the bridge falls back to their preferred protocol (ACP, PayPal, etc.).

Sources and references

Related articles

x402 Stablecoin Payments for AI Agents | Building Agentic Commerce #4 | Trusteed