> ## Documentation Index
> Fetch the complete documentation index at: https://docs.credprotocol.com/llms.txt
> Use this file to discover all available pages before exploring further.

# Machine Payments (x402 & MPP)

> Pay per request — no account required — with x402 (USDC on Base/SKALE/Tempo) or the Machine Payments Protocol (Tempo, Stripe crypto deposits, or reputation-backed Cred credit)

Every paid Cred Protocol endpoint is **machine payable**. An agent that calls a paid endpoint with no credentials gets back a `402 Payment Required` that advertises three ways to pay; it picks one, attaches the payment to the retry, and gets the data. Nothing to sign up for.

<CardGroup cols={3}>
  <Card title="API key" icon="key" href="/guides/authentication">
    Metered against a plan. `Authorization: Bearer <api_key>`
  </Card>

  <Card title="x402" icon="coins" href="#x402">
    USDC on Base, SKALE or Tempo. `X-PAYMENT: <signed payment>`
  </Card>

  <Card title="MPP" icon="robot" href="#mpp-machine-payments-protocol">
    Tempo, Stripe crypto deposit, or Cred credit. `Authorization: Payment <credential>`
  </Card>
</CardGroup>

## Pricing

Everything is priced in **Cred Units (CU)**, 1 CU = **\$0.01**. The same price applies whether you pay with an API key, x402 or MPP.

| Endpoint                                                                 | Method | CU            | Price       |
| ------------------------------------------------------------------------ | ------ | ------------- | ----------- |
| `/api/v2/score/address/{address}`                                        | GET    | 1             | \$0.01      |
| `/api/v2/score/address/{address}` (enhanced, off-chain data)             | POST   | 3             | \$0.03      |
| `/api/v2/score/` (aggregated) · `/api/v2/score/batch/`                   | GET    | 1 per address | \$0.01/addr |
| `/api/v2/report/address/{address}`                                       | GET    | 7             | \$0.07      |
| `/api/v2/report/address/{address}` (enhanced)                            | POST   | 10            | \$0.10      |
| `/api/v2/report/` (aggregated)                                           | GET    | 7             | \$0.07      |
| `/api/v2/report/address/{address}/summary`                               | GET    | 5             | \$0.05      |
| `/api/v2/report/address/{address}/chain/{chain_id}`                      | GET    | 3             | \$0.03      |
| `/api/v2/report/address/{address}/chain/{chain_id}/summary`              | GET    | 1             | \$0.01      |
| `/api/v2/report/address/{address}/total/usd` (+ `/aggregate`)            | GET    | 4             | \$0.04      |
| `/api/v2/report/address/{address}/chain/{chain_id}/total/usd`            | GET    | 2             | \$0.02      |
| `/api/v2/identity/address/{address}/attestations`                        | GET    | 1             | \$0.01      |
| `/api/v2/identity/address/{address}/sybil`                               | GET    | 3             | \$0.03      |
| `/api/v2/agents/{agent_id}/reputation` (submit on-chain feedback)        | POST   | 10            | \$0.10      |
| `/api/v2/agents/{agent_id}/reputation/summary`                           | GET    | 1             | \$0.01      |
| **Validator** `https://validator.credprotocol.com/v1/validate/{address}` | POST   | —             | \$0.05      |

Agent-registry reads (`/api/v2/agents`, `/agents/count`, `/agents/search`, `/agents/{id}`) and `/api/v2/health` are free. The `/mcp/*` REST endpoints and MCP tools use the same prices — see [MCP Services](/mcp-services/overview) and `GET https://api.credprotocol.com/mcp/tools`.

## The 402 response

Call any paid endpoint without credentials:

```bash theme={null}
curl -i https://api.credprotocol.com/api/v2/score/address/vitalik.eth
```

