---
name: capacitr
description: "WHAT: Call Capacitr's paid Signals API on app.capacitr.xyz — submit a URL/post/question, read the signals feed, or read one market's narratives — paying per call over x402 (USDC on Base) or MPP (pathUSD on Tempo). WHEN: an agent needs market signals, ranked prediction-market/perp trades for a piece of news, or wants to pay for an x402/MPP-gated endpoint. KEYWORDS: capacitr, x402, mpp, tempo, signals, payment required, 402, USDC, Base, prediction markets, polymarket, hyperliquid"
---

# Capacitr Signals API (x402)

Capacitr exposes a pay-per-call Signals API at `https://app.capacitr.xyz`. Three paid routes, one payment protocol per chain, no accounts and no API keys — payment IS the credential.

| Route | What it does | Auth |
|---|---|---|
| `GET /api/x402/routes` | The live route registry: endpoints, prices, rails, limits. | Free |
| `GET /api/x402/agent-instructions` | The full integration spec as a Markdown download. | Free |
| `GET /api/x402/signals/sample` | A canned feed page in the exact paid shape (`sample: true`). Build your parser against this before spending anything. | Free |
| `GET /api/x402/signals` | Read one page of Signals Capacitr has already produced. | Paid |
| `POST /api/x402/signals` | Submit a URL, post, article or question; get back the Feed Card of matched markets and ranked trades. | Paid |
| `GET /api/x402/markets/narratives` | Every narrative Capacitr has linked to ONE market (Hyperliquid, Robinhood, Polymarket): direction, rationale, source. | Paid |

Nothing else under `/api/x402/` exists — a route that is not in the registry is not offered. The registry lists only live routes; planned kinds never appear as callable. `/api/research`, `/api/skill/discovery` and `/api/analyze-link` are a different (skill-key/Privy) surface, not part of this API.

## The flow: discover → 402 → settle → retry

Every paid call is the same four steps:

