-
Notifications
You must be signed in to change notification settings - Fork 4.2k
refactor(x/mint): remove staking as a required module #21858
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from 6 commits
27494e8
e9d7c1d
dd4603f
0d771e4
3954247
a16eea6
bad6264
321ea18
246e4e1
870debd
b55219b
ab8fc1d
f21026b
dbde391
3154eb4
3d0fe07
ace9fd4
da93369
c74d409
1b006bf
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||||||||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -18,6 +18,10 @@ func (keeper Keeper) InitGenesis(ctx context.Context, ak types.AccountKeeper, da | |||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| ak.GetModuleAccount(ctx, types.ModuleName) | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| if keeper.mintFn == nil { | ||||||||||||||||||||||||||||||||||||||||||
| panic("mintFn cannot be nil") | ||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Approve the nil check for The addition of a nil check for However, consider moving this check to the beginning of the function. This would prevent unnecessary operations if func (keeper Keeper) InitGenesis(ctx context.Context, ak types.AccountKeeper, data *types.GenesisState) error {
+ if keeper.mintFn == nil {
+ panic("mintFn cannot be nil")
+ }
+
if err := keeper.Minter.Set(ctx, data.Minter); err != nil {
return err
}
if err := keeper.Params.Set(ctx, data.Params); err != nil {
return err
}
ak.GetModuleAccount(ctx, types.ModuleName)
- if keeper.mintFn == nil {
- panic("mintFn cannot be nil")
- }
return nil
}This change would improve the function's efficiency and readability. Committable suggestion
Suggested change
|
||||||||||||||||||||||||||||||||||||||||||
| return nil | ||||||||||||||||||||||||||||||||||||||||||
| } | ||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
|
|
||||||||||||||||||||||||||||||||||||||||||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -1,12 +1,14 @@ | ||
| package keeper_test | ||
|
|
||
| import ( | ||
| "context" | ||
| "testing" | ||
|
|
||
| "github.com/golang/mock/gomock" | ||
| "github.com/stretchr/testify/suite" | ||
|
|
||
| "cosmossdk.io/collections" | ||
| "cosmossdk.io/core/appmodule" | ||
| "cosmossdk.io/log" | ||
| "cosmossdk.io/math" | ||
| storetypes "cosmossdk.io/store/types" | ||
|
|
@@ -51,14 +53,17 @@ func (s *GenesisTestSuite) SetupTest() { | |
| s.sdkCtx = testCtx.Ctx | ||
| s.key = key | ||
|
|
||
| stakingKeeper := minttestutil.NewMockStakingKeeper(ctrl) | ||
| accountKeeper := minttestutil.NewMockAccountKeeper(ctrl) | ||
| bankKeeper := minttestutil.NewMockBankKeeper(ctrl) | ||
| s.accountKeeper = accountKeeper | ||
| accountKeeper.EXPECT().GetModuleAddress(minterAcc.Name).Return(minterAcc.GetAddress()) | ||
| accountKeeper.EXPECT().GetModuleAccount(s.sdkCtx, minterAcc.Name).Return(minterAcc) | ||
|
|
||
| s.keeper = keeper.NewKeeper(s.cdc, runtime.NewEnvironment(runtime.NewKVStoreService(key), log.NewNopLogger()), stakingKeeper, accountKeeper, bankKeeper, "", "") | ||
| s.keeper = keeper.NewKeeper(s.cdc, runtime.NewEnvironment(runtime.NewKVStoreService(key), log.NewNopLogger()), accountKeeper, bankKeeper, "", "") | ||
| err := s.keeper.SetMintFn(func(ctx context.Context, env appmodule.Environment, minter *types.Minter, epochId string, epochNumber int64) error { | ||
| return nil | ||
| }) | ||
| s.NoError(err) | ||
|
Comment on lines
+63
to
+66
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Enhance test coverage for While the Suggestions:
Example test case: func (s *GenesisTestSuite) TestSetMintFn() {
called := false
err := s.keeper.SetMintFn(func(ctx context.Context, env appmodule.Environment, minter *types.Minter, epochId string, epochNumber int64) error {
called = true
return nil
})
s.NoError(err)
// Trigger a mint operation
// ...
s.True(called, "SetMintFn was not called during minting operation")
} |
||
| } | ||
|
|
||
| func (s *GenesisTestSuite) TestImportExportGenesis() { | ||
|
|
||
| Original file line number | Diff line number | Diff line change | ||||||||||||||||||
|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|---|
|
|
@@ -2,6 +2,7 @@ package keeper | |||||||||||||||||||
|
|
||||||||||||||||||||
| import ( | ||||||||||||||||||||
| "context" | ||||||||||||||||||||
| "errors" | ||||||||||||||||||||
| "fmt" | ||||||||||||||||||||
|
|
||||||||||||||||||||
| "cosmossdk.io/collections" | ||||||||||||||||||||
|
|
@@ -20,7 +21,6 @@ type Keeper struct { | |||||||||||||||||||
| appmodule.Environment | ||||||||||||||||||||
|
|
||||||||||||||||||||
| cdc codec.BinaryCodec | ||||||||||||||||||||
| stakingKeeper types.StakingKeeper | ||||||||||||||||||||
| bankKeeper types.BankKeeper | ||||||||||||||||||||
| feeCollectorName string | ||||||||||||||||||||
| // the address capable of executing a MsgUpdateParams message. Typically, this | ||||||||||||||||||||
|
|
@@ -30,13 +30,17 @@ type Keeper struct { | |||||||||||||||||||
| Schema collections.Schema | ||||||||||||||||||||
| Params collections.Item[types.Params] | ||||||||||||||||||||
| Minter collections.Item[types.Minter] | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // mintFn is used to mint new coins during BeginBlock. This function is in charge of | ||||||||||||||||||||
| // minting new coins based on arbitrary logic, previously done through InflationCalculationFn. | ||||||||||||||||||||
| // If mintFn is nil, the default minting logic is used. | ||||||||||||||||||||
| mintFn types.MintFn | ||||||||||||||||||||
|
Comment on lines
+34
to
+35
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Clarify the behavior when 'mintFn' is nil to avoid inconsistency The comment states: "If |
||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // NewKeeper creates a new mint Keeper instance | ||||||||||||||||||||
| func NewKeeper( | ||||||||||||||||||||
| cdc codec.BinaryCodec, | ||||||||||||||||||||
| env appmodule.Environment, | ||||||||||||||||||||
| sk types.StakingKeeper, | ||||||||||||||||||||
| ak types.AccountKeeper, | ||||||||||||||||||||
| bk types.BankKeeper, | ||||||||||||||||||||
| feeCollectorName string, | ||||||||||||||||||||
|
|
@@ -51,7 +55,6 @@ func NewKeeper( | |||||||||||||||||||
| k := Keeper{ | ||||||||||||||||||||
| Environment: env, | ||||||||||||||||||||
| cdc: cdc, | ||||||||||||||||||||
| stakingKeeper: sk, | ||||||||||||||||||||
| bankKeeper: bk, | ||||||||||||||||||||
| feeCollectorName: feeCollectorName, | ||||||||||||||||||||
| authority: authority, | ||||||||||||||||||||
|
|
@@ -67,21 +70,20 @@ func NewKeeper( | |||||||||||||||||||
| return k | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // GetAuthority returns the x/mint module's authority. | ||||||||||||||||||||
| func (k Keeper) GetAuthority() string { | ||||||||||||||||||||
| return k.authority | ||||||||||||||||||||
| } | ||||||||||||||||||||
| // SetMintFn sets the mint function. | ||||||||||||||||||||
|
tac0turtle marked this conversation as resolved.
Outdated
|
||||||||||||||||||||
| // This is a required call by the application developer | ||||||||||||||||||||
| func (k *Keeper) SetMintFn(mintFn types.MintFn) error { | ||||||||||||||||||||
| if mintFn == nil { | ||||||||||||||||||||
| return errors.New("mintFn cannot be nil") | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // StakingTokenSupply implements an alias call to the underlying staking keeper's | ||||||||||||||||||||
| // StakingTokenSupply to be used in BeginBlocker. | ||||||||||||||||||||
| func (k Keeper) StakingTokenSupply(ctx context.Context) (math.Int, error) { | ||||||||||||||||||||
| return k.stakingKeeper.StakingTokenSupply(ctx) | ||||||||||||||||||||
| k.mintFn = mintFn | ||||||||||||||||||||
| return nil | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // BondedRatio implements an alias call to the underlying staking keeper's | ||||||||||||||||||||
| // BondedRatio to be used in BeginBlocker. | ||||||||||||||||||||
| func (k Keeper) BondedRatio(ctx context.Context) (math.LegacyDec, error) { | ||||||||||||||||||||
| return k.stakingKeeper.BondedRatio(ctx) | ||||||||||||||||||||
| // GetAuthority returns the x/mint module's authority. | ||||||||||||||||||||
| func (k Keeper) GetAuthority() string { | ||||||||||||||||||||
| return k.authority | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| // MintCoins implements an alias call to the underlying supply keeper's | ||||||||||||||||||||
|
|
@@ -101,20 +103,26 @@ func (k Keeper) AddCollectedFees(ctx context.Context, fees sdk.Coins) error { | |||||||||||||||||||
| return k.bankKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, k.feeCollectorName, fees) | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| func (k Keeper) DefaultMintFn(ic types.InflationCalculationFn) types.MintFn { | ||||||||||||||||||||
| func (k Keeper) MintFn(ctx context.Context, minter *types.Minter, epochId string, epochNumber int64) error { | ||||||||||||||||||||
| return k.mintFn(ctx, k.Environment, minter, epochId, epochNumber) | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Add nil check in 'MintFn' method to prevent potential panics The Apply this diff to add a nil check: func (k Keeper) MintFn(ctx context.Context, minter *types.Minter, epochId string, epochNumber int64) error {
+ if k.mintFn == nil {
+ return errors.New("mintFn is not set; please ensure SetMintFn is called")
+ }
return k.mintFn(ctx, k.Environment, minter, epochId, epochNumber)
}Committable suggestion
Suggested change
|
||||||||||||||||||||
|
|
||||||||||||||||||||
| // DefaultMintFn returns a default mint function. It requires the Staking module and the mint keeper. | ||||||||||||||||||||
| // The default Mintfn has a requirement on staking as it uses bond to calculate inflation. | ||||||||||||||||||||
| func DefaultMintFn(ic types.InflationCalculationFn, staking types.StakingKeeper, k Keeper) types.MintFn { | ||||||||||||||||||||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Initialize 'mintFn' with default logic to improve safety Consider initializing Apply this refactor to set a default func NewKeeper(
cdc codec.BinaryCodec,
env appmodule.Environment,
ak types.AccountKeeper,
bk types.BankKeeper,
feeCollectorName string,
authority string,
+ staking types.StakingKeeper,
) Keeper {
// ensure mint module account is set
if addr := ak.GetModuleAddress(types.ModuleName); addr == nil {
panic(fmt.Sprintf("the x/%s module account has not been set", types.ModuleName))
}
sb := collections.NewSchemaBuilder(env.KVStoreService)
k := Keeper{
Environment: env,
cdc: cdc,
bankKeeper: bk,
feeCollectorName: feeCollectorName,
authority: authority,
Params: collections.NewItem(sb, types.ParamsKey, "params", codec.CollValue[types.Params](cdc)),
Minter: collections.NewItem(sb, types.MinterKey, "minter", codec.CollValue[types.Minter](cdc)),
+ mintFn: DefaultMintFn(DefaultInflationCalculationFn, staking, nil),
}
// [existing code]
return k
}This refactor requires passing
tac0turtle marked this conversation as resolved.
Outdated
|
||||||||||||||||||||
| return func(ctx context.Context, env appmodule.Environment, minter *types.Minter, epochId string, epochNumber int64) error { | ||||||||||||||||||||
| // the default mint function is called every block, so we only check if epochId is "block" which is | ||||||||||||||||||||
| // a special value to indicate that this is not an epoch minting, but a regular block minting. | ||||||||||||||||||||
| if epochId != "block" { | ||||||||||||||||||||
| return nil | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| stakingTokenSupply, err := k.StakingTokenSupply(ctx) | ||||||||||||||||||||
| stakingTokenSupply, err := staking.StakingTokenSupply(ctx) | ||||||||||||||||||||
| if err != nil { | ||||||||||||||||||||
| return err | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| bondedRatio, err := k.BondedRatio(ctx) | ||||||||||||||||||||
| bondedRatio, err := staking.BondedRatio(ctx) | ||||||||||||||||||||
| if err != nil { | ||||||||||||||||||||
| return err | ||||||||||||||||||||
| } | ||||||||||||||||||||
|
|
||||||||||||||||||||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -59,7 +59,6 @@ func (s *KeeperTestSuite) SetupTest() { | |
| s.mintKeeper = keeper.NewKeeper( | ||
| encCfg.Codec, | ||
| env, | ||
| stakingKeeper, | ||
| accountKeeper, | ||
| bankKeeper, | ||
| authtypes.FeeCollectorName, | ||
|
|
@@ -75,40 +74,19 @@ func (s *KeeperTestSuite) SetupTest() { | |
| s.msgServer = keeper.NewMsgServerImpl(s.mintKeeper) | ||
| } | ||
|
|
||
| func (s *KeeperTestSuite) TestAliasFunctions() { | ||
| stakingTokenSupply := math.NewIntFromUint64(100000000000) | ||
| s.stakingKeeper.EXPECT().StakingTokenSupply(s.ctx).Return(stakingTokenSupply, nil) | ||
| tokenSupply, err := s.mintKeeper.StakingTokenSupply(s.ctx) | ||
| s.NoError(err) | ||
| s.Equal(tokenSupply, stakingTokenSupply) | ||
|
|
||
| bondedRatio := math.LegacyNewDecWithPrec(15, 2) | ||
| s.stakingKeeper.EXPECT().BondedRatio(s.ctx).Return(bondedRatio, nil) | ||
| ratio, err := s.mintKeeper.BondedRatio(s.ctx) | ||
| s.NoError(err) | ||
| s.Equal(ratio, bondedRatio) | ||
|
|
||
| coins := sdk.NewCoins(sdk.NewCoin("stake", math.NewInt(1000000))) | ||
| s.bankKeeper.EXPECT().MintCoins(s.ctx, types.ModuleName, coins).Return(nil) | ||
| s.Equal(s.mintKeeper.MintCoins(s.ctx, sdk.NewCoins()), nil) | ||
| s.Nil(s.mintKeeper.MintCoins(s.ctx, coins)) | ||
|
|
||
| fees := sdk.NewCoins(sdk.NewCoin("stake", math.NewInt(1000))) | ||
| s.bankKeeper.EXPECT().SendCoinsFromModuleToModule(s.ctx, types.ModuleName, authtypes.FeeCollectorName, fees).Return(nil) | ||
| s.Nil(s.mintKeeper.AddCollectedFees(s.ctx, fees)) | ||
| } | ||
|
|
||
| func (s *KeeperTestSuite) TestDefaultMintFn() { | ||
| s.stakingKeeper.EXPECT().StakingTokenSupply(s.ctx).Return(math.NewIntFromUint64(100000000000), nil).AnyTimes() | ||
| bondedRatio := math.LegacyNewDecWithPrec(15, 2) | ||
| s.stakingKeeper.EXPECT().BondedRatio(s.ctx).Return(bondedRatio, nil).AnyTimes() | ||
| s.bankKeeper.EXPECT().MintCoins(s.ctx, types.ModuleName, sdk.NewCoins(sdk.NewCoin("stake", math.NewInt(792)))).Return(nil) | ||
| s.bankKeeper.EXPECT().SendCoinsFromModuleToModule(s.ctx, types.ModuleName, authtypes.FeeCollectorName, gomock.Any()).Return(nil) | ||
| err := s.mintKeeper.SetMintFn(keeper.DefaultMintFn(types.DefaultInflationCalculationFn, s.stakingKeeper, s.mintKeeper)) | ||
| s.NoError(err) | ||
|
Comment on lines
+83
to
+84
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Add Assertions to Confirm Mint Function Is Set Correctly While you are checking for errors after setting the Mint function, consider adding assertions to verify that the Mint function has been set as intended. This will ensure that |
||
|
|
||
| minter, err := s.mintKeeper.Minter.Get(s.ctx) | ||
| s.NoError(err) | ||
|
|
||
| err = s.mintKeeper.DefaultMintFn(types.DefaultInflationCalculationFn)(s.ctx, s.mintKeeper.Environment, &minter, "block", 0) | ||
| err = s.mintKeeper.MintFn(s.ctx, &minter, "block", 0) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Enhance Test by Verifying Mint Operation Results After calling |
||
| s.NoError(err) | ||
|
|
||
| // set a maxSupply and call again. totalSupply will be bigger than maxSupply. | ||
|
|
@@ -118,7 +96,7 @@ func (s *KeeperTestSuite) TestDefaultMintFn() { | |
| err = s.mintKeeper.Params.Set(s.ctx, params) | ||
| s.NoError(err) | ||
|
|
||
| err = s.mintKeeper.DefaultMintFn(types.DefaultInflationCalculationFn)(s.ctx, s.mintKeeper.Environment, &minter, "block", 0) | ||
| err = s.mintKeeper.MintFn(s.ctx, &minter, "block", 0) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Verify Behavior When Total Supply Exceeds Max Supply In this scenario where the total supply exceeds the max supply, consider adding assertions to check that no additional coins are minted and that the minter's state reflects this condition. Confirming this behavior in your test ensures that the Mint function correctly handles cases where minting should be limited. |
||
| s.NoError(err) | ||
|
|
||
| // modify max supply to be almost reached | ||
|
|
@@ -134,7 +112,7 @@ func (s *KeeperTestSuite) TestDefaultMintFn() { | |
| s.bankKeeper.EXPECT().MintCoins(s.ctx, types.ModuleName, sdk.NewCoins(sdk.NewCoin("stake", math.NewInt(2000)))).Return(nil) | ||
| s.bankKeeper.EXPECT().SendCoinsFromModuleToModule(s.ctx, types.ModuleName, authtypes.FeeCollectorName, gomock.Any()).Return(nil) | ||
|
|
||
| err = s.mintKeeper.DefaultMintFn(types.DefaultInflationCalculationFn)(s.ctx, s.mintKeeper.Environment, &minter, "block", 0) | ||
| err = s.mintKeeper.MintFn(s.ctx, &minter, "block", 0) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Assert Minted Amount Matches Adjusted Parameters Given the adjustments to |
||
| s.NoError(err) | ||
| } | ||
|
|
||
|
|
@@ -144,12 +122,13 @@ func (s *KeeperTestSuite) TestBeginBlocker() { | |
| s.stakingKeeper.EXPECT().BondedRatio(s.ctx).Return(bondedRatio, nil).AnyTimes() | ||
| s.bankKeeper.EXPECT().MintCoins(s.ctx, types.ModuleName, sdk.NewCoins(sdk.NewCoin("stake", math.NewInt(792)))).Return(nil) | ||
| s.bankKeeper.EXPECT().SendCoinsFromModuleToModule(s.ctx, types.ModuleName, authtypes.FeeCollectorName, gomock.Any()).Return(nil) | ||
|
|
||
| err := s.mintKeeper.SetMintFn(keeper.DefaultMintFn(types.DefaultInflationCalculationFn, s.stakingKeeper, s.mintKeeper)) | ||
| s.NoError(err) | ||
| // get minter (it should get modified afterwards) | ||
| minter, err := s.mintKeeper.Minter.Get(s.ctx) | ||
| s.NoError(err) | ||
|
|
||
| err = s.mintKeeper.BeginBlocker(s.ctx, s.mintKeeper.DefaultMintFn(types.DefaultInflationCalculationFn)) | ||
| err = s.mintKeeper.BeginBlocker(s.ctx) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Enhance Test by Asserting State Changes After After invoking |
||
| s.NoError(err) | ||
|
|
||
| // get minter again and compare | ||
|
|
@@ -158,10 +137,12 @@ func (s *KeeperTestSuite) TestBeginBlocker() { | |
| s.NotEqual(minter, newMinter) | ||
|
|
||
| // now use a mintfn that doesn't do anything | ||
| err = s.mintKeeper.BeginBlocker(s.ctx, func(ctx context.Context, env appmodule.Environment, minter *types.Minter, epochId string, epochNumber int64) error { | ||
| err = s.mintKeeper.SetMintFn(func(ctx context.Context, env appmodule.Environment, minter *types.Minter, epochId string, epochNumber int64) error { | ||
| return nil | ||
| }) | ||
| s.NoError(err) | ||
| err = s.mintKeeper.BeginBlocker(s.ctx) | ||
| s.NoError(err) | ||
|
|
||
| // get minter again and compare | ||
| unchangedMinter, err := s.mintKeeper.Minter.Get(s.ctx) | ||
|
|
||
Uh oh!
There was an error while loading. Please reload this page.