x402 micropayment, live demo.
Buy a compliance report from StableKYA.com for $0.001 testnet USDC, signed by a Coinbase Smart Wallet and settled on Base Sepolia via the Coinbase CDP x402 facilitator. Watch every stage of the payment lifecycle as it happens.
Your Wallet
The x402 journey begins when you delegate spending authority by connecting a wallet. This demo expects a Coinbase Smart Wallet (an ERC-4337 account-abstraction wallet with a WebAuthn passkey) on Base Sepolia, but any EIP-1193 provider — Coinbase Wallet, MetaMask, Rainbow — will connect. Your wallet's identity, address and chain, becomes the foundation for every compliance check that follows.
validateUserOp path of its ERC-4337 account contract, not by an off-chain dashboard. That places it below the STATE line in the diagram above. For the full wallet taxonomy, see StableKYA.com.
The Gate
When any HTTP client — browser, CLI, or AI agent — hits a paywalled resource, the server responds with HTTP 402 Payment Required. The payment requirements are encoded in the response headers. The server doesn't know or care what the client is.
The Payment
You sign an EIP-3009 transferWithAuthorization against Circle's USDC contract on Base Sepolia — a gasless USDC transfer that the Coinbase CDP x402 facilitator submits on your behalf. OFAC screening (Chainalysis address screening) fires at S6 as a code-enforced gate before the transfer lands on-chain.
transferWithAuthorization call to Circle's USDC contract on Base Sepolia. For the full checkpoint taxonomy, see StableKYA.com.
Payment & Delivery
Two events fire in close sequence on two different rails. On the on-chain rail, the Coinbase CDP x402 facilitator drives a transferWithAuthorization call to Circle's USDC contract on Base Sepolia, reaching soft finality in ~2s and inheriting hard finality from Ethereum L1 data availability. On the HTTP rail, the StableKYA Worker responds with 200 OK and the compliance PDF body. The two rails are bound by the x402 protocol into a near-atomic delivery-versus-payment exchange — payment on the left, delivery on the right.
Know Your Agent: Anatomy of an x402 Compliant Transaction
The compliance diagram inside this report maps the transaction you just completed.
200 OK response is the resource half of the exchange. The compliance diagram inside it maps the transaction you just made.
The Code
The payment flow code — buyer site and publisher Worker — is open source. The server is ~40 lines. The client is ~60.
// stablekya.com/api/report — x402 gate
export default {
async fetch(request: Request, env: Env) {
const paymentSig = request.headers
.get('PAYMENT-SIGNATURE');
if (!paymentSig) {
return new Response('Payment Required', {
status: 402,
headers: {
'PAYMENT-REQUIRED': btoa(JSON.stringify({
accepts: [{
scheme: 'exact',
network: 'base-sepolia',
asset: 'USDC',
amount: '1000',
payTo: env.MERCHANT_ADDRESS,
resource: 'kya-compliance-report-v1',
}],
})),
},
});
}
// Verify payment via facilitator...
const report = await env.REPORTS
.get('kya-report-v1.pdf');
return new Response(report.body, {
headers: {
'Content-Type': 'application/pdf',
},
});
},
}; // Stable402.com — x402 buyer flow
async function purchaseReport() {
// 1. Hit the gate
const res402 = await fetch(
'https://stablekya.com/api/report'
);
const requirements = JSON.parse(atob(
res402.headers.get('PAYMENT-REQUIRED')
)).accepts[0];
// 2. Sign EIP-3009 authorization
const signature = await walletClient
.signTypedData({
domain: {
name: 'USDC', version: '2',
chainId: 84532,
verifyingContract: USDC,
},
types: {
TransferWithAuthorization: [
/* from, to, value, ... */
],
},
message: {
from: address,
to: requirements.payTo,
value: BigInt(requirements.amount),
},
});
// 3. Retry with payment
const res200 = await fetch(
'https://stablekya.com/api/report',
{
headers: {
'PAYMENT-SIGNATURE': btoa(
JSON.stringify({
x402Version: 2,
accepted: requirements,
payload: { signature },
})
),
},
}
);
// 4. Deliver the PDF
const pdf = await res200.blob();
downloadPdf(pdf, 'kya-report.pdf');
}