Datapoints
In Pooler, data points are specific, quantifiable elements derived from Uniswap V2 and V3 trading activities.
Each snapshot inherits SnapshotBase
which looks something like this:
loading...
Base Snapshots
The following type of Base Snapshots are generated by Pooler for the Uniswap V2 and V3 Dashboards:
1. Pair Reserves Snapshot
Liquidity reserves of each pair per Epoch. The reserves snapshot looks something like this:
loading...
Significant differences between the V2 and V3 implementations can be found in the generation of this base snapshot and are outlined below:
V2 Reserves Snapshot Caclulations
The token reserve amounts for a UniswapV2 pair are retrieved from the getReserves() function that is available in the UniswapV2Pair
contract. These amounts are converted from their native integer format into a normalized decimal format and are then used to populate the snapshot's token0Reserves
and token1Reserves
fields. This calculation can be seen in the UniswapV2 compute module here:
loading...
The price of a token in a UniswapV2 pair can be derived using the ratio of the pair's token reserves, or by utilizing one of the pricing functions available in the UniswapV2Library
contract such as getAmountsOut(). See the UniswapV2 Pricing documentation for additional information. The snapshot's token0Prices
and token1Prices
fields are calculated by first deriving each token's price in terms of ETH (or the source chain's equivalent gas token), and then converting the resulting ETH price to USD terms.
For each token, the compute attempts to find a UniswapV2 pair consisting of the given token and wrapped ETH (WETH). If the token's WETH pair exists, its ETH price is derived using the ratio of the pair's token reserves. If the token's WETH pair does not exist, an additional pair consisting of the given token and a whitelisted token is used to derive an intermediary price before converting it back in terms of ETH. This calculation can be seen in the Pricing Utils of the UniswapV2 compute module.
The ETH price in terms of USD is calculated in Pooler's Snapshot Utils, and it is used to convert each token's ETH price to USD in the Pricing Utils of the UniswapV2 compute module. The results are used to populate the snapshot's token0Prices
and token1Prices
fields.
The snapshot's token0ReservesUSD
and token1ReservesUSD
fields are calculated by applying the token0Prices
and token1Prices
to the token0Reserves
and token1Reserves
values respectively. This calculation can be seen in the Core Utils of the UniswapV2 compute module.
V3 Reserves Snapshot Caclulations
The following section contains references to advanced concepts specific to the UniswapV3 Protocol. It is recommended that you read the UniswapV3 Concepts documentation as well as the UniswapV3 Math Primer before continuing if you are unfamilar with the inner workings of the protocol.
Unlike the UniswapV2Pair
contract, the getReserves()
function is not available in the UniswapV3Pool
contract, so the token reserve amounts cannot be retrieved directly from the chain and must be calculated manually. The calculation is computationally expensive, as it involves iterating over each available tick on the pool's price curve to sum the liquidity available at each tick. In order to reduce resource usage and limit the number of RPC requests, Powerloom's UniswapV3 dashboard implementation splits the computation of the UniswapPairTotalReservesSnapshot
into two phases:
- An initial manual calculation of the token reserves for each pool using the
calculate_reserves()
function found in the Total Value Locked Utils of the UniswapV3 compute module. - Incremental adjustments to the initially calculated reserve values based on
Mint
andBurn
events for each token in the pool. This calculation can be seen in the Core Utils of the UniswapV3 compute module.
The resulting reserve values are used to populate the snapshot's token0Reserves
and token1Reserves
fields.
The price of a token in a UniswapV3 pool can be calculated from the sqrtPriceX96
value returned from a UniswapV3Pool
contract's slot0() function. This value is returned in a format known as Q Notation. For additional information on Q notation and price calculation in UniswapV3, see the UniswapV3 Math Primer.
The snapshot's token0Prices
and token1Prices
are computed following a similar process to the UniswapV2 calculation, however, instead of the using the ratio of the the token reserves or a pricing function, the prices are derived from each pool's sqrtPriceX96
. This calculation can be seen here:
loading...
The snapshot's token0ReservesUSD
and token1ReservesUSD
fields are calculated by applying the token0Prices
and token1Prices
to the token0Reserves
and token1Reserves
values respectively. This calculation can be seen in the Core Utils of the UniswapV3 compute module.
2. Trade Volume Snapshot
Trade volume of each pair per Epoch. The trade volume snapshot looks something like this:
loading...
Aggregate Snapshots
The above base snapshots are then used to generate higher order aggregates. These aggregates are then used to generate the data points that are used in the Uniswap V2 and V3 Dashboards. Refer to data-composition for more details on how data points are composed.
The following aggregate snapshots are generated by Pooler using base snapshots.
1. 24 Hour Trade Volume Snapshot
24 hour trade volume of each pair per Epoch. The 24 hour trade volume snapshot looks something like this:
loading...
2. 7 days Trade Volume Snapshot
7 days trade volume of each pair per Epoch. The 7 days trade volume snapshot is exactly like 24 hour trade volume snapshot but with a different time window.
3. 24 hours Top Pairs Snapshot
Top pairs by 24 hour trade volume per Epoch. The 24 hours top pairs snapshot looks something like this:
loading...
4. 7 days Top Pairs Snapshot
Top pairs by 7 days trade volume per Epoch. The 7 days top pairs snapshot is very similar to 24 hour top pairs snapshot but with a different time window.
5. 24 hours Top Tokens Snapshot
Top tokens by 24 hour trade volume per Epoch. The 24 hours top tokens snapshot looks something like this:
loading...
6. 24 hours Stats Snapshot
24 hour stats of each pair per Epoch. The 24 hours stats snapshot looks something like this:
loading...
Implementation
The implementation of these processes is detailed in the Closer Look at Snapshots
The specific configurations for data points like pair reserves, token prices, trading volumes, and fees are outlined in config/projects.json
and config/aggregator.json
. These configurations dictate what data to capture and how to process it. We have covered that in the Data sources section.