```http theme={null}
HTTP/2 402
X-Payment-Methods: x402,tempo,stripe,cred
X-PAYMENT-REQUIRED: <base64 x402 PaymentRequirements>
WWW-Authenticate: Payment id="ch_9a39…", realm="api.credprotocol.com", method="tempo",  intent="charge", request="<base64url>",
                  Payment id="ch_1f86…", realm="api.credprotocol.com", method="cred",   intent="credit", request="<base64url>",
                  Payment id="ch_4ca5…", realm="api.credprotocol.com", method="stripe", intent="charge", request="<base64url>"
```

```json theme={null}
{
  "detail": {
    "error": "authentication_required",
    "cred_units": 1,
    "options": [
      { "method": "api_token",    "header": "Authorization: Bearer YOUR_API_KEY", "cost": "1 Cred Units" },
      { "method": "x402_payment", "header": "X-PAYMENT: <signed_payment>", "price": "$0.01", "currency": "USDC" },
      { "method": "mpp",          "header": "Authorization: Payment <credential>", "price": "$0.01", "spec": "https://mpp.dev" }
    ]
  }
}
```

The body is human/LLM readable; the headers are what payment SDKs consume. Pick whichever rail your agent supports and retry.

## x402

[x402](https://docs.cdp.coinbase.com/x402/welcome) is a one-round-trip USDC micropayment. The `X-PAYMENT-REQUIRED` header carries base64 `PaymentRequirements` (scheme `exact`, price in USDC, `payTo` address, one entry per accepted network). Sign a USDC transfer authorization with your wallet and retry with it in `X-PAYMENT`; the payment settles through the facilitator during the request and the response includes `X-Payment-Transaction` / `X-Payment-Network`.

**Networks:** Base (8453), Base Sepolia (84532), SKALE Base (1187947933), SKALE Base Sepolia (324705682), and Tempo. SKALE is gasless with sub-second finality.

<CodeGroup>
  ```javascript JavaScript (x402 SDK) theme={null}
  import { x402Client } from 'x402';

  const client = new x402Client({ wallet, network: 'base' });
  // Automatically answers the 402 and retries with X-PAYMENT
  const res = await client.fetch(
    'https://api.credprotocol.com/api/v2/score/address/vitalik.eth'
  );
  console.log(await res.json());
  ```

  ```python Python (manual) theme={null}
  import base64, requests

  url = "https://api.credprotocol.com/api/v2/score/address/vitalik.eth"
  r = requests.get(url)
  if r.status_code == 402:
      requirements = base64.b64decode(r.headers["X-PAYMENT-REQUIRED"])
      signed = sign_usdc_transfer(requirements)          # your wallet
      r = requests.get(url, headers={"X-PAYMENT": signed})
  print(r.json(), r.headers.get("X-Payment-Transaction"))
  ```
</CodeGroup>

Full details, including per-network USDC contracts, are in the [x402 section of the Authentication guide](/guides/authentication#x402-payment-authentication). Try it interactively at [credprotocol.com/try](https://credprotocol.com/try).

## MPP (Machine Payments Protocol)

[MPP](https://mpp.dev) uses standard HTTP auth semantics: the server lists **challenges** in `WWW-Authenticate: Payment …`, the client fulfils one and sends the resulting **credential** in `Authorization: Payment <base64url>`, and the server returns a **receipt** in the `Payment-Receipt` response header.

Each challenge has an `id`, a `method`, an `intent` (`charge` or `credit`) and a base64url `request` describing what to pay:

| method   | intent | `request` (decoded)                                                                                                                                            | How you pay                                                                                                                                                                                 |
| -------- | ------ | -------------------------------------------------------------------------------------------------------------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- |
| `tempo`  | charge | `{"amount":"10000","currency":"<USDC contract>","recipient":"0xD750…","methodDetails":{"chainId":4217}}`                                                       | Send USDC (6 decimals) on Tempo (chain 4217) to `recipient`. Credential payload: the signed transaction (pull) or the tx hash (push).                                                       |
| `stripe` | charge | `{"amount":"0.01","currency":"usd","stripeDetails":{"networkId":"tempo","paymentMethodTypes":["crypto"],"depositAddress":"0x5e8f…","paymentIntentId":"pi_…"}}` | Send USDC on Tempo to the Stripe crypto `depositAddress` (a PaymentIntent is pre-created for you). Credential payload: `{"txHash": "...", "paymentIntentId": "pi_…"}`.                      |
| `cred`   | credit | `{"amount":"0.01","currency":"usd","recipient":"0xD750…","minCredScore":640,"creditTerms":"session"}`                                                          | No transfer up front. Prove wallet ownership with an EIP-712 signature; wallets with a Cred Score ≥ 640 get session credit, settled later via an EIP-3009 `transferWithAuthorization` pull. |

The credential you send back is:

```json theme={null}
{
  "challenge": { "...the challenge object you are answering, verbatim..." },
  "source": "0xYourWallet",
  "payload": { "...method-specific, see table..." }
}
```

base64url-encoded into `Authorization: Payment <credential>`.

<CodeGroup>
  ```python Python (Cred credit — reputation-backed, no pre-funding) theme={null}
  import base64, json, requests, re

  URL = "https://api.credprotocol.com/api/v2/score/address/vitalik.eth"

  r = requests.get(URL)                                    # 402
  challenges = parse_www_authenticate(r.headers["WWW-Authenticate"])
  ch = next(c for c in challenges if c["method"] == "cred")

  payload = {
      "walletAddress": WALLET,
      "walletSignature": sign_eip712_ownership(WALLET, ch),   # your wallet
      "timestamp": now_iso(),
      # optional: "eip3009Authorization": {...} for pull-payment settlement
  }
  credential = base64.urlsafe_b64encode(json.dumps(
      {"challenge": ch, "source": WALLET, "payload": payload}
  ).encode()).rstrip(b"=").decode()

  r = requests.get(URL, headers={"Authorization": f"Payment {credential}"})
  print(r.status_code, r.json())
  print("receipt:", r.headers.get("Payment-Receipt"))
  ```

  ```bash cURL (Tempo push — pay first, then present the tx hash) theme={null}
  # 1. Read the tempo challenge from the 402
  curl -si https://api.credprotocol.com/api/v2/score/address/vitalik.eth | grep -i www-authenticate

  # 2. Send 10000 units of USDC on Tempo (chainId 4217) to the recipient in the challenge

  # 3. Retry with the credential (challenge + payload with the tx hash), base64url-encoded
  curl https://api.credprotocol.com/api/v2/score/address/vitalik.eth \
    -H "Authorization: Payment $CREDENTIAL"
  ```
</CodeGroup>

**Receipts.** Successful paid responses include `Payment-Receipt: <base64url>` decoding to `{"status":"success","challengeId":"ch_…","method":"tempo","reference":"<tx hash or ref>","timestamp":"…"}`.

**MPP over MCP.** The MCP server (`https://api.credprotocol.com/mcp`) speaks the MPP MCP transport: a paid tool called without credentials returns JSON-RPC error `-32042` whose `data` is the challenge; put the credential in `_meta["org.paymentauth/credential"]` on the retried `tools/call` and the receipt comes back in the result's `_meta["org.paymentauth/receipt"]`. See [MCP Services](/mcp-services/overview).

## Validator (ERC-8004 trust assessments)

`POST https://validator.credprotocol.com/v1/validate/{address}` is \$0.05 and accepts x402 (USDC on Base) and Cred credit; `GET /v1/payment-methods` lists what's currently enabled. See [ERC-8004 Validation](/erc-8004-validation).

## Choosing a rail

* **You already have a plan** → API key. Simplest, and usage shows up in the [console](https://app.credprotocol.com/dashboard/console).
* **Autonomous agent with a funded wallet** → x402 (Base/SKALE/Tempo) or MPP `tempo`. One request, settles inline.
* **Agent that can't hold crypto** → MPP `stripe` (USDC deposit on Tempo via a Stripe-managed address).
* **Agent with on-chain reputation but no float** → MPP `cred`: a Cred Score ≥ 640 unlocks session credit, settled afterwards.

Errors: `402` = no/insufficient payment (body explains); `401` = credentials present but invalid; `429` = rate limited. See [Error Handling](/guides/error-handling).
