When an agent calls a paid endpoint that speaks x402 v2, the first answer it gets is not the data. It is HTTP 402 with a PAYMENT-REQUIRED response header carrying the payment requirements, base64-encoded. This post walks the decoded object field by field, using a fictional example, so you can write (or debug) a client that handles any x402 service.
Decoded, the object looks like this:
{
"x402Version": 2,
"accepts": [
{
"scheme": "exact",
"network": "eip155:8453",
"asset": "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
"amount": "3000000",
"payTo": "0x1234...abcd",
"maxTimeoutSeconds": 1800,
"extra": { "name": "USD Coin", "version": "2" }
}
]
}
x402Version
The protocol version the server speaks. v2 responses carry their requirements under accepts, a list, because a server can offer more than one way to pay. A client should pick the first entry it can satisfy rather than assuming there is exactly one.
scheme
How the amount is interpreted. exact means the transfer must be for exactly amount of asset. Other schemes can describe looser arrangements; if your client only understands exact, skip anything else.
network
The chain, in CAIP-2 form. eip155:8453 is Base mainnet. This matters twice: the wallet must hold funds on that chain, and the signed authorization must name that chain, or settlement fails.
asset
The token contract address. Here it is USDC on Base. Never infer the token from the network alone; read the address and check it against a known list if your client cares about what it is spending.
amount
The price in the asset's smallest unit, as a decimal string. USDC has 6 decimals, so 3000000 is 3.00 USDC. Treat it as an integer string: no floats, ever, anywhere near money.
payTo
The recipient address the authorization must name. The signature is only valid for this recipient, so a client never needs to trust a destination it was told about anywhere else.
maxTimeoutSeconds
How long the offer stands. After this window the server can change price or terms, so a client should sign and submit promptly, and re-request the 402 if the window has passed.
extra
Asset-specific metadata the signing step needs. For USDC's EIP-3009 transferWithAuthorization, name and version are the EIP-712 domain values: get them wrong and the signature verifies nothing.
What the client does with it
Decode the PAYMENT-REQUIRED header, pick an accepts entry you can satisfy, sign the EIP-3009 authorization locally, and resubmit the original request with the base64-encoded payment payload in the PAYMENT-SIGNATURE header. If the payload is valid, the same URL now returns the paid resource, with a PAYMENT-RESPONSE header carrying the settlement details. If anything is off (wrong chain, wrong domain values, expired window), the response is another 402, usually with a reason.
The full specification and reference clients are in the protocol documentation: https://docs.x402.org
This article was generated by an AI system.
Top comments (0)