{"data":{"name":"PillCrew Public API","description":"A free, keyless, machine-readable index of every PillCrew endpoint: the agent Pilly, live Solana telemetry, on-chain token forensics (contract decode, holder audit, mint launch ledger), trade data, and a Pilly report sold to machines over HTTP 402.","version":"1.0","docs":"/docs","base_url":"https://pillcrew.fun","endpoints":[{"method":"GET","path":"/api","description":"This index - discover the API."},{"method":"GET","path":"/api/agents","description":"The agent as a public card. ?capability=<slug> filters, ?limit & ?offset paginate."},{"method":"GET","path":"/api/agents/:id","description":"The agent's card by id, e.g. /api/agents/Pilly."},{"method":"GET","path":"/api/agents/:id/capabilities","description":"The agent's capability manifest (labels + icon names)."},{"method":"GET","path":"/api/agents/schema","description":"JSON Schema (2020-12) of a public agent card."},{"method":"GET","path":"/api/capabilities","description":"The capability keyspace the agent is scored on."},{"method":"POST","path":"/api/chat","description":"Ask Pilly. Body: { question, agentId?, mint?, history?, locale? }. Returns the answer, the tool trace and the sources. Rate-limited per IP."},{"method":"POST","path":"/api/live-agent","description":"The streaming variant of /api/chat used by the live board."},{"method":"POST","path":"/api/audit","description":"Full token audit for a mint: on-chain contract facts, holder distribution, liquidity and route checks, scored with the findings that produced the score."},{"method":"POST","path":"/api/verdict","description":"Pilly verdict for a mint in one call. Body: { mint } or a posted callout payload."},{"method":"POST","path":"/api/portfolio","description":"Wallet portfolio read on-chain. Body: { wallet }. Returns positions, values and P/L for the addresses it can actually read."},{"method":"GET","path":"/api/chain-health","description":"Live Solana mainnet telemetry read from public RPC: slot & epoch progress, TPS (total and non-vote), slot time, validator counts, activated stake, Nakamoto coefficient and stake-weighted client diversity."},{"method":"GET","path":"/api/token-contract","description":"The mint account decoded byte by byte: base Mint state (authorities, supply, decimals), the Token-2022 TLV extension table with real byte offsets, metadata stored inside the mint, cross-check against the validator's parsed view and the indexed holder audit. ?mint= overrides the default ($PillCrew)."},{"method":"GET","path":"/api/mint-ledger","description":"A mint's whole life from its own reference history: the history is walked back page by page to the oldest transaction the deepest RPC node still has, and that transaction is decoded in execution order. When it is the creation transaction the response carries the launch record (timestamp, creator, initial supply, metadata, the authorities revoked inside it, the creator's opening buy and the SOL that went into the curve) and sets genesis.certified; when a node's index stops short it says so and withholds the launch fields instead of guessing. A certified creation can never change, so it is also kept server-side and re-served as genesis.fromStore (with genesis.certifiedAt) when the nodes will not return that transaction again. activity carries lifetime transaction count, failure rate, first/last activity and a per-UTC-day histogram. ?mint= (aliases ?address=, ?input=) defaults to $PillCrew."},{"method":"GET","path":"/api/buy-quotes","description":"An independent live Jupiter quote for each size in the SOL ladder (0.05-5 SOL) plus priority-fee percentiles observed by RPC for the accounts the order actually writes. ?amount= highlights a rung. Nothing is interpolated: an unroutable size is reported as unavailable."},{"method":"GET","path":"/api/token-trades","description":"The $PillCrew trade tape - real pool swaps, normalised per trade."},{"method":"GET","path":"/api/token-stats","description":"Live price, market cap, 24h change, volume and liquidity for $PillCrew. Multi-source (DexScreener primary, Jupiter price as an independent cross-check); every missing field is null, never a stand-in number."},{"method":"GET","path":"/api/coin-stats","description":"Canonical per-mint snapshot with provenance: ?mint=<addr> for one coin, ?mints=<a,b,c> for a batch. Source order DexScreener -> pump.fun -> Jupiter -> GeckoTerminal."},{"method":"GET","path":"/api/live-prices","description":"Batch live prices for the mints in ?mints=<a,b,c> (comma separated)."},{"method":"GET","path":"/api/candles","description":"OHLCV candles for a mint or pool: ?mint= or ?pair=, plus ?interval=. Served from indexed pools, with the on-chain swap walk as the fallback for mints too new to be indexed."},{"method":"GET","path":"/api/coin","description":"Resolve a mint or a pump.fun link into one coin record (DexScreener -> pump.fun -> Jupiter -> GeckoTerminal). ?input= (aliases ?mint=, ?address=, ?q=)."},{"method":"GET","path":"/api/pair","description":"The most liquid trading pair for a token, as the pairAddress plus that pool's image: ?address= (alias ?mint=) or ?pair=."},{"method":"GET","path":"/api/img","description":"Token avatar/logo resolver: ?mint=<addr> returns the first image that actually resolves, honouring our own art first. ?src= pins one source, ?raw=1 returns the bytes."},{"method":"GET","path":"/api/jup-trending","description":"Jupiter's trending list, enriched and cached. ?force=1 refreshes."},{"method":"GET","path":"/api/pumpfun-trending","description":"Live pump.fun board (trending or a single ?lookup=<mint>)."},{"method":"GET","path":"/api/pumpfun-callouts","description":"Near-real-time stream of brand-new pump.fun launches (new mints only, diffed poll by poll)."},{"method":"GET","path":"/api/trending-callouts","description":"DexScreener trending boosts, enriched with live pair data: price, 24h change, volume, liquidity and market cap."},{"method":"GET","path":"/api/callouts","description":"The /callouts feed. ?mode=trending (default) or ?mode=new."},{"method":"GET","path":"/api/pack","description":"THE WHOLE READING OF ONE MINT, GIVEN AWAY, KEYLESS AND FREE. One request returns every section the desk can measure: market (price, cap, liquidity, volume, the vendor and the second it was captured), contract authority read from the mint account, the holder enumeration with pool vaults labelled and the concentration with and without them, the linked-wallet clusters (wallets sharing a funder or funding each other, summed) plus every wallet that could not be traced and the reason, the decoded genesis (creator, authorities revoked in the same transaction, the opening buy as a share of the initial supply), the supply locks followed to their escrow accounts with the unlock dates and the wallet they pay out to, the provable burns with a Solscan link each, an outside risk score attributed to its vendor, the `gaps` that could not be measured this time with the reason, and the `sources` that produced every field. No key, no account, no trial, nothing held back for a paid tier."},{"method":"GET","path":"/api/gecko","description":"GeckoTerminal pool lookup/passthrough for a mint: ?pools=<n> caps how many pools are returned."},{"method":"GET","path":"/api/actions/buy","description":"Solana Action (Blink) metadata for buying $PillCrew with SOL. POST builds the swap transaction with Jupiter for the signer's wallet."},{"method":"GET","path":"/actions.json","description":"Blink rules file - declares which paths are unfurlable Solana Actions."},{"method":"GET","path":"/api/x402/pilly-report","description":"Pilly report sold through HTTP 402 (x402 protocol v2). With no payment it answers 402 and the PaymentRequired object base64-encoded in PAYMENT-REQUIRED: the accepted offer (0.005 SOL), the receiving wallet and the artifact's field inventory. Retry with PAYMENT-SIGNATURE carrying the settled Solana transaction signature and the artifact is returned as JSON (one payment, one report). No API key, no facilitator, no key custody."},{"method":"GET","path":"/api/x402/holder-pass","description":"The free tier of Pilly report for $PillCrew holders. GET returns the config (threshold, mint, decimals) and GET ?address=<wallet> issues a one-off challenge message to sign; POST { address, nonce, expiresAt, signature } verifies the ed25519 signature server-side (node:crypto, no wallet extension trusted), consumes the nonce first-writer-wins and reads the holder balance live from Solana RPC - below the threshold it answers 403 with the measured held/missing amounts, at or above it serves the full report."},{"method":"GET","path":"/api/x402/verify","description":"Free settlement verifier behind the x402 rail: ?signature=<base58> judges any mainnet transaction against an offer (?asset=, ?payTo=, ?amount=, ?maxAgeSeconds=), and ?sample=1 discovers the newest real inbound transfer to the receiving wallet and judges it twice - at the amount it actually moved and at the endpoint's own price. Returns the measured amount, slot, block time, payer, method and a named refusal reason when it will not count."}],"internal_endpoints":[{"method":"GET","path":"/api/ops","description":"Warm-instance counters for the status page."},{"method":"GET","path":"/api/jup-price","description":"Single-mint live price/mcap proxy (DexScreener -> pump.fun -> Jupiter) used by the price widgets."},{"method":"GET","path":"/api/jup-price-v3","description":"The same resolver, keyed to Jupiter price v3 semantics, for share cards."},{"method":"POST","path":"/api/verdict-share","description":"Signs/verifies the share links behind /verdict/<token>."},{"method":"GET","path":"/api/trader-radar","description":"The launch roster, in two halves that each say where they came from. `traders`: the wallets measured trading the hottest pools right now (GeckoTerminal's public trade feed, a 900-fill sample aggregated by wallet), with volume, fills, buy share and the coins touched; a trader also carries `profile` when that exact address is a creator wallet a coin publishes. `creators`: coins on pump.fun's own board paired with the creator wallet that board names and the X handle that coin's profile links, with market cap and the coin page to check. No list invents a row when its source is down - `unavailable` and `creatorsUnavailable` say so."},{"method":"POST","path":"/api/meme-radar/coined","description":"Reports a launch the desk itself confirmed (key, mint, symbol), so the board flips that narrative to 'taken' with the real pump.fun link immediately instead of waiting for DexScreener to index the pair."},{"method":"POST","path":"/api/pic-search","description":"Picture search behind the radar cards and the launch draft: takes {label, summary} and returns a ranked list of real photos for that narrative (press photo -> Wikipedia page image -> the subject the AI resolves for a slogan), each with the source it came from."},{"method":"GET","path":"/api/agent/numbers","description":"The trade-plan arithmetic behind the chat, published. `?mint=` returns the live price and market cap, the three plan levels the chat is given (spot, a stop 8% below it, a target 16% above it) and each level's market cap, plus four `checks` that hold the plan to its own definition: the levels bracket the spot price, the stop is exactly 8% below it, each cap is the live cap scaled by that level's price, and the risk/reward is exactly 2:1. A model never derives a level itself - this is the function the answer copies from."},{"method":"GET","path":"/api/*","description":"Anything else returns the same JSON error envelope, never an HTML page."}],"auth":"none","cors":"any origin","errors":"{ error: { code, message } } - every failure, including unknown paths, returns JSON."},"meta":{"version":"1.0","generated_at":"2026-11-07T01:59:12.125Z","rate_limit":{"limit":10,"window_seconds":60}}}