Read API

The endpoints below are open to anyone: no key, no sign-up, CORS open to any origin. Where the API and the chain disagree, the chain is right.

Base URL

https://api.agiartificialgatointelligence.com/api

Responses are JSON: ok: true on success, or { "ok": false, "error": "..." } with a 4xx or 5xx status. Reads are GET; the writes at the end of the list are POST. Amounts are in the quote asset, and the dollar rates are in /api/stats. One exception: in the pool of a listed token ($AGI), the hook takes the fee of a buy in the token, so fee and tax of those buys in /api/trades are token units.

Endpoints

GET /api/stats
Protocol totals, the last 30 days of volume and launches, top tokens and creators, and the USD rate of each quote asset under prices, the source of every dollar figure on the site.
GET /api/launches
The launch list. ?limit= 1-200 (default 50), ?offset=, ?sort= newest | progress | volume | holders | trending (24 h volume in dollars). Each token carries its price, phase, progress, supply, pool reserves (pool_token_f, pool_quote_f), its live holders count and its last 24 h (trades24h, volume24hQuote, volume24hUsd, change24hPct).
GET /api/coin/:token
One token: the same object as above plus holders, stats24h and supplyBreakdown, the supply split into liquidity, locked, burned, creator, protocol and market, with the top-10 concentration measured on the market share alone. Liquidity is the pool position’s own reserve when it is known; lockedPct is what a locker holds outside the position. stats24h also splits the day into buys / sells, buy_volume_quote / sell_volume_quote and distinct buyers / sellers; the pool hook selling the fees it collected counts as a sell but not as a seller.
GET /api/coin/:token/flow
The same buy and sell split for a shorter window: ?window= 5m | 1h | 4h | 24h (default 24h). The fields match stats24h (trades, volume_quote, price_change_pct, buys, sells, buy_volume_quote, sell_volume_quote, buyers, sellers), plus the window and its start, since. The change is measured against the last trade before the window (the first one inside it if the token is younger); 0 when nothing traded in the window.
GET /api/trades
The latest trades across every launch, newest first, with the token's symbol and pair. ?limit= 1-60 (default 20).
GET /api/trades/best
The best entries of the period: buys whose price is up since, best first. It is not a profit figure. Each entry is one buy with its entryPrice and the priceNow, and changePct is the move between them, whether or not the wallet still holds the token. ?window= 7d (default) | 24h, ?limit= 1-30 (default 12). One entry per wallet and token (its best buy), only buys of at least $10 and only those that are up; an empty entries is a valid answer. Fields: wallet, tag (as in /api/traders), token, symbol, logo, source, pairSymbol, paidUsd, entryPrice, priceNow, changePct, timestamp (unix seconds) and txHash. With source launchpad (curve and pool buys) both prices are in the token’s pair asset, pairSymbol, so the move does not depend on that asset’s own price, and paidUsd is the amount paid at the pair’s current dollar rate. With dex (swaps from /trade of tokens with no trades indexed here) the prices are in dollars and pairSymbol is USD. Wallets of the project and tokens we do not show are left out. updatedAt is in milliseconds; cached for a few minutes.
GET /api/trades/:token
The trades of one token. ?limit= 1-200 (default 50), ?min= a minimum size in the token’s pair asset (the most recent trades at or above it; the response echoes min). Curve and pool trades both appear; curve is null for trades in the Uniswap pool. fee_conversion is true on the pool hook’s own sells of the fees it collected: real volume, but no one’s trade.
GET /api/candles/:token
OHLC candles. ?res= 1m | 5m | 15m | 1h, ?limit= 1-1000 (default 200). There is no daily resolution; group hourly candles to build it.
GET /api/holders/:token
Holders by balance. ?limit= 1-500 (default 100), ?offset=. A row can carry a tag: the pool, the curve, the locker, the hook, the burn address or the creator. The largest holder of a graduated token is usually its pool.
GET /api/wallet/:address
What one address holds across the launches we index, valued at each token’s live price. Each position carries a cost object (avg, paid, bought, sold, received, pnl, pnlPct, movedOut, since) built from the buys and sells the indexer recorded, in the pair asset. It is null when there are no indexed buys, for example for tokens received by transfer. When part of what was bought left the wallet by transfer, movedOut is true and pnl and pnlPct are null. They are also null, with movedOut false, when the wallet holds more than it bought minus sold here: tokens that arrived by transfer have no known cost.
GET /api/traders
The wallets holding the most across the launches we index, in dollars. Each row carries paid, received, value, pnl, pnlPct, trades, the tokens it trades (tokens, up to six { token, symbol }, and tokensTotal) and a tag when the address is the pool, the curve, the escrow or a creator. ?limit= 1-50 (default 10), ?sort=value (default) or paid. With ?window=24h | 7d | 30d it lists what each wallet moved in that window (bought, sold, traded), with no profit figure. When a wallet moved tokens to another address without selling, movedOut is true and pnl is null. pnl is also null when a wallet holds more than it bought minus sold here, or sold more than it bought.
GET /api/traders/rank/:address
One wallet's place in the whole table: rank (null when it is not in it), total and its row. ?window=all (default) | 24h | 7d | 30d, and ?sort= the column the table is ordered by: pnl (default), paid, value or trades for all time; traded (default), bought, sold or trades for a window. Wallets without a result go last.
GET /api/burns/:token
Every burn of that token (a Transfer to 0x…dEaD), newest first, with amountF, the running total cumulativeF, pctOfSupply and the transaction hash. ?limit= 1-500 (default 100) caps the rows returned; total, totalCount and totalPct always cover every burn. Without a token it lists recent burns across tokens, and the totals and cumulativeF are null.
GET /api/profile/:address
A wallet's public profile: an optional name, a color from a fixed palette (with its colorHex), an optional one-line bio, an X handle (x, stored bare, plus the xUrl we build from it), an optional username, separate from the display name, and, if uploaded, pfpUrl and coverUrl. A wallet that never set anything gets a deterministic color (isDefaultColor: true). GET /api/profiles?addresses=a,b,c returns up to 100 at once, and GET /api/profile/by-username/:username finds a profile by its handle.
GET /api/thesis/:token
What holders say about a token. Each entry carries the text, the timestamp and price it was posted at, balanceThen, balanceNow (0 if the author sold since; null if unknown), likes and the author profile. A thesis whose author no longer holds is closed, with the author’s last sale as closePrice and the move since posting as closedPct. Newest first, or ?sort=likes; ?viewer=0x… adds likedByViewer; ?limit= 1-200 (default 50), ?offset=. For a Solana launch, :token is the mint exactly as written (base58 is case-sensitive), priceIn is quote (the pair per whole token, like priceQuote in /api/sol/token) and each author is a Solana account, without a profile.
GET /api/thesis/wallet/:account
The theses of a Solana account, newest first (up to 50), with the symbol of each token and mostLikedThesis. The theses of a 0x wallet come with GET /api/wallet/:address.
GET /api/wallet/:address · closed
Positions this address bought here and no longer holds: the same shape as an open position, with totalSupply (tokens), the cost object (plus avgExit, the average price of what was sold, buys, sells and last) and a realised pnl, received minus paid, in the pair asset. movedOut is true when the tokens left by transfer rather than by selling, and then pnl is null. It is also null when more was sold than was bought here. Open positions carry the same fields. counts.closed says how many.
GET /api/wallet/:address/activity
This address’s trades, newest first. ?limit= 1-200 (default 50), ?offset=, ?side=buy|sell, ?token= one address, ?minUsd= a minimum trade size in dollars (a pair without a dollar price is left out while it is set). total counts what the filters leave. Each row carries mcQuote, the token’s market cap at that trade in the pair asset (trade price times total supply). ?source= picks where the trades come from: launchpad (the default), markets (swaps on the markets page, with usd at the time of the swap), solana (the Solana account this wallet linked, signed by both) or all, merged by time. With a source, totals gives the count in each one and solana the linked account, if any.
GET /api/holders/:token/pnl?addresses=a,b,c
Up to 100 holders of one token at once: each one’s balance, first-seen since, buys, sells, paid, received, avgEntry (null without indexed buys), avgHoldSeconds (the average age of that wallet’s open positions across every token, as in /api/trader) and its thesis on that token, if any.
GET /api/trader/:address
One wallet as a trader: trades, firstSeen, lastSeen, avgHoldSeconds, openPositions, its bestTrades in dollars, only positions with a known result (pnlUsd, pnlPct, avgEntryMcUsd, open, movedOut), its badges (creator, graduate, burner, diamond, early), its theses, mostLikedThesis and launches.
GET /api/follows/:address
Who a wallet follows (following, followingCount) and how many follow it (followers). Follows are public and signed. GET /api/follows/:address/mutuals?viewer=0x… lists which of the wallets the viewer follows also follow :address (mutuals, mutualCount), and whether the two follow each other (followsYou, youFollow). GET /api/follows/:address/suggestions suggests up to eight wallets to follow: first those followed by the wallets it follows (followedBy), then the authors of the week's most liked theses (thesisLikes), never itself or a wallet it already follows.
GET /api/crews · GET /api/crew/:id · GET /api/crew/invite/:token
Crews: a name and a list of wallets, with no admin. They are invite only: joining needs the crew’s invite link (/c/<token>), and leaving is signing. The list carries each crew’s memberCount; ?member=0x… returns the crew one wallet is in (null for none). A wallet belongs to at most one crew. A crew can carry a logoUrl, set by the wallet that created it (POST /api/crew/logo, signed, PNG, JPEG or WebP up to 256 KB and 1024 px). /api/crew/invite/:token returns the crew an invite link points to (404 once its creator resets the link). The token itself never appears in a public response: only the wallet that created the crew gets it, when creating the crew and later from POST /api/crew/invite, signed (with reset: true it replaces it and the old link stops working).
GET /api/crews/leaderboard
Crews ranked by what their members do, with the same numbers as the traders table. All time (default): the summed pnl of the members that have a result, pnlPct over what those members put in, membersWithResult, paid and value. ?window=24h | 7d | 30d: traded in that window, with no profit figure. Every crew carries its rank, memberCount and activeMembers.
GET /api/search?q=
Two characters or more: tokens by symbol, name or address and traders by profile name or address. Hidden tokens never appear.
GET /api/feed
Trades, theses, launches and burns as one list of events, newest first, each with a kind (trade | thesis | launch | burn), a stable id and a timestamp. ?since= (unix seconds) returns only what is newer; ?limit= 1-200 (default 100). When polling, set since a minute behind the last event you saw: the indexer runs behind the chain.
GET /api/recap
The last 24 hours in one object: trades, volumeUsd (summed per pair in dollars; volumeUsdPartial is true when a pair had no dollar price and was left out), launches (count and the latest five), mostTraded, topGainers and topLoser (only tokens with at least moverMinUsd of volume in the window), agiBurn and topThesis, the day's most liked thesis. Cached for a few minutes.
POST /api/profile · POST /api/profile/pfp · POST /api/profile/username · POST /api/profile/cover · POST /api/profile/solana · POST /api/thesis · POST /api/thesis/delete · POST /api/thesis/like · POST /api/follow · POST /api/crew · POST /api/crew/join · POST /api/crew/invite · POST /api/telegram/link
The writes. Each needs an EIP-191 personal_sign signature from the wallet it concerns, over a fixed text that names the exact change, such as “Join the crew ‘Gatos’” (the site builds it; identidad.js is the reference). Linking a Solana account takes two: the wallet's and the Solana account's. A thesis, and a like on one, also require a non-zero balance on chain at that moment. On a Solana launch the thesis, its like and its deletion are signed by the Solana account instead: an ed25519 signMessage signature of the same text, in base58, with the account and the mint exactly as written; the balance is read from Solana. Names are unique (case-insensitive, 409 when taken) and can change once every 30 days (429 with Retry-After). Pictures are PNG, JPEG or WebP up to 512 KB and 2048 px, served with a fixed content type. A username is 3 to 20 lowercase letters, numbers or _, unique, and changes once every 30 days (removing it counts). A cover is PNG, JPEG or WebP up to 768 KB and 3000 px wide, at least twice as wide as it is tall; {"remove": true} with its own signed text takes it off. Every write is rate-limited per wallet and per IP.

Limits, caching and what we promise

  • Rate limit. 300 requests per minute per IP, enforced approximately. Over it you get 429 with a Retry-After header.
  • Cache. Responses carry Cache-Control, from 5 seconds to 10 minutes. Polling faster returns the same data and counts against your limit.
  • Freshness. The indexer runs every minute. /api/stats reports its cursor and the chain head, so you can see how far behind it is.
  • Degraded mode. If our database is unavailable, most reads come from a snapshot and carry X-AGI-Degradado with its timestamp. The live-trades endpoint fails instead.
  • Stability. Fields may be added at any time; we try not to remove or rename them. There is no SLA.
  • User agent. Cloudflare's bot protection rejects some default user agents with a 403, Python's urllib among them. Send your own.
  • Internal routes. The market and DEX routes our pages use (/api/markets, /api/market/*, /api/dex/*, /api/referral/*, /api/builders/*) are not part of this API and can change without notice.

An example

curl 'https://api.agiartificialgatointelligence.com/api/launches?limit=5&sort=volume'

No money moves through this API. Launching, trading and claiming are transactions you sign against the contracts: see Launching a token, Trading on the curve and Claiming fees.