跳到正文
DEV Community· Conclave x402 Research·· 3 小時前AI 評分55

研究測量 22,013 個 x402 端點:目錄比預期更新,卻很少説明實際回應內容

We measured 22,013 x402 endpoints: the catalogue is fresher than we thought, but it rarely tells you what you'll get

AI 導讀

Conclave x402 Research 檢查 22,013 個 x402 目錄項目,發現抽查的端點多數符合目錄描述,但輸出説明及實際付款選項常不完整。在 100 個即時端點樣本中,93 個回覆 402,其中 83 個(89.2%)與目錄描述完全相符;兩個公開目錄只有 4,190 個資源重疊,重疊項目中 84.4% 記錄的付款選項數目不同。

正文

There is now a public catalogue of x402-payable HTTP endpoints at facilitator.payai.network/discovery/resources. If you are building an agent that pays for API calls, that catalogue is how your agent finds sellers. So we asked a simple question, and measured the whole thing rather than sampling a handful of famous sellers:

When the catalogue describes a resource, does the resource actually behave that way?

Short answer: mostly yes — more than we expected. But the catalogue is much weaker at telling you what you'll get than at telling you that it costs something.

Method

  • Fetched all 22,013 rows from the facilitator's discovery endpoint, plus the full 28,423-row Coinbase CDP discovery catalogue (paged, no payment, no keys).
  • For a random 100-row live sample, called each row with the method it declares (POST bodies sent as {}; rows with path templates like /inbox/:id excluded, because you cannot call them without parameters).
  • For each 402 response, compared the stored extensions.bazaar.info.output against the live one, and checked where the payment requirements were advertised (header vs JSON body).
  • Separately, a demand-stratified sample of 120 live 402 responses for the header/body question.

Everything below is reproducible with plain HTTP GETs. No purchases were made.

What the catalogue publishes (all 22,013 rows)

what a row says about the output rows share
a descriptor: {type: "json", example: {...}} 16,615 75.5%
an answer-instance (a real body) 237 1.1%
nothing at all 5,161 23.4%

Separately, 73.7% of rows carry a JSON Schema for their output (schema.properties.output.required).

Two things follow. First, nearly a quarter of catalogue rows publish no description of their output — a buyer cannot tell whether the call returns {ok: true, result: …}, a bare array, or an error envelope. Second, of the rows that do say something, 98.6% say it as an example rather than a schema-validated contract.

Does the catalogue lie? (live sample, n=100)

  • 93 of 100 answered 402 Payment Required when called with their declared method.
  • Of those 93, 83 (89.2%) matched their stored description exactly; 10 (10.8%) mismatched — and every mismatch was the same benign direction: the catalogue said nothing, and the live endpoint served a descriptor.
  • 7 of 100 did not answer a 402 at all: two 308 redirects, two 410 Gone, one 403, one 400, one response with no payment header.

So the headline "the x402 catalogue is 90% accurate" is roughly right, and the failure that actually costs a buyer time is not dishonesty — it is absence and drift: 23% publish no output description, and 7% are unreachable exactly as catalogued.

There is a second catalogue, and the two disagree

Everything above is the facilitator.payai.network catalogue. While checking one of its rows we found that Coinbase publishes a different x402 discovery catalogue at api.cdp.coinbase.com/platform/v2/x402/discovery/resources. So we fetched that one too (28,423 rows, paged, no key):

facilitator catalogue Coinbase (CDP) catalogue
rows 22,013 28,423
distinct resources 21,952 28,421
distinct hosts 1,283 2,712

They are not two views of the same list. The overlap is 4,190 resources — 14.7% of the CDP catalogue and 19.1% of the facilitator one. Across both there are 46,183 distinct x402 resources on 3,704 hosts. Which catalogue your agent reads therefore decides which sellers your agent can see at all.

They also disagree about the sellers they share:

  • Every facilitator row stores exactly one payment option (22,013 of 22,013), even when the live 402 offers several.
  • Half of the CDP rows store more than one (14,165 of 28,423, 49.8%).
  • Of the 4,190 resources in both, 84.4% have a different number of payment options — and in every case the CDP row lists more.

Our own two rows are the clearest example: the facilitator catalogue indexes them as Base-only, while the CDP catalogue stores Base and Polygon for the same URLs — and the live 402 we serve offers both. If you picked "Base-only" from the facilitator row, you would be wrong about a seller that accepts two rails.

The same rows also differ in freshness: on the CDP catalogue our two rows still carry a lastUpdated of 2026-10-14 and describe the output as an example, while we re-indexed the facilitator copies today. A seven-day-old row is not a lie — nothing told the second catalogue that anything changed — but a buyer who trusts it is reading last week's endpoints.

None of this is malicious. It is what happens when a "directory" is really several independent crawlers with different storage models, and it has a practical consequence: before you pay, resolve the seller from the live 402, not from whichever catalogue you happened to load.

The header is the de-facto standard

x402 v2 lets a seller advertise payment requirements in the PAYMENT-REQUIRED response header (base64url JSON) and/or in the 402 JSON body. In the 120 live 402 responses we examined:

  • 120/120 advertised the requirements in the header. Not one response omitted it.
  • 40/120 (33%) did not repeat accepts in the JSON body.

That split is not uniform: 45% of high-demand sellers omit accepts from the body, 44% of low-demand ones do, but only 14% of mid-demand ones do. If you are writing a client, read the header; if you are writing a body-only parser, you will silently see "no accepts" on a third of the ecosystem — and about half of the busiest sellers.

What this means if you build agents

  1. Call the method the catalogue declares. A large share of high-value rows are POST; probing them with GET yields 405 or 400 with no payment header, so the endpoint looks dead when it is not. We made this mistake first: a GET-only scan of our own 42 catalogue rows called 26 of them — 62% — "no payment challenge". All 26 are POST routes that return a proper 402 when asked with the method they declare.
  2. Parse PAYMENT-REQUIRED, not just the body. The header is universal; the body is not.
  3. Know which catalogue you are reading. The two public catalogues overlap on only 15% of resources and disagree about payment options on most of the ones they share; resolving the live 402 is the only way to see what a seller really accepts.
  4. Do not trust amount in the catalogue as a price. On some rails (gift cards, top-ups) the number is the value of the thing being bought, not the fee for the API call. Read the challenge for that call, not the catalogue row.

A note on what we did not measure

We did not measure revenue, and we are not claiming any. This is a catalogue-health study: what sellers publish, what they serve, and where a buyer's parser will break. It says nothing about whether any given endpoint is worth its price.

If you run an x402 endpoint, reply with its URL and I will run the same check on it — method-aware, header-aware, no purchase — and tell you what a naive client sees. That is free, in this thread, and takes about a minute per endpoint.

Method and raw counts are reproducible; if there is interest I will publish the scripts and the sampled row IDs.

來源:DEV Community · dev.to