Comment un agent IA paie une recherche web à l'appel avec x402

Sans compte ni clé API : le vrai challenge 402 renvoyé par FastAF, le client Node qui le paie en USDC sur Base, et comment plafonner ce que l'agent peut dépenser par appel.

Un agent qui a besoin d’une seule recherche Google ne devrait pas avoir à passer par un formulaire d’inscription, une clé API rangée dans un gestionnaire de secrets et un solde prépayé. Avec x402, il envoie la requête, reçoit un prix en retour, le paie depuis son propre wallet et obtient les données. Voici l’aller-retour complet face à FastAF, avec le vrai challenge et le vrai code client.

Qu’est-ce que x402 ?

x402 fait revivre le statut HTTP 402 Payment Required, resté inutilisé dans la spécification pendant des décennies. Le serveur répond à une requête non payée par un 402 accompagné d’un prix lisible par une machine ; le client paie et relance la même requête. Dans la version 2 du protocole, tout cela passe par trois en-têtes, chacun contenant du JSON encodé en base64 : PAYMENT-REQUIRED (du serveur vers le client, le prix), PAYMENT-SIGNATURE (du client vers le serveur, le paiement signé) et PAYMENT-RESPONSE (du serveur vers le client, le résultat du règlement), comme le décrit docs.x402.org, consulté le 19 octobre 2026.

Le paiement lui-même est un transfert de stablecoin, en pratique de l’USDC sur Base. Le client signe une autorisation ; un facilitateur la vérifie par rapport aux exigences du serveur et la soumet on chain. La documentation du facilitateur le dit explicitement : il « ne détient pas de fonds et n’agit pas comme dépositaire ». Le protocole a été incubé chez Coinbase puis confié à la x402 Foundation, sous l’égide de la Linux Foundation, une annonce faite le 2 avril 2026, et il est sous licence Apache-2.0.

À quoi ressemble le challenge 402 ?

Chaque endpoint FastAF est disponible sous https://api.fastaf.co/x402/v1/{endpoint} avec les mêmes paramètres que l’API à clé. La première requête ne coûte rien :

curl -i "https://api.fastaf.co/x402/v1/serp?query=x402+payment+protocol"

Le 19 octobre 2026, la réponse est revenue en HTTP/2 402 en 0,24 seconde. Le décodage de l’en-tête payment-required donne (version abrégée) :

{
  "x402Version": 2,
  "accepts": [{
    "scheme": "exact",
    "network": "eip155:8453",
    "amount": "5000",
    "asset": "0x833589fCD6eDb6E08f4c7C32D4f71b54bdA02913",
    "payTo": "0x05B75e13f071A09A26B50a18Ce5BD02a0755d76F",
    "maxTimeoutSeconds": 300,
    "extra": { "name": "USD Coin", "version": "2" }
  }]
}

Champ par champ :

  • scheme: "exact" : payer exactement ce montant, pas plus.
  • network: "eip155:8453" : le mainnet de Base, en notation CAIP-2.
  • amount: "5000" : en unités atomiques. L’USDC a 6 décimales, donc 5000 correspond à 0,005 $, le prix d’une recherche.
  • asset : le contrat USDC sur Base. La table des assets par défaut du SDK lui-même indique la même adresse pour l’USDC.
  • payTo : l’adresse qui reçoit le paiement.
  • maxTimeoutSeconds: 300 : l’autorisation signée est valable cinq minutes.
  • extra.name et extra.version : le domaine EIP-712 du token, dont le client a besoin pour signer une autorisation de transfert valide.

Un détail à connaître : les paramètres sont validés avant qu’un prix ne soit annoncé. La même URL sans q a renvoyé 400 invalid_parameters, et non un 402 : un agent n’est donc jamais invité à payer pour une requête mal formée.

Comment l’agent le paie-t-il en Node ?

Les paquets officiels se chargent de l’analyse, de la signature et de la relance. Les versions ci-dessous sont les versions actuelles sur npm (@x402/fetch 2.28.0, avec @x402/core et @x402/evm à la même version) :

import { wrapFetchWithPayment } from "@x402/fetch";
import { x402Client } from "@x402/core/client";
import { registerExactEvmScheme } from "@x402/evm/exact/client";
import { privateKeyToAccount } from "viem/accounts";

const client = new x402Client();
registerExactEvmScheme(client, {
  signer: privateKeyToAccount(process.env.AGENT_WALLET_KEY),
  networks: ["eip155:8453"],
});

// Refuser tout paiement unitaire supérieur à un centime.
client.setSpendControls({ maxAmountPerPayment: "$0.01" });

