From 808b22ad565c4e7ac443b48ed109edad69025188 Mon Sep 17 00:00:00 2001 From: Blake <104744707+r3v4s@users.noreply.github.com> Date: Fri, 20 Dec 2024 17:23:35 +0900 Subject: [PATCH] GSW-1839 refactor: use avl.Tree in position (#440) * GSW-1839 refactor: use avl.Tree to manage list of position object - keep tokenId type as uint64 ( seqid is not necessary for position contract ) * GSW-1839 fix: getting avl data size * fix: sonarcube warning * fix: delete duplication * fix: missing error msg * fix: remove token register for pool * fix: error code changes * chore: remove `filename__function()` in error msg template * fix: run test fail issue --------- Co-authored-by: Lee ByeongJun Co-authored-by: 0xTopaz --- position/_GET_no_receiver.gno | 35 ++- position/_GET_no_receiver_string.gno | 12 +- position/_RPC_api.gno | 120 +++++----- position/_RPC_dry.gno | 8 +- position/_helper_test.gno | 19 +- position/errors.gno | 26 +- position/helper.gno | 2 +- position/liquidity_management.gno | 2 +- position/position.gno | 225 +++++++++++------- .../__TEST_0_INIT_VARS_HELPERS_test.gnoA | 3 +- position/tests/__TEST_position_full_test.gnoA | 3 +- ...osition_increase_burned_position_test.gnoA | 8 +- ..._TEST_position_increase_decrease_test.gnoA | 2 +- ...nt_gnot_grc20_in-range_out-range_test.gnoA | 4 +- ...osition_native_increase_decrease_test.gnoA | 4 +- ...T_position_native_mint_swap_burn_test.gnoA | 6 +- ...ST_position_reposition_gnot_pair_test.gnoA | 14 +- ...T_position_reposition_grc20_pair_test.gnoA | 20 +- ..._reposition_grc20_pair_with_swap_test.gnoA | 18 +- ...iff_range_diff_position_swap_fee_test.gnoA | 8 +- ...ame_range_diff_position_swap_fee_test.gnoA | 8 +- ...owed_left_grc20_pair_more_action_test.gnoA | 14 +- ...owed_left_pair_more_action_exact_test.gnoA | 14 +- position/utils_test.gno | 4 +- position/wrap_unwrap.gno | 2 +- 25 files changed, 315 insertions(+), 266 deletions(-) diff --git a/position/_GET_no_receiver.gno b/position/_GET_no_receiver.gno index ffd26f73..b49143d8 100644 --- a/position/_GET_no_receiver.gno +++ b/position/_GET_no_receiver.gno @@ -12,51 +12,62 @@ import ( // type Position func PositionGetPosition(tokenId uint64) Position { - return positions[tokenId] + position, _ := GetPosition(tokenId) + return position } func PositionGetPositionNonce(tokenId uint64) *u256.Uint { - return positions[tokenId].nonce + position := MustGetPosition(tokenId) + return position.nonce } func PositionGetPositionOperator(tokenId uint64) std.Address { - return positions[tokenId].operator + position := MustGetPosition(tokenId) + return position.operator } func PositionGetPositionPoolKey(tokenId uint64) string { - return positions[tokenId].poolKey + position := MustGetPosition(tokenId) + return position.poolKey } func PositionGetPositionTickLower(tokenId uint64) int32 { - return positions[tokenId].tickLower + position := MustGetPosition(tokenId) + return position.tickLower } func PositionGetPositionTickUpper(tokenId uint64) int32 { - return positions[tokenId].tickUpper + position := MustGetPosition(tokenId) + return position.tickUpper } func PositionGetPositionLiquidity(tokenId uint64) *u256.Uint { - return positions[tokenId].liquidity + position := MustGetPosition(tokenId) + return position.liquidity } func PositionGetPositionFeeGrowthInside0LastX128(tokenId uint64) *u256.Uint { - return positions[tokenId].feeGrowthInside0LastX128 + position := MustGetPosition(tokenId) + return position.feeGrowthInside0LastX128 } func PositionGetPositionFeeGrowthInside1LastX128(tokenId uint64) *u256.Uint { - return positions[tokenId].feeGrowthInside1LastX128 + position := MustGetPosition(tokenId) + return position.feeGrowthInside1LastX128 } func PositionGetPositionTokensOwed0(tokenId uint64) *u256.Uint { - return positions[tokenId].tokensOwed0 + position := MustGetPosition(tokenId) + return position.tokensOwed0 } func PositionGetPositionTokensOwed1(tokenId uint64) *u256.Uint { - return positions[tokenId].tokensOwed1 + position := MustGetPosition(tokenId) + return position.tokensOwed1 } func PositionIsInRange(tokenId uint64) bool { - position := positions[tokenId] + position := MustGetPosition(tokenId) poolPath := position.poolKey poolCurrentTick := pl.PoolGetSlot0Tick(poolPath) diff --git a/position/_GET_no_receiver_string.gno b/position/_GET_no_receiver_string.gno index 6048a62a..52a9c3a3 100644 --- a/position/_GET_no_receiver_string.gno +++ b/position/_GET_no_receiver_string.gno @@ -2,25 +2,25 @@ package position // type Position func PositionGetPositionNonceStr(tokenId uint64) string { - return positions[tokenId].nonce.ToString() + return MustGetPosition(tokenId).nonce.ToString() } func PositionGetPositionLiquidityStr(tokenId uint64) string { - return positions[tokenId].liquidity.ToString() + return MustGetPosition(tokenId).liquidity.ToString() } func PositionGetPositionFeeGrowthInside0LastX128Str(tokenId uint64) string { - return positions[tokenId].feeGrowthInside0LastX128.ToString() + return MustGetPosition(tokenId).feeGrowthInside0LastX128.ToString() } func PositionGetPositionFeeGrowthInside1LastX128Str(tokenId uint64) string { - return positions[tokenId].feeGrowthInside1LastX128.ToString() + return MustGetPosition(tokenId).feeGrowthInside1LastX128.ToString() } func PositionGetPositionTokensOwed0Str(tokenId uint64) string { - return positions[tokenId].tokensOwed0.ToString() + return MustGetPosition(tokenId).tokensOwed0.ToString() } func PositionGetPositionTokensOwed1Str(tokenId uint64) string { - return positions[tokenId].tokensOwed1.ToString() + return MustGetPosition(tokenId).tokensOwed1.ToString() } diff --git a/position/_RPC_api.gno b/position/_RPC_api.gno index 5b1cd3d0..5afcdd68 100644 --- a/position/_RPC_api.gno +++ b/position/_RPC_api.gno @@ -5,7 +5,6 @@ import ( "time" "gno.land/p/demo/json" - "gno.land/p/demo/ufmt" i256 "gno.land/p/gnoswap/int256" "gno.land/r/gnoswap/v1/common" @@ -52,8 +51,9 @@ type ResponseApiGetPositions struct { func ApiGetPositions() string { rpcPositions := []RpcPosition{} - for lpTokenId, _ := range positions { - rpcPosition := rpcMakePosition(lpTokenId) + + for tokenId := uint64(1); tokenId < nextId; tokenId++ { + rpcPosition := rpcMakePosition(tokenId) rpcPositions = append(rpcPositions, rpcPosition) } @@ -74,7 +74,7 @@ func ApiGetPositions() string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, position := range r.Response { - _positionNode := json.ObjectNode("", map[string]*json.Node{ + positionNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(position.LpTokenId)), "burned": json.BoolNode("burned", position.Burned), "owner": json.StringNode("owner", gnft.OwnerOf(tokenIdFrom(position.LpTokenId)).String()), @@ -92,7 +92,7 @@ func ApiGetPositions() string { "fee0Unclaimed": json.StringNode("fee0Unclaimed", position.FeeUnclaimed0), "fee1Unclaimed": json.StringNode("fee1Unclaimed", position.FeeUnclaimed1), }) - responses.AppendArray(_positionNode) + responses.AppendArray(positionNode) } node := json.ObjectNode("", map[string]*json.Node{ @@ -111,12 +111,14 @@ func ApiGetPositions() string { func ApiGetPosition(lpTokenId uint64) string { rpcPositions := []RpcPosition{} - _, ok := positions[lpTokenId] - if ok { - rpcPosition := rpcMakePosition(lpTokenId) - rpcPositions = append(rpcPositions, rpcPosition) + position, exist := GetPosition(lpTokenId) + if !exist { + return "" } + rpcPosition := rpcMakePosition(lpTokenId) + rpcPositions = append(rpcPositions, rpcPosition) + r := ResponseApiGetPositions{ Stat: ResponseQueryBase{ Height: std.GetHeight(), @@ -126,7 +128,7 @@ func ApiGetPosition(lpTokenId uint64) string { } // STAT NODE - _stat := json.ObjectNode("", map[string]*json.Node{ + stat := json.ObjectNode("", map[string]*json.Node{ "height": json.NumberNode("height", float64(std.GetHeight())), "timestamp": json.NumberNode("timestamp", float64(time.Now().Unix())), }) @@ -134,7 +136,7 @@ func ApiGetPosition(lpTokenId uint64) string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, position := range r.Response { - _positionNode := json.ObjectNode("", map[string]*json.Node{ + positionNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(position.LpTokenId)), "burned": json.BoolNode("burned", position.Burned), "owner": json.StringNode("owner", gnft.OwnerOf(tokenIdFrom(position.LpTokenId)).String()), @@ -152,11 +154,11 @@ func ApiGetPosition(lpTokenId uint64) string { "fee0Unclaimed": json.StringNode("fee0Unclaimed", position.FeeUnclaimed0), "fee1Unclaimed": json.StringNode("fee1Unclaimed", position.FeeUnclaimed1), }) - responses.AppendArray(_positionNode) + responses.AppendArray(positionNode) } node := json.ObjectNode("", map[string]*json.Node{ - "stat": _stat, + "stat": stat, "response": responses, }) @@ -170,8 +172,9 @@ func ApiGetPosition(lpTokenId uint64) string { func ApiGetPositionsByPoolPath(poolPath string) string { rpcPositions := []RpcPosition{} - for lpTokenId, position := range positions { + for lpTokenId := uint64(1); lpTokenId < nextId; lpTokenId++ { + position := MustGetPosition(lpTokenId) if position.poolKey != poolPath { continue } @@ -189,7 +192,7 @@ func ApiGetPositionsByPoolPath(poolPath string) string { } // STAT NODE - _stat := json.ObjectNode("", map[string]*json.Node{ + stat := json.ObjectNode("", map[string]*json.Node{ "height": json.NumberNode("height", float64(std.GetHeight())), "timestamp": json.NumberNode("timestamp", float64(time.Now().Unix())), }) @@ -197,7 +200,7 @@ func ApiGetPositionsByPoolPath(poolPath string) string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, position := range r.Response { - _positionNode := json.ObjectNode("", map[string]*json.Node{ + positionNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(position.LpTokenId)), "burned": json.BoolNode("burned", position.Burned), "owner": json.StringNode("owner", gnft.OwnerOf(tokenIdFrom(position.LpTokenId)).String()), @@ -215,11 +218,11 @@ func ApiGetPositionsByPoolPath(poolPath string) string { "fee0Unclaimed": json.StringNode("fee0Unclaimed", position.FeeUnclaimed0), "fee1Unclaimed": json.StringNode("fee1Unclaimed", position.FeeUnclaimed1), }) - responses.AppendArray(_positionNode) + responses.AppendArray(positionNode) } node := json.ObjectNode("", map[string]*json.Node{ - "stat": _stat, + "stat": stat, "response": responses, }) @@ -233,8 +236,8 @@ func ApiGetPositionsByPoolPath(poolPath string) string { func ApiGetPositionsByAddress(address std.Address) string { rpcPositions := []RpcPosition{} - for lpTokenId, position := range positions { - + for lpTokenId := uint64(1); lpTokenId < nextId; lpTokenId++ { + position := MustGetPosition(lpTokenId) if !(position.operator == address || gnft.OwnerOf(tokenIdFrom(lpTokenId)) == address) { continue } @@ -252,7 +255,7 @@ func ApiGetPositionsByAddress(address std.Address) string { } // STAT NODE - _stat := json.ObjectNode("", map[string]*json.Node{ + stat := json.ObjectNode("", map[string]*json.Node{ "height": json.NumberNode("height", float64(std.GetHeight())), "timestamp": json.NumberNode("timestamp", float64(time.Now().Unix())), }) @@ -260,7 +263,7 @@ func ApiGetPositionsByAddress(address std.Address) string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, position := range r.Response { - _positionNode := json.ObjectNode("", map[string]*json.Node{ + positionNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(position.LpTokenId)), "burned": json.BoolNode("burned", position.Burned), "owner": json.StringNode("owner", gnft.OwnerOf(tokenIdFrom(position.LpTokenId)).String()), @@ -278,11 +281,11 @@ func ApiGetPositionsByAddress(address std.Address) string { "fee0Unclaimed": json.StringNode("fee0Unclaimed", position.FeeUnclaimed0), "fee1Unclaimed": json.StringNode("fee1Unclaimed", position.FeeUnclaimed1), }) - responses.AppendArray(_positionNode) + responses.AppendArray(positionNode) } node := json.ObjectNode("", map[string]*json.Node{ - "stat": _stat, + "stat": stat, "response": responses, }) @@ -296,7 +299,7 @@ func ApiGetPositionsByAddress(address std.Address) string { func ApiGetPositionsUnclaimedFee() string { rpcUnclaimedFee := []RpcUnclaimedFee{} - for lpTokenId, _ := range positions { + for lpTokenId := uint64(1); lpTokenId < nextId; lpTokenId++ { unclaimedFee0, unclaimedFee1 := unclaimedFee(lpTokenId) rpcUnclaimedFee = append(rpcUnclaimedFee, RpcUnclaimedFee{ LpTokenId: lpTokenId, @@ -306,7 +309,7 @@ func ApiGetPositionsUnclaimedFee() string { } // STAT NODE - _stat := json.ObjectNode("", map[string]*json.Node{ + stat := json.ObjectNode("", map[string]*json.Node{ "height": json.NumberNode("height", float64(std.GetHeight())), "timestamp": json.NumberNode("timestamp", float64(time.Now().Unix())), }) @@ -314,16 +317,16 @@ func ApiGetPositionsUnclaimedFee() string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, unclaimedFee := range rpcUnclaimedFee { - _unclaimedFeeNode := json.ObjectNode("", map[string]*json.Node{ + unclaimedFeeNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(unclaimedFee.LpTokenId)), "fee0": json.StringNode("fee0", unclaimedFee.Fee0), "fee1": json.StringNode("fee1", unclaimedFee.Fee1), }) - responses.AppendArray(_unclaimedFeeNode) + responses.AppendArray(unclaimedFeeNode) } node := json.ObjectNode("", map[string]*json.Node{ - "stat": _stat, + "stat": stat, "response": responses, }) @@ -346,7 +349,7 @@ func ApiGetPositionUnclaimedFeeByLpTokenId(lpTokenId uint64) string { }) // STAT NODE - _stat := json.ObjectNode("", map[string]*json.Node{ + stat := json.ObjectNode("", map[string]*json.Node{ "height": json.NumberNode("height", float64(std.GetHeight())), "timestamp": json.NumberNode("timestamp", float64(time.Now().Unix())), }) @@ -354,16 +357,16 @@ func ApiGetPositionUnclaimedFeeByLpTokenId(lpTokenId uint64) string { // RESPONSE (ARRAY) NODE responses := json.ArrayNode("", []*json.Node{}) for _, unclaimedFee := range rpcUnclaimedFee { - _unclaimedFeeNode := json.ObjectNode("", map[string]*json.Node{ + unclaimedFeeNode := json.ObjectNode("", map[string]*json.Node{ "lpTokenId": json.NumberNode("lpTokenId", float64(unclaimedFee.LpTokenId)), "fee0": json.StringNode("fee0", unclaimedFee.Fee0), "fee1": json.StringNode("fee1", unclaimedFee.Fee1), }) - responses.AppendArray(_unclaimedFeeNode) + responses.AppendArray(unclaimedFeeNode) } node := json.ObjectNode("", map[string]*json.Node{ - "stat": _stat, + "stat": stat, "response": responses, }) @@ -376,13 +379,7 @@ func ApiGetPositionUnclaimedFeeByLpTokenId(lpTokenId uint64) string { } func rpcMakePosition(lpTokenId uint64) RpcPosition { - position, exist := positions[lpTokenId] - if !exist { - panic(addDetailToError( - errDataNotFound, - ufmt.Sprintf("_RPC_api.gno__rpcMakePosition() || lpTokenId(%d) not found", lpTokenId), - )) - } + position := MustGetPosition(lpTokenId) burned := isBurned(lpTokenId) @@ -427,40 +424,30 @@ func rpcMakePosition(lpTokenId uint64) RpcPosition { func unclaimedFee(tokenId uint64) (*i256.Int, *i256.Int) { // ref: https://blog.uniswap.org/uniswap-v3-math-primer-2#calculating-uncollected-fees - _liquidity := positions[tokenId].liquidity // u256 - liquidity := i256.FromUint256(_liquidity) // i256 + position := MustGetPosition(tokenId) + + liquidityU256 := position.liquidity + liquidity := i256.FromUint256(liquidityU256) - tickLower := positions[tokenId].tickLower - tickUpper := positions[tokenId].tickUpper + tickLower := position.tickLower + tickUpper := position.tickUpper - poolKey := positions[tokenId].poolKey + poolKey := position.poolKey pool := pl.GetPoolFromPoolPath(poolKey) currentTick := pool.Slot0Tick() - _feeGrowthGlobal0X128 := pool.FeeGrowthGlobal0X128() // u256 - feeGrowthGlobal0X128 := i256.FromUint256(_feeGrowthGlobal0X128) // i256 - - _feeGrowthGlobal1X128 := pool.FeeGrowthGlobal1X128() // u256 - feeGrowthGlobal1X128 := i256.FromUint256(_feeGrowthGlobal1X128) // i256 - - _tickUpperFeeGrowthOutside0X128 := pool.GetTickFeeGrowthOutside0X128(tickUpper) // u256 - tickUpperFeeGrowthOutside0X128 := i256.FromUint256(_tickUpperFeeGrowthOutside0X128) // i256 - - _tickUpperFeeGrowthOutside1X128 := pool.GetTickFeeGrowthOutside1X128(tickUpper) // u256 - tickUpperFeeGrowthOutside1X128 := i256.FromUint256(_tickUpperFeeGrowthOutside1X128) // i256 - - _tickLowerFeeGrowthOutside0X128 := pool.GetTickFeeGrowthOutside0X128(tickLower) // u256 - tickLowerFeeGrowthOutside0X128 := i256.FromUint256(_tickLowerFeeGrowthOutside0X128) // i256 + feeGrowthGlobal0X128 := i256.FromUint256(pool.FeeGrowthGlobal0X128()) + feeGrowthGlobal1X128 := i256.FromUint256(pool.FeeGrowthGlobal1X128()) - _tickLowerFeeGrowthOutside1X128 := pool.GetTickFeeGrowthOutside1X128(tickLower) // u256 - tickLowerFeeGrowthOutside1X128 := i256.FromUint256(_tickLowerFeeGrowthOutside1X128) // i256 + tickUpperFeeGrowthOutside0X128 := i256.FromUint256(pool.GetTickFeeGrowthOutside0X128(tickUpper)) + tickUpperFeeGrowthOutside1X128 := i256.FromUint256(pool.GetTickFeeGrowthOutside1X128(tickUpper)) - _feeGrowthInside0LastX128 := positions[tokenId].feeGrowthInside0LastX128 // u256 - feeGrowthInside0LastX128 := i256.FromUint256(_feeGrowthInside0LastX128) // i256 + tickLowerFeeGrowthOutside0X128 := i256.FromUint256(pool.GetTickFeeGrowthOutside0X128(tickLower)) + tickLowerFeeGrowthOutside1X128 := i256.FromUint256(pool.GetTickFeeGrowthOutside1X128(tickLower)) - _feeGrowthInside1LastX128 := positions[tokenId].feeGrowthInside1LastX128 // u256 - feeGrowthInside1LastX128 := i256.FromUint256(_feeGrowthInside1LastX128) // i256 + feeGrowthInside0LastX128 := i256.FromUint256(position.feeGrowthInside0LastX128) + feeGrowthInside1LastX128 := i256.FromUint256(position.feeGrowthInside1LastX128) var tickLowerFeeGrowthBelow0, tickLowerFeeGrowthBelow1, tickUpperFeeGrowthAbove0, tickUpperFeeGrowthAbove1 *i256.Int @@ -510,5 +497,6 @@ func subIn256(x, y *i256.Int) *i256.Int { } func isBurned(tokenId uint64) bool { - return positions[tokenId].burned + position := MustGetPosition(tokenId) + return position.burned } diff --git a/position/_RPC_dry.gno b/position/_RPC_dry.gno index 670ba038..56f361cb 100644 --- a/position/_RPC_dry.gno +++ b/position/_RPC_dry.gno @@ -23,16 +23,16 @@ func DryMint( tickCurrent int32, tickLower int32, tickUpper int32, - _amount0Desired string, - _amount1Desired string, + amount0DesiredStr string, + amount1DesiredStr string, ) (string, string) { // FROM: position__liquidity_management.gno sqrtRatioX96 := common.TickMathGetSqrtRatioAtTick(tickCurrent) sqrtLowerX96 := common.TickMathGetSqrtRatioAtTick(tickLower) sqrtUpperX96 := common.TickMathGetSqrtRatioAtTick(tickUpper) - amount0Desired := u256.MustFromDecimal(_amount0Desired) - amount1Desired := u256.MustFromDecimal(_amount1Desired) + amount0Desired := u256.MustFromDecimal(amount0DesiredStr) + amount1Desired := u256.MustFromDecimal(amount1DesiredStr) liquidity := common.GetLiquidityForAmounts( sqrtRatioX96, diff --git a/position/_helper_test.gno b/position/_helper_test.gno index f998f2ab..83736375 100644 --- a/position/_helper_test.gno +++ b/position/_helper_test.gno @@ -4,6 +4,7 @@ import ( "std" "testing" + "gno.land/p/demo/avl" "gno.land/p/demo/testutils" "gno.land/p/demo/uassert" pusers "gno.land/p/demo/users" @@ -155,18 +156,6 @@ func (QuxToken) Approve() func(spender pusers.AddressOrName, amount uint64) { return qux.Approve } -func init() { - std.TestSetRealm(std.NewUserRealm(consts.TOKEN_REGISTER)) - - pl.RegisterGRC20Interface(wugnotPath, WugnotToken{}) - pl.RegisterGRC20Interface(gnsPath, GNSToken{}) - pl.RegisterGRC20Interface(barPath, BarToken{}) - pl.RegisterGRC20Interface(bazPath, BazToken{}) - pl.RegisterGRC20Interface(fooPath, FooToken{}) - pl.RegisterGRC20Interface(oblPath, OBLToken{}) - pl.RegisterGRC20Interface(quxPath, QuxToken{}) -} - var ( admin = pusers.AddressOrName(consts.ADMIN) alice = pusers.AddressOrName(testutils.TestAddress("alice")) @@ -544,7 +533,7 @@ func ugnotDeposit(t *testing.T, addr std.Address, amount uint64) { // resetObject resets the object state(clear or make it default values) func resetObject(t *testing.T) { - positions = make(map[uint64]Position) + positions = avl.NewTree() nextId = 1 } @@ -567,7 +556,7 @@ func TestBeforeResetObject(t *testing.T) { uassert.Equal(t, liquidity, "50000", "liquidity should be 50000") uassert.Equal(t, amount0, "50000", "amount0 should be 50000") uassert.Equal(t, amount1, "50000", "amount1 should be 50000") - uassert.Equal(t, len(positions), 1, "positions should have 1 position") + uassert.Equal(t, positions.Size(), 1, "positions should have 1 position") uassert.Equal(t, nextId, uint64(2), "nextId should be 2") uassert.Equal(t, gnft.TotalSupply(), uint64(1), "gnft total supply should be 1") uassert.Equal(t, pl.PoolGetLiquidity("gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500"), "50000", "pool liquidity should be 50000") @@ -576,7 +565,7 @@ func TestBeforeResetObject(t *testing.T) { func TestResetObject(t *testing.T) { resetObject(t) - uassert.Equal(t, len(positions), 0, "positions should be empty") + uassert.Equal(t, positions.Size(), 0, "positions should be empty") uassert.Equal(t, nextId, uint64(1), "nextId should be 1") } diff --git a/position/errors.gno b/position/errors.gno index 60ef43ce..bfc2dd96 100644 --- a/position/errors.gno +++ b/position/errors.gno @@ -7,21 +7,21 @@ import ( ) var ( - errNoPermission = errors.New("[GNOSWAP-POSITION-001] caller has no permission") - errSlippage = errors.New("[GNOSWAP-POSITION-002] slippage failed") - errWrapUnwrap = errors.New("[GNOSWAP-POSITION-003] wrap, unwrap failed") - errOutOfRange = errors.New("[GNOSWAP-POSITION-004] out of range for numeric value") - errInvalidInput = errors.New("[GNOSWAP-POSITION-005] invalid input data") - errDataNotFound = errors.New("[GNOSWAP-POSITION-006] requested data not found") - errExpired = errors.New("[GNOSWAP-POSITION-007] transaction expired") - errWugnotMinimum = errors.New("[GNOSWAP-POSITION-008] can not wrap less than minimum amount") - errNotClear = errors.New("[GNOSWAP-POSITION-009] position is not clear") - errZeroLiquidity = errors.New("[GNOSWAP-POSITION-010] zero liquidity") - errInvalidAddress = errors.New("[GNOSWAP-POSITION-011] invalid address") + errNoPermission = errors.New("[GNOSWAP-POSITION-001] caller has no permission") + errSlippage = errors.New("[GNOSWAP-POSITION-002] slippage failed") + errWrapUnwrap = errors.New("[GNOSWAP-POSITION-003] wrap, unwrap failed") + errOutOfRange = errors.New("[GNOSWAP-POSITION-004] out of range for numeric value") + errInvalidInput = errors.New("[GNOSWAP-POSITION-005] invalid input data") + errDataNotFound = errors.New("[GNOSWAP-POSITION-006] requested data not found") + errExpired = errors.New("[GNOSWAP-POSITION-007] transaction expired") + errWugnotMinimum = errors.New("[GNOSWAP-POSITION-008] can not wrap less than minimum amount") + errNotClear = errors.New("[GNOSWAP-POSITION-009] position is not clear") + errZeroLiquidity = errors.New("[GNOSWAP-POSITION-010] zero liquidity") + errPositionExist = errors.New("[GNOSWAP-POSITION-011] position with same tokenId already exists") + errInvalidAddress = errors.New("[GNOSWAP-POSITION-012] invalid address") + errPositionDoesNotExist = errors.New("[GNOSWAP-POSITION-013] position does not exist") ) -// TODO: -// addDetailToError -> newErrorWithDetail func addDetailToError(err error, detail string) string { finalErr := ufmt.Errorf("%s || %s", err.Error(), detail) return finalErr.Error() diff --git a/position/helper.gno b/position/helper.gno index 532e0fdc..806acacd 100644 --- a/position/helper.gno +++ b/position/helper.gno @@ -102,7 +102,7 @@ func isOwnerOrOperator(addr std.Address, tokenId uint64) bool { return true } if isStaked(tokenIdFrom(tokenId)) { - position, exist := positions[tokenId] + position, exist := GetPosition(tokenId) if exist && addr == position.operator { return true } diff --git a/position/liquidity_management.gno b/position/liquidity_management.gno index d700bfb3..d9a77d0f 100644 --- a/position/liquidity_management.gno +++ b/position/liquidity_management.gno @@ -49,7 +49,7 @@ func addLiquidity(params AddLiquidityParams) (*u256.Uint, *u256.Uint, *u256.Uint if !(amount0Cond && amount1Cond) { panic(addDetailToError( errSlippage, - ufmt.Sprintf("liquidity_management.gno__addLiquidity() || LM_Price Slippage Check(amount0(%s) >= params.amount0Min(%s), amount1(%s) >= params.amount1Min(%s))", amount0Uint.ToString(), params.amount0Min.ToString(), amount1Uint.ToString(), params.amount1Min.ToString()), + ufmt.Sprintf("LM_Price Slippage Check(amount0(%s) >= params.amount0Min(%s), amount1(%s) >= params.amount1Min(%s))", amount0Uint.ToString(), params.amount0Min.ToString(), amount1Uint.ToString(), params.amount1Min.ToString()), )) } diff --git a/position/position.gno b/position/position.gno index 42503da3..a2d1cd0a 100644 --- a/position/position.gno +++ b/position/position.gno @@ -2,6 +2,9 @@ package position import ( "std" + "strconv" + + "gno.land/p/demo/avl" "gno.land/p/demo/ufmt" "gno.land/r/demo/wugnot" @@ -17,8 +20,8 @@ import ( ) var ( - positions map[uint64]Position = make(map[uint64]Position) // tokenId -> Position - nextId uint64 = 1 // lp token id + positions = avl.NewTree() // tokenId[uint64] -> Position + nextId = uint64(1) ) // Mint creates a new liquidity position and mints liquidity tokens. @@ -31,10 +34,10 @@ func Mint( fee uint32, tickLower int32, tickUpper int32, - _amount0Desired string, // *u256.Uint - _amount1Desired string, // *u256.Uint - _amount0Min string, // *u256.Uint - _amount1Min string, // *u256.Uint + amount0DesiredStr string, + amount1DesiredStr string, + amount0MinStr string, + amount1MinStr string, deadline int64, mintTo std.Address, caller std.Address, @@ -51,7 +54,7 @@ func Mint( if !(isUserCalled || isStakerCalled) { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__Mint() || only user or staker can call isUserCalled(%t) || isStakerCalled(%t), but called from %s", isUserCalled, isStakerCalled, prev.Addr().String()), + ufmt.Sprintf("only user or staker can call isUserCalled(%t) || isStakerCalled(%t), but called from %s", isUserCalled, isStakerCalled, prev.Addr().String()), )) } } @@ -67,16 +70,16 @@ func Mint( if token1 < token0 { token0, token1 = token1, token0 - _amount0Desired, _amount1Desired = _amount1Desired, _amount0Desired - _amount0Min, _amount1Min = _amount1Min, _amount0Min + amount0DesiredStr, amount1DesiredStr = amount1DesiredStr, amount0DesiredStr + amount0MinStr, amount1MinStr = amount1MinStr, amount0MinStr tickLower, tickUpper = -tickUpper, -tickLower token0IsNative, token1IsNative = token1IsNative, token0IsNative } - amount0Desired := u256.MustFromDecimal(_amount0Desired) - amount1Desired := u256.MustFromDecimal(_amount1Desired) - amount0Min := u256.MustFromDecimal(_amount0Min) - amount1Min := u256.MustFromDecimal(_amount1Min) + amount0Desired := u256.MustFromDecimal(amount0DesiredStr) + amount1Desired := u256.MustFromDecimal(amount1DesiredStr) + amount0Min := u256.MustFromDecimal(amount0MinStr) + amount1Min := u256.MustFromDecimal(amount1MinStr) // one of token amount can be 0 if position is out of range // check this condition by using DryMint() @@ -150,7 +153,7 @@ func handleNativeToken(token0IsNative, token1IsNative bool, caller std.Address) if (newUserWugnotBalance - oldUserWugnotBalance) != ugnotSent { panic(addDetailToError( errWrapUnwrap, - ufmt.Sprintf("position.gno__Mint() || ugnot sent(%d) != wugnot received(%d)", ugnotSent, newUserWugnotBalance-oldUserWugnotBalance), + ufmt.Sprintf("ugnot sent(%d) != wugnot received(%d)", ugnotSent, newUserWugnotBalance-oldUserWugnotBalance), )) } } @@ -207,7 +210,13 @@ func mint(params MintParams) (uint64, *u256.Uint, *u256.Uint, *u256.Uint) { tokensOwed1: u256.Zero(), burned: false, } - positions[tokenId] = position + updated := setPosition(tokenId, position) + if updated { + panic(addDetailToError( + errPositionExist, + ufmt.Sprintf("tokenId(%d) already exists", tokenId), + )) + } return tokenId, liquidity, amount0, amount1 } @@ -217,19 +226,19 @@ func mint(params MintParams) (uint64, *u256.Uint, *u256.Uint, *u256.Uint) { // ref: https://docs.gnoswap.io/contracts/position/position.gno#increaseliquidity func IncreaseLiquidity( tokenId uint64, - _amount0Desired string, // uint256 - _amount1Desired string, // uint256 - _amount0Min string, // uint256 - _amount1Min string, // uint256 + amount0DesiredStr string, + amount1DesiredStr string, + amount0MinStr string, + amount1MinStr string, deadline int64, ) (uint64, string, string, string, string) { common.IsHalted() en.MintAndDistributeGns() - amount0Desired := u256.MustFromDecimal(_amount0Desired) - amount1Desired := u256.MustFromDecimal(_amount1Desired) - amount0Min := u256.MustFromDecimal(_amount0Min) - amount1Min := u256.MustFromDecimal(_amount1Min) + amount0Desired := u256.MustFromDecimal(amount0DesiredStr) + amount1Desired := u256.MustFromDecimal(amount1DesiredStr) + amount0Min := u256.MustFromDecimal(amount0MinStr) + amount1Min := u256.MustFromDecimal(amount1MinStr) increaseLiquidityParams := IncreaseLiquidityParams{ tokenId: tokenId, amount0Desired: amount0Desired, @@ -240,7 +249,7 @@ func IncreaseLiquidity( } // wrap if target pool has wugnot - position := positions[tokenId] + position := MustGetPosition(tokenId) pToken0, pToken1, _ := splitOf(position.poolKey) isToken0Wugnot := pToken0 == consts.WRAPPED_WUGNOT @@ -288,7 +297,7 @@ func increaseLiquidity(params IncreaseLiquidityParams) (uint64, *u256.Uint, *u25 if !exists(params.tokenId) { panic(addDetailToError( errDataNotFound, - ufmt.Sprintf("position.gno__increaseLiquidity() || tokenId(%d) doesn't exist", params.tokenId), + ufmt.Sprintf("tokenId(%d) doesn't exist", params.tokenId), )) } @@ -299,13 +308,13 @@ func increaseLiquidity(params IncreaseLiquidityParams) (uint64, *u256.Uint, *u25 if owner != caller { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__increaseLiquidity() || only owner(%s) can increase liquidity for tokenId(%d), but called from %s", owner, params.tokenId, caller), + ufmt.Sprintf("only owner(%s) can increase liquidity for tokenId(%d), but called from %s", owner, params.tokenId, caller), )) } checkDeadline(params.deadline) - position := positions[params.tokenId] + position := MustGetPosition(params.tokenId) liquidity, amount0, amount1 := addLiquidity( AddLiquidityParams{ poolKey: position.poolKey, @@ -345,7 +354,13 @@ func increaseLiquidity(params IncreaseLiquidityParams) (uint64, *u256.Uint, *u25 position.liquidity = new(u256.Uint).Add(position.liquidity, liquidity) position.burned = false - positions[params.tokenId] = position + updated := setPosition(params.tokenId, position) + if !updated { + panic(addDetailToError( + errPositionDoesNotExist, + ufmt.Sprintf("can not increase liquidity for non-existent position(%d)", params.tokenId), + )) + } return params.tokenId, liquidity, amount0, amount1, position.poolKey } @@ -357,8 +372,8 @@ func increaseLiquidity(params IncreaseLiquidityParams) (uint64, *u256.Uint, *u25 func DecreaseLiquidity( tokenId uint64, liquidityRatio uint64, - _amount0Min string, // uint256 - _amount1Min string, // uint256 + amount0MinStr string, + amount1MinStr string, deadline int64, unwrapResult bool, ) (uint64, string, string, string, string, string, string) { @@ -369,12 +384,12 @@ func DecreaseLiquidity( if !isNormalRange { panic(addDetailToError( errOutOfRange, - ufmt.Sprintf("position.gno__decreaseLiquidity() || liquidityRatio(%d) should be in range 1 ~ 100", liquidityRatio), + ufmt.Sprintf("liquidityRatio(%d) should be in range 1 ~ 100", liquidityRatio), )) } - amount0Min := u256.MustFromDecimal(_amount0Min) - amount1Min := u256.MustFromDecimal(_amount1Min) + amount0Min := u256.MustFromDecimal(amount0MinStr) + amount1Min := u256.MustFromDecimal(amount1MinStr) decreaseLiquidityParams := DecreaseLiquidityParams{ tokenId: tokenId, liquidityRatio: liquidityRatio, @@ -424,13 +439,13 @@ func decreaseLiquidity(params DecreaseLiquidityParams) (uint64, *u256.Uint, *u25 fee0 := u256.MustFromDecimal(fee0Str) fee1 := u256.MustFromDecimal(fee1Str) - position := positions[params.tokenId] + position := MustGetPosition(params.tokenId) positionLiquidity := position.liquidity if positionLiquidity.IsZero() { panic(addDetailToError( errZeroLiquidity, - ufmt.Sprintf("position.gno__decreaseLiquidity() || position(tokenId:%d) has 0 liquidity", params.tokenId), + ufmt.Sprintf("position(tokenId:%d) has 0 liquidity", params.tokenId), )) } @@ -472,7 +487,13 @@ func decreaseLiquidity(params DecreaseLiquidityParams) (uint64, *u256.Uint, *u25 position.feeGrowthInside0LastX128 = feeGrowthInside0LastX128 position.feeGrowthInside1LastX128 = feeGrowthInside1LastX128 position.liquidity = new(u256.Uint).Sub(positionLiquidity, liquidityToRemove) - positions[params.tokenId] = position + updated := setPosition(params.tokenId, position) + if !updated { + panic(addDetailToError( + errPositionDoesNotExist, + ufmt.Sprintf("can not decrease liquidity for non-existent position(%d)", params.tokenId), + )) + } // GIVE BACK TO USER _amount0, _amount1 := pl.Collect( @@ -498,7 +519,7 @@ func decreaseLiquidity(params DecreaseLiquidityParams) (uint64, *u256.Uint, *u25 if overflow { position.tokensOwed1 = u256.Zero() } - positions[params.tokenId] = position + setPosition(params.tokenId, position) if position.isClear() { burnPosition(params.tokenId) // just update flag (we don't want to burn actual position) @@ -522,10 +543,10 @@ func Reposition( tokenId uint64, tickLower int32, tickUpper int32, - _amount0Desired string, // uint256 - _amount1Desired string, // uint256 - _amount0Min string, // *u256.Uint - _amount1Min string, // *u256.Uint + amount0DesiredStr string, + amount1DesiredStr string, + amount0MinStr string, + amount1MinStr string, ) (uint64, string, int32, int32, string, string) { common.IsHalted() en.MintAndDistributeGns() @@ -534,7 +555,7 @@ func Reposition( if !exists(tokenId) { panic(addDetailToError( errDataNotFound, - ufmt.Sprintf("position.gno__Reposition() || tokenId(%d) doesn't exist", tokenId), + ufmt.Sprintf("tokenId(%d) doesn't exist", tokenId), )) } @@ -545,19 +566,19 @@ func Reposition( if owner != caller { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__Reposition() || only owner(%s) can reposition for tokenId(%d), but called from %s", owner, tokenId, caller), + ufmt.Sprintf("only owner(%s) can reposition for tokenId(%d), but called from %s", owner, tokenId, caller), )) } // position should be burned to reposition - position := positions[tokenId] + position := MustGetPosition(tokenId) oldTickLower := position.tickLower oldTickUpper := position.tickUpper if !(position.isClear()) { panic(addDetailToError( errNotClear, - ufmt.Sprintf("position.gno__Reposition() || position(%d) isn't clear(liquidity:%s, tokensOwed0:%s, tokensOwed1:%s)", tokenId, position.liquidity.ToString(), position.tokensOwed0.ToString(), position.tokensOwed1.ToString()), + ufmt.Sprintf("position(%d) isn't clear(liquidity:%s, tokensOwed0:%s, tokensOwed1:%s)", tokenId, position.liquidity.ToString(), position.tokensOwed0.ToString(), position.tokensOwed1.ToString()), )) } @@ -585,10 +606,10 @@ func Reposition( poolKey: position.poolKey, tickLower: tickLower, tickUpper: tickUpper, - amount0Desired: u256.MustFromDecimal(_amount0Desired), - amount1Desired: u256.MustFromDecimal(_amount1Desired), - amount0Min: u256.MustFromDecimal(_amount0Min), - amount1Min: u256.MustFromDecimal(_amount1Min), + amount0Desired: u256.MustFromDecimal(amount0DesiredStr), + amount1Desired: u256.MustFromDecimal(amount1DesiredStr), + amount0Min: u256.MustFromDecimal(amount0MinStr), + amount1Min: u256.MustFromDecimal(amount1MinStr), caller: std.PrevRealm().Addr(), }, ) @@ -615,7 +636,13 @@ func Reposition( position.tokensOwed1 = u256.Zero() position.burned = false - positions[tokenId] = position + updated := setPosition(tokenId, position) + if !updated { + panic(addDetailToError( + errPositionDoesNotExist, + ufmt.Sprintf("can not reposition non-existent position(%d)", tokenId), + )) + } poolSqrtPriceX96 := pl.PoolGetSlot0SqrtPriceX96(position.poolKey) @@ -651,7 +678,7 @@ func CollectFee(tokenId uint64, unwrapResult bool) (uint64, string, string, stri if !exists(tokenId) { panic(addDetailToError( errDataNotFound, - ufmt.Sprintf("position.gno__CollectFee() || tokenId(%d) doesn't exist", tokenId), + ufmt.Sprintf("tokenId(%d) doesn't exist", tokenId), )) } @@ -659,13 +686,7 @@ func CollectFee(tokenId uint64, unwrapResult bool) (uint64, string, string, stri isAuthorizedForToken(tokenId) // verify position - position, exist := positions[tokenId] - if !exist { - panic(addDetailToError( - errDataNotFound, - ufmt.Sprintf("position.gno__CollectFee() || position(%d) doesn't exist", tokenId), - )) - } + position := MustGetPosition(tokenId) token0, token1, fee := splitOf(position.poolKey) @@ -725,7 +746,13 @@ func CollectFee(tokenId uint64, unwrapResult bool) (uint64, string, string, stri position.tokensOwed0 = new(u256.Uint).Sub(tokensOwed0, u256.MustFromDecimal(amount0)) position.tokensOwed1 = new(u256.Uint).Sub(tokensOwed1, u256.MustFromDecimal(amount1)) - positions[tokenId] = position + updated := setPosition(tokenId, position) + if !updated { + panic(addDetailToError( + errPositionDoesNotExist, + ufmt.Sprintf("can not collect fee for non-existent position(%d)", tokenId), + )) + } // handle withdrawal fee withoutFee0, withoutFee1 := pl.HandleWithdrawalFee(tokenId, token0, amount0, token1, amount1, position.poolKey, std.PrevRealm().Addr()) @@ -778,39 +805,30 @@ func updateTokensOwed( return new(u256.Uint).Add(tokensOwed, add) } -func burnNFT(tokenId uint64) { - isAuthorizedForToken(tokenId) - - position := positions[tokenId] - +func burnPosition(tokenId uint64) { + position := MustGetPosition(tokenId) if !(position.isClear()) { panic(addDetailToError( errNotClear, - ufmt.Sprintf("position.gno__burnNFT() || position(%d) isn't clear(liquidity:%s, tokensOwed0:%s, tokensOwed1:%s)", tokenId, position.liquidity.ToString(), position.tokensOwed0.ToString(), position.tokensOwed1.ToString()), + ufmt.Sprintf("position(%d) isn't clear(liquidity:%s, tokensOwed0:%s, tokensOwed1:%s)", tokenId, position.liquidity.ToString(), position.tokensOwed0.ToString(), position.tokensOwed1.ToString()), )) } - delete(positions, tokenId) - gnft.Burn(tokenIdFrom(tokenId)) -} -func burnPosition(tokenId uint64) { - position := positions[tokenId] - if !(position.isClear()) { + position.burned = true + updated := setPosition(tokenId, position) + if !updated { panic(addDetailToError( - errNotClear, - ufmt.Sprintf("position.gno__burnPosition() || position(%d) isn't clear(liquidity:%s, tokensOwed0:%s, tokensOwed1:%s)", tokenId, position.liquidity.ToString(), position.tokensOwed0.ToString(), position.tokensOwed1.ToString()), + errDataNotFound, + ufmt.Sprintf("can not burn non-existent position(%d)", tokenId), )) } - - position.burned = true - positions[tokenId] = position } func isAuthorizedForToken(tokenId uint64) { if !(isOwnerOrOperator(std.PrevRealm().Addr(), tokenId)) { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__isAuthorizedForToken() || caller(%s) is not approved or owner of tokenId(%d)", std.PrevRealm().Addr(), tokenId), + ufmt.Sprintf("caller(%s) is not approved or owner of tokenId(%d)", std.PrevRealm().Addr(), tokenId), )) } } @@ -819,7 +837,7 @@ func verifyTokenIdAndOwnership(tokenId uint64) { if !exists(tokenId) { panic(addDetailToError( errDataNotFound, - ufmt.Sprintf("position.gno__verifyTokenIdAndOwnership() || tokenId(%d) doesn't exist", tokenId), + ufmt.Sprintf("tokenId(%d) doesn't exist", tokenId), )) } @@ -828,7 +846,7 @@ func verifyTokenIdAndOwnership(tokenId uint64) { if owner != caller { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__verifyTokenIdAndOwnership() || only owner(%s) can decrease liquidity(tokenId:%d), but called from %s", owner, tokenId, caller), + ufmt.Sprintf("only owner(%s) can decrease liquidity(tokenId:%d), but called from %s", owner, tokenId, caller), )) } } @@ -846,7 +864,7 @@ func verifyBurnedAmounts(burnedAmount0, burnedAmount1, amount0Min, amount1Min *u if !(burnedAmount0.Gte(amount0Min) && burnedAmount1.Gte(amount1Min)) { panic(addDetailToError( errSlippage, - ufmt.Sprintf("position.gno__verifyBurnedAmounts() || burnedAmount0(%s) >= amount0Min(%s) && burnedAmount1(%s) >= amount1Min(%s)", burnedAmount0.ToString(), amount0Min.ToString(), burnedAmount1.ToString(), amount1Min.ToString()), + ufmt.Sprintf("burnedAmount0(%s) >= amount0Min(%s) && burnedAmount1(%s) >= amount1Min(%s)", burnedAmount0.ToString(), amount0Min.ToString(), burnedAmount1.ToString(), amount1Min.ToString()), )) } } @@ -864,18 +882,55 @@ func SetPositionOperator(tokenId uint64, operator std.Address) { if caller != consts.STAKER_PATH { panic(addDetailToError( errNoPermission, - ufmt.Sprintf("position.gno__SetPositionOperator() || caller(%s) is not staker", caller), + ufmt.Sprintf("caller(%s) is not staker", caller), + )) + } + + position := MustGetPosition(tokenId) + position.operator = operator + updated := setPosition(tokenId, position) + if !updated { + panic(addDetailToError( + errPositionDoesNotExist, + ufmt.Sprintf("can not set operator for non-existent position(%d)", tokenId), )) } +} - position, exist := positions[tokenId] +// MustGetPosition returns a position for a given tokenId +// panics if position doesn't exist +func MustGetPosition(tokenId uint64) Position { + position, exist := GetPosition(tokenId) if !exist { panic(addDetailToError( errDataNotFound, - ufmt.Sprintf("position.gno__SetPositionOperator() || position(%d) doesn't exist", tokenId), + ufmt.Sprintf("position with tokenId(%d) doesn't exist", tokenId), )) } + return position +} - position.operator = operator - positions[tokenId] = position +// GetPosition returns a position for a given tokenId +// Returns false if position doesn't exist +func GetPosition(tokenId uint64) (Position, bool) { + tokenIdStr := strconv.FormatUint(tokenId, 10) + iPosition, exist := positions.Get(tokenIdStr) + if !exist { + return Position{}, false + } + + return iPosition.(Position), true +} + +// setPosition sets a position for a given tokenId +// Returns true if position is newly created, false if position already exists and just updated. +func setPosition(tokenId uint64, position Position) bool { + tokenIdStr := strconv.FormatUint(tokenId, 10) + return positions.Set(tokenIdStr, position) +} + +// removePosition removes a position for a given tokenId +func removePosition(tokenId uint64) { + tokenIdStr := strconv.FormatUint(tokenId, 10) + positions.Remove(tokenIdStr) } diff --git a/position/tests/__TEST_0_INIT_VARS_HELPERS_test.gnoA b/position/tests/__TEST_0_INIT_VARS_HELPERS_test.gnoA index f7972bb9..a3732dab 100644 --- a/position/tests/__TEST_0_INIT_VARS_HELPERS_test.gnoA +++ b/position/tests/__TEST_0_INIT_VARS_HELPERS_test.gnoA @@ -63,7 +63,6 @@ func isOwner(t *testing.T, tokenId uint64, addr std.Address) bool { } func getPoolFromLpTokenId(lpTokenId uint64) *pl.Pool { - position := positions[lpTokenId] - + position := MustGetPosition(lpTokenId) return pl.GetPoolFromPoolPath(position.poolKey) } diff --git a/position/tests/__TEST_position_full_test.gnoA b/position/tests/__TEST_position_full_test.gnoA index 3577b249..abf32fa4 100644 --- a/position/tests/__TEST_position_full_test.gnoA +++ b/position/tests/__TEST_position_full_test.gnoA @@ -7,12 +7,11 @@ import ( "gno.land/r/gnoswap/v1/common" "gno.land/r/gnoswap/v1/consts" + "gno.land/r/gnoswap/v1/gns" pl "gno.land/r/gnoswap/v1/pool" "gno.land/r/onbloc/bar" "gno.land/r/onbloc/foo" - - "gno.land/r/gnoswap/v1/gns" ) func init() { diff --git a/position/tests/__TEST_position_increase_burned_position_test.gnoA b/position/tests/__TEST_position_increase_burned_position_test.gnoA index f2fcf71f..1fcfe4cc 100644 --- a/position/tests/__TEST_position_increase_burned_position_test.gnoA +++ b/position/tests/__TEST_position_increase_burned_position_test.gnoA @@ -103,7 +103,7 @@ func TestDecreaseLiquidity(t *testing.T) { uassert.Equal(t, fee0, "0") uassert.Equal(t, fee1, "0") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.burned, false) // not burned yet } @@ -119,7 +119,7 @@ func TestDecreaseLiquidityToBurnPosition(t *testing.T) { max_timeout, // deadline true, // unwrapResult ) - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.burned, true) // it is burned uassert.Equal(t, position.liquidity.ToString(), "0") // and liquidity is 0 } @@ -132,7 +132,7 @@ func TestIncreaseLiquidityBurnedPosition(t *testing.T) { pool := getPoolFromLpTokenId(uint64(1)) oldLiquidity := pool.PoolGetLiquidity() - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.burned, true) // it is burned _, _, m0, m1, _ := IncreaseLiquidity( @@ -150,6 +150,6 @@ func TestIncreaseLiquidityBurnedPosition(t *testing.T) { newLiquidity := pool.PoolGetLiquidity() uassert.Equal(t, newLiquidity.Gt(oldLiquidity), true) - position = positions[uint64(1)] + position = MustGetPosition(uint64(1)) uassert.Equal(t, position.burned, false) } diff --git a/position/tests/__TEST_position_increase_decrease_test.gnoA b/position/tests/__TEST_position_increase_decrease_test.gnoA index cf356b53..5abf8059 100644 --- a/position/tests/__TEST_position_increase_decrease_test.gnoA +++ b/position/tests/__TEST_position_increase_decrease_test.gnoA @@ -200,7 +200,7 @@ func TestDecreaseLiquidityAllThenAgainShouldPanic(t *testing.T) { // decreasing position(with 0 liquidity) should panic uassert.PanicsWithMessage( t, - `[GNOSWAP-POOL-010] zero liquidity || position.gno__positionUpdate() || both liquidityDelta and (self)liquidity are zero`, + `[GNOSWAP-POOL-010] zero liquidity || both liquidityDelta and current position's liquidity are zero`, func() { DecreaseLiquidity( uint64(1), // tokenId diff --git a/position/tests/__TEST_position_mint_gnot_grc20_in-range_out-range_test.gnoA b/position/tests/__TEST_position_mint_gnot_grc20_in-range_out-range_test.gnoA index f9bc8af4..e0d17d96 100644 --- a/position/tests/__TEST_position_mint_gnot_grc20_in-range_out-range_test.gnoA +++ b/position/tests/__TEST_position_mint_gnot_grc20_in-range_out-range_test.gnoA @@ -110,6 +110,7 @@ func TestOneSideOnlyUgnot(t *testing.T) { wugnot.Approve(a2u(consts.POSITION_ADDR), consts.UINT64_MAX) // POSITION FOR WRAP std.TestSetOrigSend(std.Coins{{"ugnot", 100_000_000}}, nil) + std.TestIssueCoins(consts.POSITION_ADDR, std.Coins{{"ugnot", 100_000_000}}) uassert.Equal(t, ugnotBalanceOf(fresh01), uint64(0)) std.TestSetRealm(fresh01Realm) @@ -144,6 +145,7 @@ func TestBothWithFresh(t *testing.T) { wugnot.Approve(a2u(consts.POSITION_ADDR), consts.UINT64_MAX) // POSITION FOR WRAP + std.TestIssueCoins(consts.POSITION_ADDR, std.Coins{{"ugnot", 100_000_000}}) std.TestSetOrigSend(std.Coins{{"ugnot", 100_000_000}}, nil) uassert.Equal(t, ugnotBalanceOf(fresh02), uint64(0)) @@ -184,7 +186,7 @@ func TestBothWithFreshButNoSend(t *testing.T) { std.TestSetRealm(fresh02Realm) uassert.PanicsWithMessage( t, - `WUGNOT:insufficient balance`, + `insufficient balance`, func() { Mint(consts.GNS_PATH, consts.GNOT, fee500, 6000, 16000, "70000000", "70000000", "0", "0", max_timeout, fresh02, fresh02) }, diff --git a/position/tests/__TEST_position_native_increase_decrease_test.gnoA b/position/tests/__TEST_position_native_increase_decrease_test.gnoA index b9837dfc..9b676a9f 100644 --- a/position/tests/__TEST_position_native_increase_decrease_test.gnoA +++ b/position/tests/__TEST_position_native_increase_decrease_test.gnoA @@ -44,6 +44,8 @@ func testMintPosition(t *testing.T) { // prepare 50000005ugnot (5 for refund test) std.TestIssueCoins(admin, std.Coins{{"ugnot", 50000005}}) uassert.Equal(t, ugnotBalanceOf(admin), uint64(50000005)) + + std.TestIssueCoins(consts.POSITION_ADDR, std.Coins{{"ugnot", 200000000}}) uassert.Equal(t, ugnotBalanceOf(consts.POSITION_ADDR), uint64(200000000)) // send & set orig send @@ -76,7 +78,7 @@ func testMintPosition(t *testing.T) { uassert.Equal(t, amount0, "50000000") uassert.Equal(t, amount1, "18394892") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") // SPEND ALL WUGNOT diff --git a/position/tests/__TEST_position_native_mint_swap_burn_test.gnoA b/position/tests/__TEST_position_native_mint_swap_burn_test.gnoA index 75eff249..0d9c7c2f 100644 --- a/position/tests/__TEST_position_native_mint_swap_burn_test.gnoA +++ b/position/tests/__TEST_position_native_mint_swap_burn_test.gnoA @@ -47,6 +47,8 @@ func testMintPosition(t *testing.T) { std.TestIssueCoins(admin, std.Coins{{"ugnot", 50000005}}) uassert.Equal(t, ugnotBalanceOf(admin), uint64(50000005)) + + std.TestIssueCoins(consts.POSITION_ADDR, std.Coins{{"ugnot", 200000000}}) uassert.Equal(t, ugnotBalanceOf(consts.POSITION_ADDR), uint64(200000000)) banker := std.GetBanker(std.BankerTypeRealmIssue) @@ -78,7 +80,7 @@ func testMintPosition(t *testing.T) { uassert.Equal(t, amount0, "49984837") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") @@ -133,7 +135,7 @@ func testSwap(t *testing.T) { uassert.Equal(t, amount0, "1234567") uassert.Equal(t, amount1, "-1224110") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") diff --git a/position/tests/__TEST_position_reposition_gnot_pair_test.gnoA b/position/tests/__TEST_position_reposition_gnot_pair_test.gnoA index 0b72ad8d..a0dc361e 100644 --- a/position/tests/__TEST_position_reposition_gnot_pair_test.gnoA +++ b/position/tests/__TEST_position_reposition_gnot_pair_test.gnoA @@ -47,6 +47,8 @@ func testMintPosition01InRange(t *testing.T) { std.TestIssueCoins(admin, std.Coins{{"ugnot", 50000005}}) uassert.Equal(t, ugnotBalanceOf(admin), uint64(50000005)) + + std.TestIssueCoins(consts.POSITION_ADDR, std.Coins{{"ugnot", 200000000}}) uassert.Equal(t, ugnotBalanceOf(consts.POSITION_ADDR), uint64(200000000)) banker := std.GetBanker(std.BankerTypeRealmIssue) @@ -78,7 +80,7 @@ func testMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") @@ -118,7 +120,7 @@ func testSwap(t *testing.T) { uassert.Equal(t, amount0, "-452903") uassert.Equal(t, amount1, "1234567") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") @@ -147,7 +149,7 @@ func testCollectFee01(t *testing.T) { std.TestSetRealm(adminRealm) tokenId, tokensOwed0, tokensOwed1, poolPath, fee0, fee1 := CollectFee(1, false) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") }) @@ -175,7 +177,7 @@ func testDecreaseLiquidityInPosition(t *testing.T) { ownerOfPosition = gnft.OwnerOf(tid(lpTokenId)) uassert.Equal(t, ownerOfPosition, admin) - position := positions[lpTokenId] + position := MustGetPosition(lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") @@ -201,7 +203,7 @@ func testReposition(t *testing.T) { lpTokenId := uint64(1) // check current state - position := positions[lpTokenId] + position := MustGetPosition(lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") @@ -237,7 +239,7 @@ func testReposition(t *testing.T) { // user ugnot uassert.Equal(t, ugnotBalanceOf(admin), uint64(81600118)) - position = positions[lpTokenId] + position = MustGetPosition(lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/demo/wugnot:gno.land/r/gnoswap/v1/gns:500") diff --git a/position/tests/__TEST_position_reposition_grc20_pair_test.gnoA b/position/tests/__TEST_position_reposition_grc20_pair_test.gnoA index 94482779..44eb7723 100644 --- a/position/tests/__TEST_position_reposition_grc20_pair_test.gnoA +++ b/position/tests/__TEST_position_reposition_grc20_pair_test.gnoA @@ -48,7 +48,7 @@ func TestMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -81,7 +81,7 @@ func TestSwap1(t *testing.T) { uassert.Equal(t, amount0, "1234567") uassert.Equal(t, amount1, "-3332779") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -120,7 +120,7 @@ func TestMintPosition02InRange(t *testing.T) { uassert.Equal(t, amount0, "21030652") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -169,7 +169,7 @@ func TestDecreaseLiquidityInPosition(t *testing.T) { ownerOfPosition = gnft.OwnerOf(tid(_lpTokenId)) uassert.Equal(t, ownerOfPosition, admin) - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -208,7 +208,7 @@ func TestMintPosition03InRange(t *testing.T) { uassert.Equal(t, amount0, "21030652") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -226,7 +226,7 @@ func TestRepositionNotOwner(t *testing.T) { std.TestSetRealm(std.NewUserRealm(test1)) uassert.PanicsWithMessage( t, - `[GNOSWAP-POSITION-001] caller has no permission || position.gno__Reposition() || only owner(g17290cwvmrapvp869xfnhhawa8sm9edpufzat7d) can reposition for tokenId(1), but called from g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5`, + `[GNOSWAP-POSITION-001] caller has no permission || only owner(g17290cwvmrapvp869xfnhhawa8sm9edpufzat7d) can reposition for tokenId(1), but called from g1jg8mtutu9khhfwc4nxmuhcpftf0pajdhfvsqf5`, func() { Reposition(uint64(1), -1000, 1000, "500", "500", "0", "0") }) @@ -236,7 +236,7 @@ func TestRepositionOwnerButNowBurned(t *testing.T) { std.TestSetRealm(adminRealm) uassert.PanicsWithMessage( t, - `[GNOSWAP-POSITION-009] position is not clear || position.gno__Reposition() || position(2) isn't clear(liquidity:341464938, tokensOwed0:0, tokensOwed1:0)`, + `[GNOSWAP-POSITION-009] position is not clear || position(2) isn't clear(liquidity:341464938, tokensOwed0:0, tokensOwed1:0)`, func() { Reposition(uint64(2), -1000, 1000, "500", "500", "0", "0") }) @@ -246,7 +246,7 @@ func TestRepositionSlippageTooLarge(t *testing.T) { std.TestSetRealm(adminRealm) uassert.PanicsWithMessage( t, - `[GNOSWAP-POSITION-002] slippage failed || liquidity_management.gno__addLiquidity() || LM_Price Slippage Check(amount0(0) >= params.amount0Min(100000000000), amount1(500) >= params.amount1Min(100000000000))`, + `[GNOSWAP-POSITION-002] slippage failed || LM_Price Slippage Check(amount0(0) >= params.amount0Min(100000000000), amount1(500) >= params.amount1Min(100000000000))`, func() { Reposition(uint64(1), -1000, 1000, "500", "500", "100000000000", "100000000000") }) @@ -258,7 +258,7 @@ func TestReposition(t *testing.T) { _lpTokenId := uint64(1) // check current state - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -281,7 +281,7 @@ func TestReposition(t *testing.T) { "100", // amount1Min ) - position = positions[_lpTokenId] + position = MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") diff --git a/position/tests/__TEST_position_reposition_grc20_pair_with_swap_test.gnoA b/position/tests/__TEST_position_reposition_grc20_pair_with_swap_test.gnoA index 8a366488..eb14c5f7 100644 --- a/position/tests/__TEST_position_reposition_grc20_pair_with_swap_test.gnoA +++ b/position/tests/__TEST_position_reposition_grc20_pair_with_swap_test.gnoA @@ -48,7 +48,7 @@ func TestMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -87,7 +87,7 @@ func TestMintPosition02InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -126,7 +126,7 @@ func TestMintPosition03InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -159,7 +159,7 @@ func TestSwap1(t *testing.T) { uassert.Equal(t, amount0, "1234567") uassert.Equal(t, amount1, "-3345595") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -218,7 +218,7 @@ func TestDecreaseLiquidity03(t *testing.T) { ownerOfPosition = gnft.OwnerOf(tid(_lpTokenId)) uassert.Equal(t, ownerOfPosition, admin) - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -238,7 +238,7 @@ func TestReposition(t *testing.T) { _lpTokenId := uint64(3) // check current state - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -261,7 +261,7 @@ func TestReposition(t *testing.T) { "0", // amount1Min ) - position = positions[_lpTokenId] + position = MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -304,7 +304,7 @@ func TestSwap2(t *testing.T) { uassert.Equal(t, amount0, "1234567") uassert.Equal(t, amount1, "-3330062") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -345,7 +345,7 @@ func TestUnclaimedFee03_AfterSwap2(t *testing.T) { foo.Approve(a2u(consts.POOL_ADDR), consts.UINT64_MAX) tokenId, afterFee0, afterFee1, poolPath, fee0, fee1 := CollectFee(3, true) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") uassert.Equal(t, fee0, "204") diff --git a/position/tests/__TEST_position_same_user_same_pool_diff_range_diff_position_swap_fee_test.gnoA b/position/tests/__TEST_position_same_user_same_pool_diff_range_diff_position_swap_fee_test.gnoA index 42311950..ba58c6ee 100644 --- a/position/tests/__TEST_position_same_user_same_pool_diff_range_diff_position_swap_fee_test.gnoA +++ b/position/tests/__TEST_position_same_user_same_pool_diff_range_diff_position_swap_fee_test.gnoA @@ -47,7 +47,7 @@ func TestMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -86,7 +86,7 @@ func TestMintPosition02InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -132,7 +132,7 @@ func TestUnclaimedFee01(t *testing.T) { foo.Approve(a2u(consts.POOL_ADDR), consts.UINT64_MAX) tokenId, tokensOwed0, tokensOwed1, poolPath, fee0, fee1 := CollectFee(1, true) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") } @@ -150,7 +150,7 @@ func TestUnclaimedFee02(t *testing.T) { foo.Approve(a2u(consts.POOL_ADDR), consts.UINT64_MAX) tokenId, tokensOwed0, tokensOwed1, poolPath, fee0, fee1 := CollectFee(2, true) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") } diff --git a/position/tests/__TEST_position_same_user_same_pool_same_range_diff_position_swap_fee_test.gnoA b/position/tests/__TEST_position_same_user_same_pool_same_range_diff_position_swap_fee_test.gnoA index 1b2754ea..27b864fc 100644 --- a/position/tests/__TEST_position_same_user_same_pool_same_range_diff_position_swap_fee_test.gnoA +++ b/position/tests/__TEST_position_same_user_same_pool_same_range_diff_position_swap_fee_test.gnoA @@ -47,7 +47,7 @@ func TestMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -86,7 +86,7 @@ func TestMintPosition02InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -132,7 +132,7 @@ func TestUnclaimedFee01(t *testing.T) { foo.Approve(a2u(consts.POOL_ADDR), consts.UINT64_MAX) tokenId, afterFee0, afterFee1, poolPath, fee0, fee1 := CollectFee(1, false) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") uassert.Equal(t, fee0, "308") @@ -152,7 +152,7 @@ func TestUnclaimedFee02(t *testing.T) { foo.Approve(a2u(consts.POOL_ADDR), consts.UINT64_MAX) tokenId, afterFee0, afterFee1, poolPath, fee0, fee1 := CollectFee(2, false) - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.tokensOwed0.ToString(), "0") uassert.Equal(t, position.tokensOwed1.ToString(), "0") uassert.Equal(t, fee0, "308") diff --git a/position/tests/__TEST_position_tokens_owed_left_grc20_pair_more_action_test.gnoA b/position/tests/__TEST_position_tokens_owed_left_grc20_pair_more_action_test.gnoA index 7acd3395..e0edf917 100644 --- a/position/tests/__TEST_position_tokens_owed_left_grc20_pair_more_action_test.gnoA +++ b/position/tests/__TEST_position_tokens_owed_left_grc20_pair_more_action_test.gnoA @@ -50,7 +50,7 @@ func TestMintPosition01InRange(t *testing.T) { uassert.Equal(t, amount0, "18394892") uassert.Equal(t, amount1, "50000000") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -85,7 +85,7 @@ func TestSwap1(t *testing.T) { uassert.Equal(t, amount1, "-3332779") // pool.swap really doesn't update the position - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -130,7 +130,7 @@ func TestMintPosition02InRange(t *testing.T) { uassert.Equal(t, amount0, "2767688") uassert.Equal(t, amount1, "50000000") - position := positions[uint64(2)] + position := MustGetPosition(uint64(2)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -164,7 +164,7 @@ func TestSwap2(t *testing.T) { uassert.Equal(t, amount1, "-3305175") // pool.swap really doesn't update the position - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -199,7 +199,7 @@ func TestSwap3(t *testing.T) { // pool.swap really doesn't update the position { - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -214,7 +214,7 @@ func TestSwap3(t *testing.T) { } { - position := positions[uint64(2)] + position := MustGetPosition(uint64(2)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") @@ -290,7 +290,7 @@ func TestDecreaseLiquidityPosition02(t *testing.T) { uassert.Equal(t, unclaimedFee0.ToString(), "0") uassert.Equal(t, unclaimedFee1.ToString(), "0") - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:500") diff --git a/position/tests/__TEST_position_tokens_owed_left_pair_more_action_exact_test.gnoA b/position/tests/__TEST_position_tokens_owed_left_pair_more_action_exact_test.gnoA index 292dd355..ad3f7d39 100644 --- a/position/tests/__TEST_position_tokens_owed_left_pair_more_action_exact_test.gnoA +++ b/position/tests/__TEST_position_tokens_owed_left_pair_more_action_exact_test.gnoA @@ -52,7 +52,7 @@ func TestMintPosition01(t *testing.T) { uassert.Equal(t, amount0, "20000000") uassert.Equal(t, amount1, "20000000") - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -89,7 +89,7 @@ func TestSwap1(t *testing.T) { std.TestSkipHeights(10) // swap really doesn't update the position - position := positions[uint64(1)] + position := MustGetPosition(uint64(1)) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -129,7 +129,7 @@ func TestMintPosition02(t *testing.T) { uassert.Equal(t, amount0, "8455058") uassert.Equal(t, amount1, "4991781") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -169,7 +169,7 @@ func TestMintPosition03(t *testing.T) { uassert.Equal(t, amount0, "40000000") uassert.Equal(t, amount1, "23615594") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -232,7 +232,7 @@ func TestMintPosition04(t *testing.T) { uassert.Equal(t, amount0, "5098207") uassert.Equal(t, amount1, "2881761") - position := positions[tokenId] + position := MustGetPosition(tokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -329,7 +329,7 @@ func TestDecreaseLiquidityPosition02(t *testing.T) { uassert.Equal(t, unclaimedFee0.ToString(), "0") uassert.Equal(t, unclaimedFee1.ToString(), "0") - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") @@ -376,7 +376,7 @@ func TestDecreaseLiquidityPosition02All(t *testing.T) { uassert.Equal(t, unclaimedFee0.ToString(), "0") uassert.Equal(t, unclaimedFee1.ToString(), "0") - position := positions[_lpTokenId] + position := MustGetPosition(_lpTokenId) uassert.Equal(t, position.nonce.ToString(), "0") uassert.Equal(t, position.operator, consts.ZERO_ADDRESS) uassert.Equal(t, position.poolKey, "gno.land/r/onbloc/bar:gno.land/r/onbloc/foo:3000") diff --git a/position/utils_test.gno b/position/utils_test.gno index 26051a27..1a2c80e4 100644 --- a/position/utils_test.gno +++ b/position/utils_test.gno @@ -288,7 +288,7 @@ func TestAssertOnlyValidAddress(t *testing.T) { name: "Failure - invalid address", addr: "g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8", // invalid length expected: false, - errorMsg: "[GNOSWAP-POSITION-011] invalid address || (g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8)", + errorMsg: "[GNOSWAP-POSITION-012] invalid address || (g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8)", }, } for _, tc := range tests { @@ -325,7 +325,7 @@ func TestAssertOnlyValidAddressWith(t *testing.T) { addr: "g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8", other: "g17290cwvmrapvp869xfnhhawa8sm9edpufzat7d", expected: false, - errorMsg: "[GNOSWAP-POSITION-011] invalid address || (g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8)", + errorMsg: "[GNOSWAP-POSITION-012] invalid address || (g1lmvrrrr4er2us84h2732sru76c9zl2nvknha8)", }, } for _, tc := range tests { diff --git a/position/wrap_unwrap.gno b/position/wrap_unwrap.gno index e1c97f9d..f0fe5395 100644 --- a/position/wrap_unwrap.gno +++ b/position/wrap_unwrap.gno @@ -17,7 +17,7 @@ func wrap(ugnotAmount uint64, to std.Address) { if ugnotAmount < consts.UGNOT_MIN_DEPOSIT_TO_WRAP { panic(addDetailToError( errWugnotMinimum, - ufmt.Sprintf("wrap.gno__wrap() || amount(%d) < minimum(%d)", ugnotAmount, consts.UGNOT_MIN_DEPOSIT_TO_WRAP), + ufmt.Sprintf("amount(%d) < minimum(%d)", ugnotAmount, consts.UGNOT_MIN_DEPOSIT_TO_WRAP), )) }