Skip to main content
When an AI agent calls a paid API, the API returns HTTP 402 Payment Required with a payment challenge. The x402 protocol standardizes this flow. The agent checks each payment with Conto before it pays.
x402 endpoints enforce explicit API-key scopes. Pre-authorization requires payments:request, managed signing (pay) and recording execution require payments:execute, and budget or service analytics require analytics:read.

Prerequisites

An active agent with an SDK key (Quickstart)
A funded wallet with USDC on the network the API settles on (Base for production, or Base Sepolia for testing). x402 is not offered on Tempo: pre-authorize and pay return 422 UNSUPPORTED_NETWORK for a wallet on a network with no USDC.
An x402-enabled API to call (or a test service that returns an x402 challenge)

How x402 works

Which path enforces depends on who holds the key: See Conto-signed payments for the managed path.

Step 1: Set up x402 policies

Without x402-specific policies, only your general spend limits apply. The policy rule reference lists every x402 rule type and value format.
x402 rules apply to every payment the agent makes, not only x402 calls. X402_MAX_PER_REQUEST caps all of its payments, and X402_MAX_PER_SERVICE denies any payment without an x402 service. Assign x402 policies only to an agent that pays for APIs.
The two rules below belong to different x402 policy types, so this example uses COMPOSITE.
1

Create the policy

Go to Policies > Create Policy.
2

Add rules

Rule 1: Cap per API callNo single x402 payment can exceed $0.50.Rule 2: Budget per serviceSpend with any one API domain cannot exceed $50 in a rolling 24 hours.
3

Assign to agent

Go to the agent’s Permissions tab and assign the policy.
You can also add X402_ALLOWED_SERVICES with a JSON array value such as ["api.example.com", "data.provider.io"]. This is the strongest guardrail: the agent can pay only the API domains you list.

Step 2: Pre-authorize a payment

When your agent receives an HTTP 402, send the payment details to POST /api/sdk/x402/pre-authorize. Conto evaluates your x402 policies plus your general spend limits. An approved payment returns a single-use grantId and grantSignature and reserves the amount for 10 minutes. The agent signs the payment and retries the API call. A declined payment returns reasons and reasonCodes, and the agent skips the call. See Pre-authorization. If Conto returns 503 PAYMENTS_PAUSED, no grant was issued. Stop before signing or retrying the resource request. Ask the owner to check payment availability, then retry with the same payment identity after service resumes. LIVE_PAYMENTS_PAUSED and the LIVE_PAYMENT_CAP_* codes are separate mainnet controls. See error handling.

Step 3: Record the transaction

After the payment settles onchain, record it with POST /api/sdk/x402/record and include the grantId and grantSignature from Step 2. See Recording transactions.
A record without a valid, unexpired grant is treated as a policy bypass. Conto records the payment, flags it for review, and alerts the account owner. See Grants and policy bypass.

Step 4: Monitor spending

Open Machine Spend in the dashboard for spend, calls, and average cost per service and endpoint. Conto also raises anomaly alerts on recorded payments. From the API, use Budget tracking and Querying services.

Full integration example

This example uses an external wallet: your agent signs, and Conto checks the payment first and records it after. It follows the x402 wire format:
  • The API answers 402. x402 v1 puts the payment requirements in the response body. x402 v2 puts them, base64 encoded, in the PAYMENT-REQUIRED header.
  • The agent retries with a signed payload in the X-PAYMENT header (v1) or PAYMENT-SIGNATURE header (v2).
  • The API returns the settlement, including the transaction hash, in the X-PAYMENT-RESPONSE header (v1) or PAYMENT-RESPONSE header (v2).
Conto takes networks in CAIP-2 form, such as eip155:8453 for Base. v1 challenges use names like base, so convert them first.
With a managed EVM wallet, replace Steps 3 and 4 with conto.x402.pay(). Pass the same fields plus x402Version and paymentRequirements: requirement, then retry the API call with the returned paymentHeaderName header set to xPaymentHeader. Record the settlement the same way.

Troubleshooting

Your general spend limits still apply to x402 payments. If the x402 amount plus today’s spend exceeds your daily limit, it’s denied. Check your wallet-level and agent-level spend limits.
Conto counts x402 spend only from recorded payments. Record every payment after it settles.
The allowlist is strict. Only listed domains can receive x402 payments. Add the exact domain (for example api.example.com, not example.com or www.api.example.com).
No. Each grant covers one payment and is used up when it is recorded, so every paid call needs its own pre-authorization.

API reference

Pre-authorization