// Refuser de payer une fois que cette exécution a dépensé 0,05 $ (unités atomiques USDC).
let spent = 0n;
client.onBeforePaymentCreation(async ({ selectedRequirements }) => {
  const amount = BigInt(selectedRequirements.amount);
  if (spent + amount > 50_000n) return { abort: true, reason: "run budget exhausted" };
  spent += amount;
});

const fetchWithPayment = wrapFetchWithPayment(fetch, client);
const res = await fetchWithPayment("https://api.fastaf.co/x402/v1/serp?query=x402+payment+protocol");
console.log(res.status, res.headers.get("X-FastAF-Credits-Used"));

Sans setSpendControls, @x402/core plafonne déjà chaque paiement à DEFAULT_MAX_AMOUNT_PER_PAYMENT, qui vaut "$1" dans le code source installé. Pour une API de recherche, c’est bien trop généreux ; réglez-le sur le coût de votre appel le plus cher.

Nous avons exécuté ce script le 19 octobre 2026 avec un wallet fraîchement généré et sans USDC : aucun appel payant n’a donc abouti, et la réponse 200 avec le reçu PAYMENT-RESPONSE correspond à ce que fait le SDK avec un wallet approvisionné. Ce qui s’est réellement passé : avec le plafond à $0.002, le SDK a refusé localement en 91 ms, avant de signer quoi que ce soit (« rejected by spendControls.maxAmountPerPayment »). Avec le plafond à $0.01, il a analysé le 402, signé, relancé, et le serveur a de nouveau répondu 402 avec invalid_exact_evm_insufficient_balance. Aucune recherche n’a été lancée et rien n’a été réglé.

Pourquoi le « réglé uniquement en cas de succès » compte-t-il pour les agents ?

Les agents ratent beaucoup d’appels : une mauvaise requête, une page qui expire, une cible non autorisée. Sur FastAF, le paiement signé n’est réglé qu’après le succès de la requête en amont. Si l’appel échoue, l’autorisation n’est jamais soumise et expire au bout de maxTimeoutSeconds, et le wallet garde son argent. L’API à clé suit la même règle : les requêtes échouées ne sont jamais facturées.

Les prix correspondent au coût en crédits de l’API à clé, à 0,001 $ le crédit. Ces montants ont été relevés sur des challenges en direct le 19 octobre 2026 :

Requête Crédits Montant x402 Prix
/scrape, page statique 1 1000 0,001 $
/serp, recherche Google 5 5000 0,005 $
/shopping 10 10000 0,01 $
/linkedin profil 60 60000 0,06 $

Quand les crédits prépayés sont-ils le meilleur choix ?

x402 convient à un agent qui fait des appels occasionnels, qui tourne là où vous ne pouvez pas provisionner de clé, ou qui doit payer sur son propre budget. Les crédits prépayés l’emportent dans trois cas :

  • Le volume. Un pack prépayé Starter à 10 $ donne 20 000 crédits, donc 1 000 recherches coûtent 2,50 $ au lieu de 5,00 $ via x402, et 1,50 $ avec le pack Pro. Les crédits restent valables 12 mois, sans abonnement.
  • MCP. Le serveur MCP hébergé sur https://api.fastaf.co/mcp s’authentifie avec une clé Bearer ; il n’accepte pas les paiements x402.
  • Un plafond strict sur le compte. Un solde épuisé renvoie 402 insufficient_credits et tout s’arrête, quoi que décide l’agent. L’article sur le plafond de dépense montre comment combiner cela avec un budget par exécution.

Comment protéger le wallet de l’agent ?

La clé privée se trouve dans l’environnement de l’agent et signe sans demander l’avis de personne : traitez-la comme un hot wallet.

  • Utilisez un wallet dédié par agent, jamais un wallet qui contient autre chose.
  • Approvisionnez-le par petites sommes et rechargez-le délibérément ; le solde représente votre pire scénario.
  • Réglez maxAmountPerPayment sur le prix de votre appel le plus cher, et ajoutez un budget par exécution dans le hook.
  • Fixez networks à eip155:8453 pour que le client ne paie jamais sur une chaîne que vous n’aviez pas prévue.

En bref

x402 transforme une réponse 402 en étiquette de prix : décoder PAYMENT-REQUIRED, signer l’autorisation USDC, relancer avec PAYMENT-SIGNATURE. Sur FastAF, une recherche coûte 0,005 $, réglée uniquement si elle aboutit, et les contrôles de dépense du SDK plafonnent chaque paiement avant que quoi que ce soit ne soit signé. Le flux complet se trouve dans la section x402 et tous les prix sont sur la page tarifs. Pour le volume ou MCP, créez un compte gratuit et commencez avec 500 crédits, sans carte.