github.com/fibonacci-chain/fbc@v0.0.0-20231124064014-c7636198c1e9/x/farm/abci.go (about) 1 package farm 2 3 import ( 4 "fmt" 5 6 sdk "github.com/fibonacci-chain/fbc/libs/cosmos-sdk/types" 7 abci "github.com/fibonacci-chain/fbc/libs/tendermint/abci/types" 8 "github.com/fibonacci-chain/fbc/x/farm/keeper" 9 "github.com/fibonacci-chain/fbc/x/farm/types" 10 ) 11 12 // BeginBlocker allocates the native token to the pools in PoolsYieldNativeToken 13 // according to the value of locked token in pool 14 func BeginBlocker(ctx sdk.Context, req abci.RequestBeginBlock, k keeper.Keeper) { 15 logger := k.Logger(ctx) 16 17 moduleAcc := k.SupplyKeeper().GetModuleAccount(ctx, MintFarmingAccount) 18 yieldedNativeTokenAmt := moduleAcc.GetCoins().AmountOf(sdk.DefaultBondDenom) 19 logger.Debug(fmt.Sprintf("MintFarmingAccount [%s] balance: %s%s", 20 moduleAcc.GetAddress(), yieldedNativeTokenAmt, sdk.DefaultBondDenom)) 21 22 if yieldedNativeTokenAmt.LTE(sdk.ZeroDec()) { 23 return 24 } 25 26 yieldedNativeToken := sdk.NewDecCoinsFromDec(sdk.DefaultBondDenom, yieldedNativeTokenAmt) 27 // 0. check the YieldNativeToken parameters 28 params := k.GetParams(ctx) 29 if !params.YieldNativeToken { // if it is false, only burn the minted native token 30 if err := k.SupplyKeeper().BurnCoins(ctx, MintFarmingAccount, yieldedNativeToken); err != nil { 31 panic(err) 32 } 33 return 34 } 35 36 // 1. gets all pools in PoolsYieldNativeToken 37 lockedPoolValueMap, pools, totalPoolsValue := calculateAllocateInfo(ctx, k) 38 if totalPoolsValue.LTE(sdk.ZeroDec()) { 39 return 40 } 41 42 // 2. allocate native token to pools according to the value 43 remainingNativeTokenAmt := yieldedNativeTokenAmt 44 for i, pool := range pools { 45 var allocatedAmt sdk.Dec 46 if i == len(pools)-1 { 47 allocatedAmt = remainingNativeTokenAmt 48 } else { 49 allocatedAmt = lockedPoolValueMap[pool.Name]. 50 MulTruncate(yieldedNativeTokenAmt).QuoTruncate(totalPoolsValue) 51 } 52 remainingNativeTokenAmt = remainingNativeTokenAmt.Sub(allocatedAmt) 53 logger.Debug( 54 fmt.Sprintf("Pool %s allocate %s yielded native token", pool.Name, allocatedAmt.String()), 55 ) 56 allocatedCoins := sdk.NewDecCoinsFromDec(sdk.DefaultBondDenom, allocatedAmt) 57 58 current := k.GetPoolCurrentRewards(ctx, pool.Name) 59 current.Rewards = current.Rewards.Add2(allocatedCoins) 60 k.SetPoolCurrentRewards(ctx, pool.Name, current) 61 logger.Debug(fmt.Sprintf("Pool %s rewards are %s", pool.Name, current.Rewards)) 62 63 pool.TotalAccumulatedRewards = pool.TotalAccumulatedRewards.Add2(allocatedCoins) 64 k.SetFarmPool(ctx, pool) 65 } 66 if !remainingNativeTokenAmt.IsZero() { 67 panic(fmt.Sprintf("there are some tokens %s not to be allocated", remainingNativeTokenAmt)) 68 } 69 70 // 3.liquidate native token minted at current block for yield farming 71 err := k.SupplyKeeper().SendCoinsFromModuleToModule(ctx, MintFarmingAccount, YieldFarmingAccount, yieldedNativeToken) 72 if err != nil { 73 panic("should not happen") 74 } 75 } 76 77 // EndBlocker called every block, process inflation, update validator set. 78 func EndBlocker(ctx sdk.Context, k keeper.Keeper) { 79 80 } 81 82 // calculateAllocateInfo gets all pools in PoolsYieldNativeToken 83 func calculateAllocateInfo(ctx sdk.Context, k keeper.Keeper) (map[string]sdk.Dec, []types.FarmPool, sdk.Dec) { 84 lockedPoolValue := make(map[string]sdk.Dec) 85 var pools types.FarmPools 86 totalPoolsValue := sdk.ZeroDec() 87 88 store := ctx.KVStore(k.StoreKey()) 89 iterator := sdk.KVStorePrefixIterator(store, types.PoolsYieldNativeTokenPrefix) 90 defer iterator.Close() 91 for ; iterator.Valid(); iterator.Next() { 92 poolName := types.SplitPoolsYieldNativeTokenKey(iterator.Key()) 93 pool, found := k.GetFarmPool(ctx, poolName) 94 if !found { 95 panic("should not happen") 96 } 97 poolValue := k.GetPoolLockedValue(ctx, pool) 98 if poolValue.LTE(sdk.ZeroDec()) { 99 continue 100 } 101 pools = append(pools, pool) 102 lockedPoolValue[poolName] = poolValue 103 totalPoolsValue = totalPoolsValue.Add(poolValue) 104 } 105 return lockedPoolValue, pools, totalPoolsValue 106 }