With the SDK, call conto.x402.preAuthorize() with the same fields.
Conto derives serviceDomain from resourceUrl, so you do not need to send it. Send the facilitator, scheme, payment ID, and session ID when available so matching policies evaluate the actual x402 challenge. Send payerAddress and network together. Use the exact signing address and the CAIP-2 network from the selected x402 requirement. This binds policy evaluation to the wallet that will pay. The binding is required when an agent has more than one active wallet. Response (Approved):
An approved decision issues a single-use grant for the exact wallet, recipient, and amount, and reserves that amount against the wallet’s spend limits. The grant expires after 10 minutes. If it is never recorded, Conto releases the reservation. Retrying pre-authorization with the same paymentId returns the same live grant instead of reserving the amount twice. Response (Denied):
A declined or review-required decision includes reasons and reasonCodes. Conto does not queue a review_required payment for a person, so handle it like a decline. x402 decisions use the shared payment reasons. x402 price, endpoint, service and session limits return SPENDING_LIMIT. Blocked or unlisted services and facilitators return RECIPIENT_NOT_ALLOWED.

Recording transactions

With the SDK, call conto.x402.record().
txHash is required. Before recording spend, Conto verifies a successful settlement on the wallet’s configured chain with the exact sender, recipient, asset, and amount. A pending receipt returns SETTLEMENT_PENDING. A mismatched transfer returns SETTLEMENT_MISMATCH. An unavailable RPC returns a temporary service error. Only verified settlements are stored as confirmed. Repeat the same payerAddress and network used for pre-authorization. Conto resolves the pair to one active wallet and uses that wallet for settlement verification and spend tracking.

Grants and policy bypass

Send the grantId and grantSignature from the approved pre-authorization. Conto checks the onchain transfer against the grant’s recipient and amount, not the values in the record request, then marks the grant used. The reserved amount becomes actual spend, so it is counted once. A record without a valid grant means the payment settled without an approval from Conto. Conto still records it, because the money has already moved, but it flags the transaction for review and raises a critical alert to the account owner. bypassReason is GRANT_MISSING, GRANT_INVALID, or GRANT_EXPIRED. agentFrozen is true when Conto froze the agent for this bypass. A frozen agent’s API key is rejected until an owner unfreezes the agent from the dashboard. While that alert is still open, further bypasses by the same agent update it (occurrence count and recent transactions) instead of sending another email.
The grant is a check, not a signing control. An agent that holds its own signing key can still pay without asking Conto. Conto detects that when the payment is recorded. To stop the payment before it is signed, keep the key behind a signer that requires a Conto approval.

Batch recording

To record several calls settled together, send one record with the per-call details in batchItems:
The top-level fields describe the one settlement, and txHash is the transaction that paid for every item. The record endpoint does not accept a top-level payments array. The sum of all batchItems must equal the top-level amount, and the grant must come from a pre-authorization for that same total. Use optional context.department and context.project values during pre-authorization and recording to apply scoped budgets and persist those dimensions on the transaction.

Conto-signed payments (managed wallets)

When the agent’s wallet is a managed EVM wallet, the agent holds no key. Conto approves and signs the payment. Call /api/sdk/x402/pay (conto.x402.pay() in the SDK) instead of pre-authorize, with the same fields plus the accepted entry from the 402 challenge:
Conto makes the same decision as pre-authorize. A declined or review-required payment returns the same body, and nothing is signed. An approved payment is signed as an EIP-3009 TransferWithAuthorization for exactly the approved payee, amount, USDC contract, and chain:
Retry the resource request with the paymentHeaderName header set to xPaymentHeader, then call /api/sdk/x402/record with the grant and the settlement txHash as usual. Send "x402Version": 2 for a v2 challenge. Conto then returns a PAYMENT-SIGNATURE header. Managed signing covers only USDC, the stablecoin that supports EIP-3009. The authorization is valid until the earlier of the grant expiry and maxTimeoutSeconds from now. Each grant is signed once, so pay is not retried automatically. If the payment is never recorded, Conto checks the authorization nonce onchain after it expires: an unused authorization releases the reserved amount, and a used one is recorded as a confirmed payment.
If /api/sdk/x402/pay returns 404, managed signing is off. Use pre-authorize and record instead. After a wallet’s key is exported, whoever holds the exported key can sign without Conto.

Querying services

List the x402 services this agent has paid. Optional period is 24h, 7d (default), 30d, or 90d. Optional limit defaults to 50, max 100. With the SDK, call conto.x402.services({ period, limit }).

Budget tracking

Check the agent’s spend, limits, and burn rate. With the SDK, call conto.x402.budget({ sessionId }).
The response contains the authenticated agent’s aggregate daily, weekly, and monthly spend, effective limits, and usage trend. Those periods use UTC calendar boundaries, include confirming transactions, and count each item in a recorded batch as one call. When sessionId is supplied, spend.session also reports the call count and amount recorded with that customer-defined ID.