exchange.IO("lp.pools", ...)
Lists all LP pools of a token (V3 and V4/Infinity CL pools for Uniswap and PancakeSwap, Slipstream and basic pools for Aerodrome and Velodrome), including fee rate, current price, liquidity, TVL and 24-hour trading volume, sorted by TVL in descending order.
exchange.IO(k, token)
exchange.IO(k, token, quote)Examples
-
List ETH/USDC pools and view the top few by TVL and trading volume.
javascriptfunction main() { var pools = exchange.IO("lp.pools", "ETH", "USDC") if (!pools) { Log("Query failed:", GetLastError()) return } pools.slice(0, 5).forEach(function (p) { Log(p.protocol, p.id, "Fee rate:", p.feeRate, "TVL:", p.tvlUsd, "24h volume:", p.volume24hUsd) }) } -
Uniswap: list the token's V4 pools (including custom-fee pools outside the common combinations), then query the first one by PoolId.
javascriptfunction main() { var v4 = exchange.IO("lp.pools", "UNI").filter(function (p) { return p.protocol == "v4" && !p.empty }) v4.forEach(function (p) { Log(p.symbol, "Fee rate:", p.fee / 10000 + "%", "Tick spacing:", p.tickSpacing, "TVL:", p.tvlUsd) }) if (v4.length > 0) { var pool = exchange.IO("lp.pool", v4[0].id) Log(v4[0].id, pool ? "Fee rate: " + pool.fee : GetLastError()) } } -
Aerodrome, Velodrome: among pools whose gauge is still distributing rewards, filter by reward APR.
javascriptfunction main() { var pools = exchange.IO("lp.pools", "ETH", "USDC").filter(function (p) { return p.gaugeAlive && p.rewardAprPct !== null }) pools.sort(function (a, b) { return b.rewardAprPct - a.rewardAprPct }) pools.slice(0, 3).forEach(function (p) { Log(p.protocol, p.id, "Tick spacing:", p.tickSpacing, "Reward APR %:", p.rewardAprPct, "Staked share:", p.stakedShare) }) }
Returns
| Type | Description |
array / null value | Array of pools |
Arguments
| Name | Type | Required | Description |
k | string | Yes | Fixed as |
token | string | Yes | Token name or contract address, e.g. |
quote | string | No | Quote currency, e.g. |
See Also
Uniswap / PancakeSwap Aerodrome / Velodrome exchange.IO exchange.IO("lp.select") exchange.IO("lp.pool") exchange.IO("lp.plan") exchange.IO("lp.positions")
Remarks
Fields of each item in the returned array:
| Field | Description |
|---|---|
id | Pool ID: for V3, Slipstream and basic pools it is the pool contract address; for V4/Infinity CL it is the PoolId (0x followed by 64 hex digits); can be passed as the pool parameter of lp.pool, lp.ticks and lp.plan |
protocol | Pool type: v3, v4 (Uniswap V4), infinity (PancakeSwap Infinity CL); for Aerodrome and Velodrome it is slipstream, slipstream2 (the old and new factory respectively) and the basic pools volatile, stable |
dex, symbol | Exchange name and the pool's trading pair (e.g. WETH_USDC) |
fee, feeRate | Fee rate: fee is in units of one millionth (500 means 0.05%), feeRate is in decimal form (0.0005); the fee of Slipstream pools may be dynamic, and the current value is shown here |
tickSpacing, tick | Tick spacing and current tick; basic pools have no ticks and the value is null |
price | Current price, expressed as quote currency per token |
liquidity | Liquidity at the current price (decimal string) |
reserveBase, reserveQuote | Balances of the two tokens in the pool; V4/Infinity CL use a singleton contract, so the value is null |
tvlQuote, tvlUsd | TVL converted to the quote currency and to USD (data for V4/Infinity CL is taken from GeckoTerminal) |
volume24hUsd, fees24hUsd | 24-hour trading volume and fee income (USD), taken from GeckoTerminal; null when unavailable |
empty | true means there is no liquidity at the current price and the current price is not meaningful: price, tvlQuote, tvlUsd are null, and such pools are placed last |
Each item for Aerodrome and Velodrome additionally includes stable (whether a basic pool uses the stable curve; null for Slipstream) and gauge information: gauge (gauge address), gaugeAlive (whether the gauge is still distributing rewards), stakedShare (share of liquidity at the current price staked in the gauge), rewardsPerDay, rewardsPerDayUsd (amount of reward tokens distributed per day and its USD value), rewardAprPct (reward APR based on the TVL of the staked portion, in %). The reward APR is extrapolated from the current per-second emission and changes with the reward token price and staked amount, so it is an instantaneous value: for Slipstream pools, stakedShare is the ratio of staked liquidity to total liquidity at the tick containing the current price; whenever the price moves or positions move in or out of range, this value jumps, and rewardAprPct may differ several-fold within a few minutes. When using it to select pools or estimate returns, fetch it multiple times at intervals and take the average.
For V4/Infinity CL pools of Uniswap and PancakeSwap, only pools without hooks are listed; neither has fixed fee tiers.
Uniswap V4: native-token pools and wrapped-token pools are listed separately (e.g. ETH_USDC and WETH_USDC). The listed pools include pools on common fee/tick spacing combinations (0.01%/1, 0.02%/4, 0.03%/6, 0.04%/8, 0.05%/10, 0.3%/60, 1%/200), as well as pools with custom fees and spacings: the PoolIds of Uniswap V4 pools are obtained from the token's pool list on GeckoTerminal (top 40 sorted by volume and liquidity), then the PoolKey is looked up on-chain via PositionManager's poolKeys and the PoolId is verified, keeping only pools without hooks (e.g. the CASHCAT/USDG 0.269% pool with spacing 54 on Robinhood). There is no upper limit on fees, so high-fee pools such as 2% are also listed. When both the token and the quote currency are routing tokens (wrapped native tokens and stablecoins such as USDC and USDT, e.g. lp.pools("ETH", "USDC")), only common combinations are listed; query results are cached for 1 hour; when GeckoTerminal is temporarily unavailable (e.g. rate-limited), only common combinations are listed and it is retried after 5 minutes. The list may still miss pools: pools not indexed by GeckoTerminal or not in the top 40, and pools for which no position has ever been created on PositionManager (poolKeys cannot find the PoolKey), will not be listed. For hookless pools outside the list, the PoolId can be passed directly to lp.pool or lp.plan (pool parameter), provided likewise that its PoolKey can be found on PositionManager.
PancakeSwap Infinity CL: only pools with fees not exceeding 1% are listed; the listed pools are those collected from recent on-chain trades during swap routing, as well as pools used by this process. Other pools can be passed directly by PoolId to lp.pool or lp.plan.
GeckoTerminal data is cached in-process for 5 minutes and shared by lp.select and lp.plan; when rate-limited, it waits briefly and retries once; if it still fails, the corresponding fields are null.
KyberSwap and 1inch exchange objects (aggregators) do not support LP commands; calling them raises the error LP functions are not available for KyberSwap on Base.