1. **Discover** — `GET /api/x402/routes` for the current routes, rails, prices and limits.
2. **Ask** — request the paid route with no credential. The response is `402` + `application/problem+json`, carrying the payment requirements in headers.
3. **Settle** — pick one accept from the challenge, validate it (chain, token, recipient, amount vs. the caller's spend limit), sign the payment, and broadcast/settle per the rail's rules.
4. **Retry** — resend the IDENTICAL request with the credential header added. `200` carries the body plus a settlement-receipt header. Confirm the on-chain transfer.

```bash
# 1 · Discover — free
curl -s https://app.capacitr.xyz/api/x402/routes | jq .

# 2 · Ask — free 402, headers carry the requirements
curl -si "https://app.capacitr.xyz/api/x402/signals?limit=5" \
  | grep -iE '^(payment-required|www-authenticate):'

# 3 · Decode the x402 challenge (signing detail in references/payment-protocol.md)
curl -si "https://app.capacitr.xyz/api/x402/signals?limit=5" \
  | awk '/^payment-required:/ {print $2}' | tr -d '\r' | base64 -d | jq .

# 4 · Retry with the signed credential — same URL, one extra header
curl -s "https://app.capacitr.xyz/api/x402/signals?limit=5" \
  -H "PAYMENT-SIGNATURE: $PAYMENT_SIGNATURE" | jq .

# POST works identically — body is validated free BEFORE any 402 is minted
curl -si -X POST https://app.capacitr.xyz/api/x402/signals \
  -H 'content-type: application/json' \
  -d '{"input":"https://x.com/...","mode":"discover"}'

# One market's narratives — same flow, market in the query string
curl -si "https://app.capacitr.xyz/api/x402/markets/narratives?marketType=trade&marketSource=hyperliquid&marketId=BTC"

# Free sample — exact paid shape, no wallet needed
curl -s https://app.capacitr.xyz/api/x402/signals/sample | jq .
```

## Payment rails

| Protocol | Chain | Token | Challenge header | Credential header | Receipt header |
|---|---|---|---|---|---|
| x402 | Base `eip155:8453` | USDC | `PAYMENT-REQUIRED` | `PAYMENT-SIGNATURE` | `PAYMENT-RESPONSE` |
| MPP | Tempo `eip155:4217` | pathUSD | `WWW-Authenticate: Payment …` | `Authorization: Payment …` | `Payment-Receipt` |
| x402 (test rail) | Base Sepolia `eip155:84532` | USDC testnet | second entry in `accepts[]` — `GET` feed only | `PAYMENT-SIGNATURE` | `PAYMENT-RESPONSE` |

The test rail is a deliberately restricted preview for exercising payment plumbing with faucet USDC: ≤5 cards/page, ≤2 pages, items ≥48h old. Responses mark it `preview: true` and `payment.test_rail: true`. Pick an accept by `network`, never by position in `accepts[]`.

## Rules

- **Get the price from the live challenge, not from this doc or the registry.** Registry prices are the operator-set book — the 402's `accepts[]` is what will actually be charged. Check chain, token, `payTo` and `amount` before signing.
- **Ask the user first.** Before paying, collect the input and a maximum spend per call, show the rails the challenge returned, and wait for the user to choose. Never auto-pick a chain.
- **One payment = one response.** A feed page costs one payment; pass `nextCursor` back as `?cursor=` and pay again for the next page.
- **Re-present a settled credential freely, with the request it paid for.** After a network drop, resend the same credential and the same request — the body replays without a second charge. On `/api/x402/markets/narratives` the query is part of what was bought: presenting the credential with a different market or a different page is `409`, not a free second page. Never reuse a nonce for a NEW payment.
- **Free validation failures stay free.** A `400` is answered before any 402 is minted (missing `input`, bad `cursor`, non-numeric `limit`).
- **402 after paying = rejection.** Read the problem body's `type` and the re-challenge's `error` field for the reason.
- **503 `feed-unavailable` + `Retry-After` = the server failed after charging.** The payment is marked `refund_due` and refunded out of band. Retry after the interval.
- **Rate limits:** 120 challenge mints/min per IP; 3 paid submits per payer per 300s; 60 paid feed reads and 60 paid narratives reads per payer per 60s. A `429` carries `Retry-After`.

## Request / response shapes

**`POST /api/x402/signals`** — body `{ "input": "…", "mode": "discover" }`. `input` is a string and required; `url` and `query` are accepted aliases for it. `mode` is `discover` (default) or `hedge`. Response is a Feed Card: `title`, `subtitle`, `narratives`, `categories`, `tags`, `publishedAt`, `bestTrade`, `otherTrades`, plus `recommendedTrades` (all trades ranked, best first — each with `marketType`, `marketSource`, `marketId`, `marketTitle`, `suggestedDirection`, `confidence`, `quoteSnapshot`, and `signalPrice` when the source is dated), `input`, `reused`, and the `payment` block.

**`GET /api/x402/signals`** — query `?q=` (string, keyword filter), `?limit=` (integer 1–10, default 10), `?cursor=` (opaque, `nextCursor` from a previous page), `?venues=` (comma-separated; only `agg` does anything). Response `{ signals: [...same card shape...], nextCursor, payment }`. `nextCursor: null` means the feed is exhausted.

**`GET /api/x402/markets/narratives`** — three required query params, all strings: `marketType`, `marketSource` and `marketId`. The venue decides the type, so only three pairs exist: `trade`+`hyperliquid` (coin, e.g. `BTC`), `trade`+`robinhood` (token contract address) and `bet`+`polymarket` (conditionId) — the same `marketId` a Signal's trades carry. `agg` and `basestocks` are not served here, and any other pairing is a free `400`. Optional: `facet` (an id from the response's `facets` — `all`, `direction:bullish|bearish|neutral` on perps and stocks, `direction:yes|no` or outcome ids on Polymarket), `limit` (integer 10–15, default 10), `cursor` and `newerThan` (opaque cursors from a previous response), `includeSignalId` (`1|0|true|false`). Response `{ narratives: [...], facets, nextCursor, firstCursor, newerResultsAvailable, payment }`; each narrative has `title`, `direction`, `subject`, `rationale`, `sourceExcerpt`, `source`, `publishedAt`, `sourceDestination`, `linkedMarket`. Use it after a Signal to dig into one of its trades' markets.

Every paid response ends with `payment`: `{ protocol, method, chain_id, currency, currency_address, amount, payer, test_rail }`.

## Full reference

- `references/endpoints.md` — per-endpoint parameters, response fields, limits and status codes.
- `references/payment-protocol.md` — challenge decoding, EIP-3009 signing, MPP on Tempo, replay and failure semantics, SDK quickstart.
