diff --git a/x/mint/abci.go b/x/mint/abci.go index 59845fe0..1c33e81d 100644 --- a/x/mint/abci.go +++ b/x/mint/abci.go @@ -1,65 +1,12 @@ package mint import ( - "time" - - "github.com/cosmos/cosmos-sdk/telemetry" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/okp4/okp4d/x/mint/keeper" - "github.com/okp4/okp4d/x/mint/types" ) // BeginBlocker mints new tokens for the previous block. func BeginBlocker(ctx sdk.Context, k keeper.Keeper) { - defer telemetry.ModuleMeasureSince(types.ModuleName, time.Now(), telemetry.MetricKeyBeginBlocker) - - // fetch stored minter & params - minter := k.GetMinter(ctx) - params := k.GetParams(ctx) - - totalSupply := k.TokenSupply(ctx, params.MintDenom) - - if uint64(ctx.BlockHeight()) == 1 { - minter.AnnualProvisions = minter.NextAnnualProvisions(params, totalSupply) - minter.TargetSupply = totalSupply.Add(minter.AnnualProvisions.TruncateInt()) - k.SetMinter(ctx, minter) - } - - // If we have reached the end of the year by reaching the targeted supply for the year - // We need to re-calculate the next inflation for the next year. - if totalSupply.GTE(minter.TargetSupply) { - minter.Inflation = minter.NextInflation(params) - minter.AnnualProvisions = minter.NextAnnualProvisions(params, totalSupply) - minter.TargetSupply = totalSupply.Add(minter.AnnualProvisions.TruncateInt()) - k.SetMinter(ctx, minter) - } - - // mint coins, update supply - mintedCoin := minter.BlockProvision(params, totalSupply) - mintedCoins := sdk.NewCoins(mintedCoin) - - err := k.MintCoins(ctx, mintedCoins) - if err != nil { - panic(err) - } - - // send the minted coins to the fee collector account - err = k.AddCollectedFees(ctx, mintedCoins) - if err != nil { - panic(err) - } - - if mintedCoin.Amount.IsInt64() { - defer telemetry.ModuleSetGauge(types.ModuleName, float32(mintedCoin.Amount.Int64()), "minted_tokens") - } - ctx.EventManager().EmitEvent( - sdk.NewEvent( - types.EventTypeMint, - sdk.NewAttribute(types.AttributeKeyInflation, minter.Inflation.String()), - sdk.NewAttribute(types.AttributeKeyAnnualProvisions, minter.AnnualProvisions.String()), - sdk.NewAttribute(sdk.AttributeKeyAmount, mintedCoin.Amount.String()), - ), - ) } diff --git a/x/mint/module.go b/x/mint/module.go index e7a66002..2cd8e541 100644 --- a/x/mint/module.go +++ b/x/mint/module.go @@ -121,7 +121,7 @@ func (am AppModule) RegisterServices(cfg module.Configurator) { fromVersion uint64 migrator func(ctx sdk.Context) error }{ - {1, migrator.Migrate1to2}, + {2, migrator.Migrate2to3}, } for _, migration := range migrations { @@ -150,7 +150,7 @@ func (am AppModule) ExportGenesis(ctx sdk.Context, cdc codec.JSONCodec) json.Raw } // ConsensusVersion implements AppModule/ConsensusVersion. -func (AppModule) ConsensusVersion() uint64 { return 2 } +func (AppModule) ConsensusVersion() uint64 { return 3 } // BeginBlock returns the begin blocker for the mint module. func (am AppModule) BeginBlock(ctx sdk.Context, _ abci.RequestBeginBlock) { diff --git a/x/mint/simulation/genesis.go b/x/mint/simulation/genesis.go index 4c389910..d5512047 100644 --- a/x/mint/simulation/genesis.go +++ b/x/mint/simulation/genesis.go @@ -15,8 +15,10 @@ import ( // Simulation parameter constants. const ( - Inflation = "inflation" - AnnualReductionFactor = "annual_reduction_factor" + Inflation = "inflation" + InflationCoef = "inflation_coef" + BoundingAdjustment = "bounding_adjustment" + TargetBoundingRatio = "target_bounding_ratio" ) // GenInflation randomized Inflation. @@ -24,9 +26,19 @@ func GenInflation(r *rand.Rand) sdk.Dec { return sdk.NewDecWithPrec(int64(r.Intn(99)), 2) } -// GenAnnualReductionFactor randomized AnnualReductionFactor. -func GenAnnualReductionFactorMax(_ *rand.Rand) sdk.Dec { - return sdk.NewDecWithPrec(20, 2) +// GenInflationCoefMax randomized AnnualReductionFactor. +func GenInflationCoefMax(_ *rand.Rand) sdk.Dec { + return sdk.NewDecWithPrec(73, 3) +} + +// GenBoundingAdjustmentMax randomized AnnualReductionFactor. +func GenBoundingAdjustmentMax(_ *rand.Rand) sdk.Dec { + return sdk.NewDecWithPrec(25, 1) +} + +// GenTargetBoundingRatioMax randomized AnnualReductionFactor. +func GenTargetBoundingRatioMax(_ *rand.Rand) sdk.Dec { + return sdk.NewDecWithPrec(66, 2) } // RandomizedGenState generates a random GenesisState for mint. @@ -42,19 +54,29 @@ func RandomizedGenState(simState *module.SimulationState) { // params - var annualReductionFactor sdk.Dec + var inflationCoef sdk.Dec + simState.AppParams.GetOrGenerate( + simState.Cdc, InflationCoef, &inflationCoef, simState.Rand, + func(r *rand.Rand) { inflationCoef = GenInflationCoefMax(r) }, + ) + var targetBoundingRatio sdk.Dec + simState.AppParams.GetOrGenerate( + simState.Cdc, TargetBoundingRatio, &targetBoundingRatio, simState.Rand, + func(r *rand.Rand) { targetBoundingRatio = GenTargetBoundingRatioMax(r) }, + ) + + var boundingAdjustment sdk.Dec simState.AppParams.GetOrGenerate( - simState.Cdc, AnnualReductionFactor, &annualReductionFactor, simState.Rand, - func(r *rand.Rand) { annualReductionFactor = GenAnnualReductionFactorMax(r) }, + simState.Cdc, BoundingAdjustment, &boundingAdjustment, simState.Rand, + func(r *rand.Rand) { boundingAdjustment = GenBoundingAdjustmentMax(r) }, ) mintDenom := sdk.DefaultBondDenom blocksPerYear := uint64(60 * 60 * 8766 / 5) - params := types.NewParams(mintDenom, annualReductionFactor, blocksPerYear) + params := types.NewParams(mintDenom, inflationCoef, boundingAdjustment, targetBoundingRatio, blocksPerYear) annualProvision := inflation.MulInt(simState.InitialStake) - targetSupply := simState.InitialStake.Add(annualProvision.TruncateInt()) - minter := types.InitialMinter(inflation, targetSupply) + minter := types.InitialMinter(inflation) minter.AnnualProvisions = annualProvision mintGenesis := types.NewGenesisState(minter, params) diff --git a/x/mint/simulation/proposals.go b/x/mint/simulation/proposals.go index b34d982e..93c9a216 100644 --- a/x/mint/simulation/proposals.go +++ b/x/mint/simulation/proposals.go @@ -36,7 +36,9 @@ func SimulateMsgUpdateParams(r *rand.Rand, _ sdk.Context, _ []simtypes.Account) params := types.DefaultParams() params.BlocksPerYear = uint64(simtypes.RandIntBetween(r, 1, 1000000)) - params.AnnualReductionFactor = sdk.NewDecWithPrec(int64(simtypes.RandIntBetween(r, 1, 100)), 2) + params.InflationCoef = sdk.NewDecWithPrec(int64(simtypes.RandIntBetween(r, 1, 100)), 2) + params.TargetBoundingRatio = sdk.NewDecWithPrec(int64(simtypes.RandIntBetween(r, 1, 100)), 2) + params.BoundingAdjustment = sdk.NewDecWithPrec(int64(simtypes.RandIntBetween(r, 1, 100)), 2) params.MintDenom = simtypes.RandStringOfLength(r, 10) return &types.MsgUpdateParams{ diff --git a/x/mint/types/minter.go b/x/mint/types/minter.go index 8f64015b..6daf9253 100644 --- a/x/mint/types/minter.go +++ b/x/mint/types/minter.go @@ -10,29 +10,26 @@ import ( // NewMinter returns a new Minter object with the given inflation, annual // provisions values and annual reduction factor. -func NewMinter(inflation, annualProvisions sdk.Dec, targetSupply math.Int) Minter { +func NewMinter(inflation, annualProvisions sdk.Dec) Minter { return Minter{ Inflation: inflation, AnnualProvisions: annualProvisions, - TargetSupply: targetSupply, } } // InitialMinter returns an initial Minter object with a given inflation value and annual reduction factor. -func InitialMinter(inflation sdk.Dec, targetSupply math.Int) Minter { +func InitialMinter(inflation sdk.Dec) Minter { return NewMinter( inflation, sdk.NewDec(0), - targetSupply, ) } // DefaultInitialMinter returns a default initial Minter object for a new chain -// which uses an inflation rate of 15%. +// which uses an inflation rate of 18%. func DefaultInitialMinter() Minter { return InitialMinter( - sdk.NewDecWithPrec(15, 2), - math.NewInt(230000000000000), + sdk.NewDecWithPrec(18, 2), ) } @@ -48,27 +45,18 @@ func ValidateMinter(minter Minter) error { // NextInflation return the new inflation rate for the next year // Get the current inflation and multiply by (1 - annual reduction factor). func (m Minter) NextInflation(params Params) sdk.Dec { - return m.Inflation.Mul(sdk.OneDec().Sub(params.AnnualReductionFactor)) + return m.Inflation } // NextAnnualProvisions returns the annual provisions based on current total // supply and inflation rate. -func (m Minter) NextAnnualProvisions(_ Params, totalSupply math.Int) sdk.Dec { +func (m Minter) NextAnnualProvisions(_ Params, totalSupply math.Int) math.LegacyDec { return m.Inflation.MulInt(totalSupply) } // BlockProvision returns the provisions for a block based on the annual // provisions rate. -func (m Minter) BlockProvision(params Params, totalSupply math.Int) sdk.Coin { +func (m Minter) BlockProvision(params Params) sdk.Coin { provisionAmt := m.AnnualProvisions.QuoInt(sdk.NewInt(int64(params.BlocksPerYear))) - - // Fixe rounding by limiting to the target supply at the end of the year block. - futureSupply := totalSupply.Add(provisionAmt.TruncateInt()) - if futureSupply.GT(m.TargetSupply) { - // In case of a rounding is not precise enough, truncating int of provisionAmt could return Zero - // To avoid negative coin if provisionAmt is equal to Zero, return minimum Zero or more coin. - return sdk.NewCoin(params.MintDenom, sdk.MaxInt(m.TargetSupply.Sub(totalSupply), sdk.ZeroInt())) - } - return sdk.NewCoin(params.MintDenom, provisionAmt.TruncateInt()) } diff --git a/x/mint/types/params.go b/x/mint/types/params.go index 85b9a5ee..7c95c6e1 100644 --- a/x/mint/types/params.go +++ b/x/mint/types/params.go @@ -10,29 +10,26 @@ import ( sdk "github.com/cosmos/cosmos-sdk/types" ) -// Parameter store keys. -var ( - KeyMintDenom = []byte("MintDenom") - KeyAnnualReductionFactor = []byte("AnnualReductionFactor") - KeyBlocksPerYear = []byte("BlocksPerYear") -) - func NewParams( - mintDenom string, annualReductionFactor sdk.Dec, blocksPerYear uint64, + mintDenom string, inflationCoef, boundingAdjustment, targetBoundingRatio sdk.Dec, blocksPerYear uint64, ) Params { return Params{ - MintDenom: mintDenom, - AnnualReductionFactor: annualReductionFactor, - BlocksPerYear: blocksPerYear, + MintDenom: mintDenom, + InflationCoef: inflationCoef, + BoundingAdjustment: boundingAdjustment, + TargetBoundingRatio: targetBoundingRatio, + BlocksPerYear: blocksPerYear, } } // default minting module parameters. func DefaultParams() Params { return Params{ - MintDenom: sdk.DefaultBondDenom, - AnnualReductionFactor: sdk.NewDecWithPrec(20, 2), // Tha annual reduction factor is configured to 20% per year - BlocksPerYear: uint64(60 * 60 * 8766 / 5), // assuming 5-second block times + MintDenom: sdk.DefaultBondDenom, + InflationCoef: sdk.NewDecWithPrec(73, 3), + BoundingAdjustment: sdk.NewDecWithPrec(25, 1), + TargetBoundingRatio: sdk.NewDecWithPrec(66, 2), + BlocksPerYear: uint64(60 * 60 * 8766 / 5), // assuming 5-second block times } } @@ -41,7 +38,13 @@ func (p Params) Validate() error { if err := validateMintDenom(p.MintDenom); err != nil { return err } - if err := validateAnnualReductionFactor(p.AnnualReductionFactor); err != nil { + if err := validateInflationCoef(p.InflationCoef); err != nil { + return err + } + if err := validateBoundingAdjustment(p.BoundingAdjustment); err != nil { + return err + } + if err := validateTargetBoundingRatio(p.TargetBoundingRatio); err != nil { return err } @@ -67,17 +70,46 @@ func validateMintDenom(i interface{}) error { return sdk.ValidateDenom(v) } -func validateAnnualReductionFactor(i interface{}) error { +func validateInflationCoef(i interface{}) error { + v, ok := i.(sdk.Dec) + if !ok { + return fmt.Errorf("invalid parameter type: %T", i) + } + + if v.IsNegative() { + return fmt.Errorf("inflation coefficient cannot be negative: %s", v) + } + if v.GT(sdk.OneDec()) { + return fmt.Errorf("inflation coefficient too large: %s", v) + } + + return nil +} + +func validateBoundingAdjustment(i interface{}) error { + v, ok := i.(sdk.Dec) + if !ok { + return fmt.Errorf("invalid parameter type: %T", i) + } + + if v.IsNegative() { + return fmt.Errorf("inflation coefficient cannot be negative: %s", v) + } + + return nil +} + +func validateTargetBoundingRatio(i interface{}) error { v, ok := i.(sdk.Dec) if !ok { return fmt.Errorf("invalid parameter type: %T", i) } if v.IsNegative() { - return fmt.Errorf("annual reduction factor cannot be negative: %s", v) + return fmt.Errorf("target bounding ratio cannot be negative: %s", v) } if v.GT(sdk.OneDec()) { - return fmt.Errorf("annual reduction factor too large: %s", v) + return fmt.Errorf("target bounding ratio too large: %s", v) } return nil