Public API
Merry Men exposes a public, read-only, CORS-open API so trading terminals, data aggregators, and wallets can discover launches, prices, and metadata with no bespoke integration. It complements the auto-indexing that already covers our pools on GeckoTerminal and DexScreener; it does not replace it.
All bigint values are serialized as decimal strings (JSON-safe). Addresses are lowercase in the indexer feed and checksummed in the token list.
Origins
Section titled “Origins”Two origins serve the API:
| Origin | Env var | Serves |
|---|---|---|
| Indexer | NEXT_PUBLIC_INDEXER_URL |
Live launches / prices / holders / candles (Ponder REST + GraphQL). CORS *. |
| Web app | https://merrymen.wtf |
The standard token list. |
Token list
Section titled “Token list”GET https://merrymen.wtf/api/tokenlistThe canonical Uniswap Token List format (name,
timestamp, version, tokens[]), what wallets and many aggregators ingest
directly. On-chain fields come from the indexer (already spam-filtered); logoURI
and socials are merged from each launch’s off-chain metadata. Cached ~5 min.
{ "name": "Merry Men", "timestamp": "2026-07-15T00:00:00.000Z", "version": { "major": 1, "minor": 42, "patch": 0 }, "keywords": ["merrymen", "launchpad", "robinhood-chain"], "logoURI": "https://merrymen.wtf/mark-coin.png", "tokens": [ { "chainId": 4663, "address": "0xAbc…", // checksummed "name": "Little John", "symbol": "JOHN", "decimals": 18, "logoURI": "https://cdn…/coins/0xabc…/logo.png", "extensions": { // present only when known "website": "https://…", "twitter": "https://x.com/…", "telegram": "https://t.me/…", "discord": "https://discord.gg/…" } } ]}version.minor tracks the token count, so the version advances as launches are
added. Tokens whose on-chain name/symbol can’t satisfy the schema are shaped
to fit or skipped, never breaking the whole list.
Launches feed
Section titled “Launches feed”GET {INDEXER_URL}/coinsThe list backing the site. ?filter= selects the ordering; ?limit= caps
results (≤200).
| filter | meaning |
|---|---|
new (default) |
newest launches first |
live |
most recently traded first |
stolen |
highest all-time WETH volume |
soon |
not-yet-graduated, nearest the graduation milestone |
escaped |
graduated tokens |
The response is an envelope, { "filter": …, "coins": [ … ] }; the array is
under coins. Each coin carries trading state plus the pointers a terminal needs:
{ "filter": "new", "coins": [ { "address": "0xabc…", // lowercase "id": "0xabc…", // == address "chainId": 4663, "name": "Little John", "symbol": "JOHN", "ticker": "$JOHN", "decimals": 18, "creator": "0x…", "pool": "0x…", // the TOKEN/WETH V3 pool "positionId": "212496", // the locked V3 position NFT id "tokenIsToken0": true, // token sorts below WETH → token0 "totalSupply": "1000000000000000000000000000", "holders": 128, "priceWeth": 1.23e-8, // latest price, WETH per token (number) "volumeWethAllTime": "…", // decimal string (wei) "volumeTokenAllTime": "…", "swapCount": 512, "lastSwapAt": "1752537600", // unix seconds, string "lastSwapIsBuy": true, "createdAtBlock": "13091099", "createdAtTimestamp": "1752537000", "metadataUrl": "https://cdn…/coins/0xabc…/metadata.json", // logo + socials, or null "graduation": { "progress": 0.4, // 0..1 "graduated": false, "netBuysWeth": "…", "liquidityWeth": "…", "thresholdNetBuysWeth": "…", "thresholdLiquidityWeth": "…", "graduatedAt": null } } ]}tokenIsToken0 tells a consumer which side of the pool is the launch token
without an extra positions() read. priceWeth is a JSON number (often in
scientific notation); all other numeric quantities are decimal strings.
graduation is an off-chain milestone badge, never a
bonding-curve state.
Per-token reads
Section titled “Per-token reads”All under {INDEXER_URL}:
| Endpoint | Returns |
|---|---|
GET /coins/:address |
Full detail (token + graduation + fee aggregate) |
GET /coins/:address/swaps |
Recent trades |
GET /coins/:address/holders |
Holder balances |
GET /coins/:address/candles |
OHLCV |
GET /coins/:address/graduation |
Milestone progress |
GET /coins/:address/fees |
Claimed creator / ops / buyback fee aggregate |
GET / and GET /graphql |
Auto GraphQL over the same schema |
Real-time (SSE)
Section titled “Real-time (SSE)”GET {INDEXER_URL}/streamServer-Sent Events for a live “new pairs / new trades” tab. Emits an update
event (a re-fetch cue) whenever the set of coins or their swap counts advance,
plus periodic ping keepalives. Per-token stream:
GET {INDEXER_URL}/coins/:address/stream.
Per-token metadata
Section titled “Per-token metadata”Off-chain launch metadata lives on the CDN at coins/<address>/metadata.json,
written at launch. The launches feed surfaces it as the metadataUrl pointer so
consumers resolve logos/socials without knowing the storage layout:
{ "name": "…", "symbol": "…", "image": "https://cdn…/logo.png", "description": "…", "socials": { "website": "…", "x": "…", "telegram": "…", "discord": "…" }, "updatedAt": 1752537600000}Configuration
Section titled “Configuration”| Var | Where | Purpose |
|---|---|---|
NEXT_PUBLIC_INDEXER_URL |
web | Indexer base URL the token list reads from |
NEXT_PUBLIC_METADATA_BASE_URL |
web | CDN base for logo/socials merge |
METADATA_BASE_URL |
indexer | Same CDN base → emits per-coin metadataUrl |
Related
Section titled “Related”- Onchain events: index it yourself instead of polling.
- Pricing calculations: derive price from pool state.

