Search Apps Documentation Source Content File Folder Download Copy Actions Download

getter.gno

11.09 Kb ยท 391 lines
  1package v1
  2
  3import (
  4	"strconv"
  5
  6	u256 "gno.land/p/gnoswap/uint256"
  7	"gno.land/p/nt/ufmt"
  8	pl "gno.land/r/gnoswap/pool"
  9)
 10
 11// GetPoolPath generates a unique pool path string based on the token paths and fee tier.
 12func GetPoolPath(token0Path, token1Path string, fee uint32) string {
 13	return pl.GetPoolPath(token0Path, token1Path, fee)
 14}
 15
 16// GetPool retrieves a pool instance based on the provided token paths and fee tier.
 17func (i *poolV1) GetPool(token0Path, token1Path string, fee uint32) (*pl.Pool, error) {
 18	poolPath := pl.GetPoolPath(token0Path, token1Path, fee)
 19	return i.getPool(poolPath)
 20}
 21
 22// GetFeeAmountTickSpacing retrieves the tick spacing associated with a given fee amount.
 23func (i *poolV1) GetFeeAmountTickSpacing(fee uint32) (spacing int32) {
 24	feeAmountTickSpacing := i.store.GetFeeAmountTickSpacing()
 25
 26	spacing, exist := feeAmountTickSpacing[fee]
 27	if !exist {
 28		panic(newErrorWithDetail(
 29			errUnsupportedFeeTier,
 30			ufmt.Sprintf("expected fee(%d) to be one of %d, %d, %d, %d", fee, FeeTier100, FeeTier500, FeeTier3000, FeeTier10000),
 31		))
 32	}
 33
 34	return spacing
 35}
 36
 37func (i *poolV1) GetToken0Path(poolPath string) string {
 38	return i.mustGetPool(poolPath).Token0Path()
 39}
 40
 41func (i *poolV1) GetToken1Path(poolPath string) string {
 42	return i.mustGetPool(poolPath).Token1Path()
 43}
 44
 45func (i *poolV1) GetFee(poolPath string) uint32 {
 46	return i.mustGetPool(poolPath).Fee()
 47}
 48
 49func (i *poolV1) GetBalanceToken0(poolPath string) string {
 50	return i.mustGetPool(poolPath).BalanceToken0().ToString()
 51}
 52
 53func (i *poolV1) GetBalanceToken1(poolPath string) string {
 54	return i.mustGetPool(poolPath).BalanceToken1().ToString()
 55}
 56
 57func (i *poolV1) GetTickSpacing(poolPath string) int32 {
 58	return i.mustGetPool(poolPath).TickSpacing()
 59}
 60
 61func (i *poolV1) GetMaxLiquidityPerTick(poolPath string) string {
 62	return i.mustGetPool(poolPath).MaxLiquidityPerTick().ToString()
 63}
 64
 65func (i *poolV1) GetSlot0FeeProtocol(poolPath string) uint8 {
 66	return i.mustGetPool(poolPath).Slot0FeeProtocol()
 67}
 68
 69func (i *poolV1) GetSlot0Unlocked(poolPath string) bool {
 70	return i.mustGetPool(poolPath).Slot0Unlocked()
 71}
 72
 73func (i *poolV1) GetFeeGrowthGlobal0X128(poolPath string) string {
 74	return i.mustGetPool(poolPath).FeeGrowthGlobal0X128().ToString()
 75}
 76
 77func (i *poolV1) GetFeeGrowthGlobal1X128(poolPath string) string {
 78	return i.mustGetPool(poolPath).FeeGrowthGlobal1X128().ToString()
 79}
 80
 81func (i *poolV1) GetProtocolFeesToken0(poolPath string) string {
 82	return i.mustGetPool(poolPath).ProtocolFeesToken0().ToString()
 83}
 84
 85func (i *poolV1) GetProtocolFeesToken1(poolPath string) string {
 86	return i.mustGetPool(poolPath).ProtocolFeesToken1().ToString()
 87}
 88
 89func (i *poolV1) GetLiquidity(poolPath string) string {
 90	return i.mustGetPool(poolPath).Liquidity().ToString()
 91}
 92
 93func (i *poolV1) MustGetPosition(poolPath, key string) *pl.PositionInfo {
 94	pool := i.mustGetPool(poolPath)
 95
 96	positions := pool.Positions()
 97
 98	result, exist := positions.Get(key)
 99	if !exist {
100		panic(newErrorWithDetail(
101			errDataNotFound,
102			ufmt.Sprintf("expected position(%s) to exist", key),
103		))
104	}
105
106	position, ok := result.(pl.PositionInfo)
107	if !ok {
108		panic("failed to cast position to PositionInfo")
109	}
110
111	return &position
112}
113
114func (i *poolV1) GetPositionFeeGrowthInside0LastX128(poolPath, key string) string {
115	return i.MustGetPosition(poolPath, key).FeeGrowthInside0LastX128().ToString()
116}
117
118func (i *poolV1) GetPositionFeeGrowthInside1LastX128(poolPath, key string) string {
119	return i.MustGetPosition(poolPath, key).FeeGrowthInside1LastX128().ToString()
120}
121
122func (i *poolV1) GetPositionTokensOwed0(poolPath, key string) string {
123	return i.MustGetPosition(poolPath, key).TokensOwed0().ToString()
124}
125
126func (i *poolV1) GetPositionTokensOwed1(poolPath, key string) string {
127	return i.MustGetPosition(poolPath, key).TokensOwed1().ToString()
128}
129
130func (i *poolV1) GetTickLiquidityGross(poolPath string, tick int32) string {
131	pool := i.mustGetPool(poolPath)
132	return GetTickLiquidityGross(pool, tick).ToString()
133}
134
135func (i *poolV1) GetTickLiquidityNet(poolPath string, tick int32) string {
136	pool := i.mustGetPool(poolPath)
137	return GetTickLiquidityNet(pool, tick).ToString()
138}
139
140func (i *poolV1) GetTickFeeGrowthOutside0X128(poolPath string, tick int32) string {
141	pool := i.mustGetPool(poolPath)
142	return GetTickFeeGrowthOutside0X128(pool, tick).ToString()
143}
144
145func (i *poolV1) GetTickFeeGrowthOutside1X128(poolPath string, tick int32) string {
146	pool := i.mustGetPool(poolPath)
147	return GetTickFeeGrowthOutside1X128(pool, tick).ToString()
148}
149
150func (i *poolV1) GetTickCumulativeOutside(poolPath string, tick int32) int64 {
151	pool := i.mustGetPool(poolPath)
152	return GetTickCumulativeOutside(pool, tick)
153}
154
155func (i *poolV1) GetTickSecondsPerLiquidityOutsideX128(poolPath string, tick int32) string {
156	pool := i.mustGetPool(poolPath)
157	return GetTickSecondsPerLiquidityOutsideX128(pool, tick).ToString()
158}
159
160func (i *poolV1) GetTickSecondsOutside(poolPath string, tick int32) uint32 {
161	pool := i.mustGetPool(poolPath)
162	return GetTickSecondsOutside(pool, tick)
163}
164
165func (i *poolV1) GetTickInitialized(poolPath string, tick int32) bool {
166	pool := i.mustGetPool(poolPath)
167	return GetTickInitialized(pool, tick)
168}
169
170func (i *poolV1) GetSlot0Tick(poolPath string) int32 {
171	return i.mustGetPool(poolPath).Slot0Tick()
172}
173
174func (i *poolV1) GetSlot0SqrtPriceX96(poolPath string) *u256.Uint {
175	slot0 := i.mustGetPool(poolPath).Slot0()
176	return u256.Zero().Set(slot0.SqrtPriceX96())
177}
178
179func (i *poolV1) GetFeeGrowthGlobalX128(poolPath string) (*u256.Uint, *u256.Uint) {
180	pool := i.mustGetPool(poolPath)
181	return u256.Zero().Set(pool.FeeGrowthGlobal0X128()), u256.Zero().Set(pool.FeeGrowthGlobal1X128())
182}
183
184func (i *poolV1) GetTickFeeGrowthOutsideX128(poolPath string, tick int32) (*u256.Uint, *u256.Uint) {
185	pool := i.mustGetPool(poolPath)
186	return u256.Zero().Set(GetTickFeeGrowthOutside0X128(pool, tick)), u256.Zero().Set(GetTickFeeGrowthOutside1X128(pool, tick))
187}
188
189func (i *poolV1) GetPositionFeeGrowthInsideLastX128(poolPath, key string) (*u256.Uint, *u256.Uint) {
190	position := i.MustGetPosition(poolPath, key)
191	return u256.Zero().Set(position.FeeGrowthInside0LastX128()), u256.Zero().Set(position.FeeGrowthInside1LastX128())
192}
193
194func (i *poolV1) GetPositionLiquidity(poolPath, key string) *u256.Uint {
195	position := i.MustGetPosition(poolPath, key)
196	return u256.Zero().Set(position.Liquidity())
197}
198
199func (i *poolV1) ExistsPoolPath(poolPath string) bool {
200	pools := i.store.GetPools()
201	return pools.Has(poolPath)
202}
203
204func (i *poolV1) GetObservation(poolPath string, secondsAgo int64) (
205	tickCumulative int64,
206	liquidityCumulative,
207	secondsPerLiquidityCumulativeX128 string,
208	blockTimestamp int64,
209) {
210	pool := i.mustGetPool(poolPath)
211	observationState := pool.ObservationState()
212
213	if observationState == nil {
214		return 0, "0", "0", 0
215	}
216
217	lastObservation, err := lastObservation(observationState)
218	if err != nil {
219		return 0, "0", "0", 0
220	}
221
222	tickCumulative = lastObservation.TickCumulative()
223	liquidityCumulative = lastObservation.LiquidityCumulative().ToString()
224	secondsPerLiquidityCumulativeX128 = lastObservation.SecondsPerLiquidityCumulativeX128().ToString()
225	blockTimestamp = lastObservation.BlockTimestamp()
226
227	return
228}
229
230func (i *poolV1) GetPoolCreationFee() int64 {
231	return i.store.GetPoolCreationFee()
232}
233
234func (i *poolV1) GetWithdrawalFee() uint64 {
235	return i.store.GetWithdrawalFeeBPS()
236}
237
238// GetTWAP returns the time-weighted average price for a pool over a specified period
239//
240// Parameters:
241//   - poolPath: The path of the pool (e.g., "gno.land/r/demo/bar:gno.land/r/demo/foo:500")
242//   - secondsAgo: Number of seconds ago to calculate TWAP from
243//
244// Returns TWAP tick and error
245func (i *poolV1) GetTWAP(poolPath string, secondsAgo uint32) (int32, *u256.Uint, error) {
246	pool, err := i.getPool(poolPath)
247	if err != nil {
248		return 0, nil, err
249	}
250
251	return getTWAP(pool, secondsAgo)
252}
253
254// GetPoolCount returns the total number of pools.
255func (i *poolV1) GetPoolCount() int {
256	pools := i.store.GetPools()
257	return pools.Size()
258}
259
260// GetPoolPaths returns a paginated list of pool paths.
261func (i *poolV1) GetPoolPaths(offset, count int) []string {
262	pools := i.store.GetPools()
263	poolPaths := make([]string, 0)
264
265	pools.IterateByOffset(offset, count, func(key string, _ any) bool {
266		poolPaths = append(poolPaths, key)
267		return false
268	})
269
270	return poolPaths
271}
272
273// GetFeeAmountTickSpacings returns all fee tier to tick spacing mappings.
274func (i *poolV1) GetFeeAmountTickSpacings() map[uint32]int32 {
275	return i.store.GetFeeAmountTickSpacing()
276}
277
278// GetPoolPositionCount returns the number of positions in a pool.
279func (i *poolV1) GetPoolPositionCount(poolPath string) int {
280	pool, err := i.getPool(poolPath)
281	if err != nil {
282		return 0
283	}
284
285	return pool.Positions().Size()
286}
287
288// GetPoolPositionKeys returns a paginated list of position keys in a pool.
289func (i *poolV1) GetPoolPositionKeys(poolPath string, offset, count int) []string {
290	pool, err := i.getPool(poolPath)
291	if err != nil {
292		return []string{}
293	}
294
295	positionKeys := make([]string, 0)
296
297	pool.Positions().IterateByOffset(offset, count, func(key string, _ any) bool {
298		positionKeys = append(positionKeys, key)
299		return false
300	})
301
302	return positionKeys
303}
304
305// Tick enumeration
306
307// GetInitializedTicksInRange returns initialized ticks within the given range.
308func (i *poolV1) GetInitializedTicksInRange(poolPath string, tickLower, tickUpper int32) []int32 {
309	pool, err := i.getPool(poolPath)
310	if err != nil {
311		return []int32{}
312	}
313
314	ticks := make([]int32, 0)
315
316	pool.IterateTicks(tickLower, tickUpper, func(tick int32, _ pl.TickInfo) bool {
317		ticks = append(ticks, tick)
318		return false
319	})
320
321	return ticks
322}
323
324// Structure getters
325
326// GetTickInfo returns the tick info for a given tick.
327func (i *poolV1) GetTickInfo(poolPath string, tick int32) (pl.TickInfo, error) {
328	pool, err := i.getPool(poolPath)
329	if err != nil {
330		return pl.TickInfo{}, err
331	}
332
333	return pool.GetTick(tick)
334}
335
336// GetTickBitmaps returns the tick bitmap for a given word position.
337func (i *poolV1) GetTickBitmaps(poolPath string, wordPos int16) (*u256.Uint, error) {
338	pool, err := i.getPool(poolPath)
339	if err != nil {
340		return nil, err
341	}
342
343	wordPosStr := strconv.Itoa(int(wordPos))
344
345	iTickBitmap, ok := pool.TickBitmaps().Get(wordPosStr)
346	if !ok {
347		return nil, ufmt.Errorf("tick bitmap %d not found", wordPos)
348	}
349
350	tickBitmap, ok := iTickBitmap.(*u256.Uint)
351	if !ok {
352		return nil, ufmt.Errorf("failed to cast tick bitmap: %T", iTickBitmap)
353	}
354
355	return tickBitmap, nil
356}
357
358// GetPosition returns the position info for a given key.
359func (i *poolV1) GetPosition(poolPath, key string) (pl.PositionInfo, error) {
360	pool, err := i.getPool(poolPath)
361	if err != nil {
362		return pl.PositionInfo{}, err
363	}
364
365	iPositionInfo, ok := pool.Positions().Get(key)
366	if !ok {
367		return pl.PositionInfo{}, ufmt.Errorf("position %s not found", key)
368	}
369
370	positionInfo, ok := iPositionInfo.(pl.PositionInfo)
371	if !ok {
372		return pl.PositionInfo{}, ufmt.Errorf("failed to cast positionInfo: %T", iPositionInfo)
373	}
374
375	return positionInfo, nil
376}
377
378// GetObservationState returns the observation state for a pool.
379func (i *poolV1) GetObservationState(poolPath string) (*pl.ObservationState, error) {
380	pool, err := i.getPool(poolPath)
381	if err != nil {
382		return nil, err
383	}
384
385	observationState := pool.ObservationState()
386	if observationState == nil {
387		return nil, ufmt.Errorf("observation state not found for pool %s", poolPath)
388	}
389
390	return observationState, nil
391}