From d52dbfbe4653abe70525cb6fdc1aab7c369ebe3b Mon Sep 17 00:00:00 2001 From: hacheigriega Date: Sat, 10 Feb 2024 14:40:51 -0500 Subject: [PATCH] feat: vesting bug fixes and simple integration testing --- app/integration.go | 206 ++++++++++++ proto/sedachain/vesting/v1/tx.proto | 62 ++++ proto/sedachain/vesting/v1/vesting.proto | 19 ++ x/vesting/keeper/integration_test.go | 226 +++++++++++++ x/vesting/testutil/expected_keepers_mocks.go | 333 +++++++++++++++++++ 5 files changed, 846 insertions(+) create mode 100644 app/integration.go create mode 100644 proto/sedachain/vesting/v1/tx.proto create mode 100644 proto/sedachain/vesting/v1/vesting.proto create mode 100644 x/vesting/keeper/integration_test.go create mode 100644 x/vesting/testutil/expected_keepers_mocks.go diff --git a/app/integration.go b/app/integration.go new file mode 100644 index 00000000..ef0ccab0 --- /dev/null +++ b/app/integration.go @@ -0,0 +1,206 @@ +package app + +import ( + "fmt" + "time" + + cmtabcitypes "github.com/cometbft/cometbft/abci/types" + cmtproto "github.com/cometbft/cometbft/proto/tendermint/types" + dbm "github.com/cosmos/cosmos-db" + + "cosmossdk.io/core/appmodule" + "cosmossdk.io/log" + "cosmossdk.io/store" + "cosmossdk.io/store/metrics" + storetypes "cosmossdk.io/store/types" + + "github.com/cosmos/cosmos-sdk/baseapp" + "github.com/cosmos/cosmos-sdk/codec" + codectypes "github.com/cosmos/cosmos-sdk/codec/types" + "github.com/cosmos/cosmos-sdk/runtime" + "github.com/cosmos/cosmos-sdk/testutil/integration" + simtestutil "github.com/cosmos/cosmos-sdk/testutil/sims" + sdk "github.com/cosmos/cosmos-sdk/types" + "github.com/cosmos/cosmos-sdk/types/module" + authtx "github.com/cosmos/cosmos-sdk/x/auth/tx" + authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" + consensusparamkeeper "github.com/cosmos/cosmos-sdk/x/consensus/keeper" + consensusparamtypes "github.com/cosmos/cosmos-sdk/x/consensus/types" +) + +const appName = "integration-app" + +// IntegationApp is a test application that can be used to test the integration of modules. +type IntegationApp struct { + *baseapp.BaseApp + + ctx sdk.Context + logger log.Logger + moduleManager module.Manager + queryHelper *baseapp.QueryServiceTestHelper +} + +// NewIntegrationApp creates an application for testing purposes. This application +// is able to route messages to their respective handlers. +func NewIntegrationApp( + sdkCtx sdk.Context, + logger log.Logger, + keys map[string]*storetypes.KVStoreKey, + appCodec codec.Codec, + modules map[string]appmodule.AppModule, +) *IntegationApp { + db := dbm.NewMemDB() + + interfaceRegistry := codectypes.NewInterfaceRegistry() + moduleManager := module.NewManagerFromMap(modules) + basicModuleManager := module.NewBasicManagerFromManager(moduleManager, nil) + basicModuleManager.RegisterInterfaces(interfaceRegistry) + + txConfig := authtx.NewTxConfig(codec.NewProtoCodec(interfaceRegistry), authtx.DefaultSignModes) + bApp := baseapp.NewBaseApp(appName, logger, db, txConfig.TxDecoder(), baseapp.SetChainID(appName)) + bApp.MountKVStores(keys) + + bApp.SetInitChainer(func(ctx sdk.Context, _ *cmtabcitypes.RequestInitChain) (*cmtabcitypes.ResponseInitChain, error) { + for _, mod := range modules { + if m, ok := mod.(module.HasGenesis); ok { + m.InitGenesis(ctx, appCodec, m.DefaultGenesis(appCodec)) + } + } + + return &cmtabcitypes.ResponseInitChain{}, nil + }) + + bApp.SetBeginBlocker(func(_ sdk.Context) (sdk.BeginBlock, error) { + return moduleManager.BeginBlock(sdkCtx) + }) + bApp.SetEndBlocker(func(_ sdk.Context) (sdk.EndBlock, error) { + return moduleManager.EndBlock(sdkCtx) + }) + + router := baseapp.NewMsgServiceRouter() + router.SetInterfaceRegistry(interfaceRegistry) + bApp.SetMsgServiceRouter(router) + + if keys[consensusparamtypes.StoreKey] != nil { + // set baseApp param store + consensusParamsKeeper := consensusparamkeeper.NewKeeper(appCodec, runtime.NewKVStoreService(keys[consensusparamtypes.StoreKey]), authtypes.NewModuleAddress("gov").String(), runtime.EventService{}) + bApp.SetParamStore(consensusParamsKeeper.ParamsStore) + + if err := bApp.LoadLatestVersion(); err != nil { + panic(fmt.Errorf("failed to load application version from store: %w", err)) + } + + if _, err := bApp.InitChain(&cmtabcitypes.RequestInitChain{ChainId: appName, ConsensusParams: simtestutil.DefaultConsensusParams}); err != nil { + panic(fmt.Errorf("failed to initialize application: %w", err)) + } + } else { + if err := bApp.LoadLatestVersion(); err != nil { + panic(fmt.Errorf("failed to load application version from store: %w", err)) + } + + // app.NewDefaultGenesisState(bApp.AppCodec()) + // req := &abci.RequestInitChain{ + // AppStateBytes: appState, + // ChainId: appName, + // ConsensusParams: consensusParams, + // Time: genesisTimestamp, + // } + + if _, err := bApp.InitChain(&cmtabcitypes.RequestInitChain{ChainId: appName}); err != nil { + // if _, err := bApp.InitChain(req); err != nil { + panic(fmt.Errorf("failed to initialize application: %w", err)) + } + } + + bApp.Commit() + + ctx := sdkCtx.WithBlockHeader(cmtproto.Header{ChainID: appName, Time: time.Now()}).WithIsCheckTx(true) + + return &IntegationApp{ + BaseApp: bApp, + logger: logger, + ctx: ctx, + moduleManager: *moduleManager, + queryHelper: baseapp.NewQueryServerTestHelper(ctx, interfaceRegistry), + } +} + +// RunMsg provides the ability to run a message and return the response. +// In order to run a message, the application must have a handler for it. +// These handlers are registered on the application message service router. +// The result of the message execution is returned as an Any type. +// That any type can be unmarshaled to the expected response type. +// If the message execution fails, an error is returned. +func (app *IntegationApp) RunMsg(msg sdk.Msg, option ...integration.Option) (*codectypes.Any, error) { + // set options + cfg := &integration.Config{} + for _, opt := range option { + opt(cfg) + } + + if cfg.AutomaticCommit { + defer app.Commit() + } + + if cfg.AutomaticFinalizeBlock { + height := app.LastBlockHeight() + 1 + if _, err := app.FinalizeBlock(&cmtabcitypes.RequestFinalizeBlock{Height: height}); err != nil { + return nil, fmt.Errorf("failed to run finalize block: %w", err) + } + } + + app.logger.Info("Running msg", "msg", msg.String()) + + handler := app.MsgServiceRouter().Handler(msg) + if handler == nil { + return nil, fmt.Errorf("handler is nil, can't route message %s: %+v", sdk.MsgTypeURL(msg), msg) + } + + msgResult, err := handler(app.ctx, msg) + if err != nil { + return nil, fmt.Errorf("failed to execute message %s: %w", sdk.MsgTypeURL(msg), err) + } + + var response *codectypes.Any + if len(msgResult.MsgResponses) > 0 { + msgResponse := msgResult.MsgResponses[0] + if msgResponse == nil { + return nil, fmt.Errorf("got nil msg response %s in message result: %s", sdk.MsgTypeURL(msg), msgResult.String()) + } + + response = msgResponse + } + + return response, nil +} + +// Context returns the application context. It can be unwrapped to a sdk.Context, +// with the sdk.UnwrapSDKContext function. +func (app *IntegationApp) Context() sdk.Context { + return app.ctx +} + +// AddTime adds time to the application context. +func (app *IntegationApp) AddTime(seconds int64) { + newTime := app.ctx.BlockHeader().Time.Add(time.Duration(int64(time.Second) * seconds)) + app.ctx = app.ctx.WithBlockTime(newTime) +} + +// QueryHelper returns the application query helper. +// It can be used when registering query services. +func (app *IntegationApp) QueryHelper() *baseapp.QueryServiceTestHelper { + return app.queryHelper +} + +// CreateMultiStore is a helper for setting up multiple stores for provided modules. +func CreateMultiStore(keys map[string]*storetypes.KVStoreKey, logger log.Logger) storetypes.CommitMultiStore { + db := dbm.NewMemDB() + cms := store.NewCommitMultiStore(db, logger, metrics.NewNoOpMetrics()) + + for key := range keys { + cms.MountStoreWithDB(keys[key], storetypes.StoreTypeIAVL, db) + } + + _ = cms.LoadLatestVersion() + return cms +} diff --git a/proto/sedachain/vesting/v1/tx.proto b/proto/sedachain/vesting/v1/tx.proto new file mode 100644 index 00000000..e5c19218 --- /dev/null +++ b/proto/sedachain/vesting/v1/tx.proto @@ -0,0 +1,62 @@ +syntax = "proto3"; +package sedachain.vesting.v1; + +import "gogoproto/gogo.proto"; +import "cosmos/base/v1beta1/coin.proto"; +import "cosmos_proto/cosmos.proto"; +import "cosmos/vesting/v1beta1/vesting.proto"; +import "cosmos/msg/v1/msg.proto"; +import "amino/amino.proto"; + +option go_package = "github.com/sedaprotocol/seda-chain/x/vesting/types"; + +// Msg defines the bank Msg service. +service Msg { + option (cosmos.msg.v1.service) = true; + + // CreateVestingAccount creates a new vesting account. + rpc CreateVestingAccount(MsgCreateVestingAccount) returns (MsgCreateVestingAccountResponse); + + // Clawback returns the vesting funds back to the funder. + rpc Clawback(MsgClawback) returns (MsgClawbackResponse); +} + +// MsgCreateVestingAccount defines a message that creates a vesting account. +message MsgCreateVestingAccount { + option (cosmos.msg.v1.signer) = "from_address"; + option (amino.name) = "cosmos-sdk/MsgCreateVestingAccount"; + + option (gogoproto.equal) = true; + + string from_address = 1 [(cosmos_proto.scalar) = "cosmos.AddressString"]; + string to_address = 2 [(cosmos_proto.scalar) = "cosmos.AddressString"]; + repeated cosmos.base.v1beta1.Coin amount = 3 [ + (gogoproto.nullable) = false, + (amino.dont_omitempty) = true, + (amino.encoding) = "legacy_coins", + (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins" + ]; + + // end of vesting as unix time (in seconds). + int64 end_time = 4; +} + +// MsgCreateVestingAccountResponse defines the CreateVestingAccount response type. +message MsgCreateVestingAccountResponse {} + +// MsgClawback defines a message that returns the vesting funds to the funder. +message MsgClawback { + option (cosmos.msg.v1.signer) = "funder_address"; + + // funder_address is the address which funded the account. + string funder_address = 1; + // account_address is the address of the vesting to claw back from. + string account_address = 2; +} + +// MsgClawbackResponse defines the MsgClawback response type. +message MsgClawbackResponse { + // coins is the funds that have been clawed back to the funder. + repeated cosmos.base.v1beta1.Coin coins = 1 + [(gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins", (gogoproto.nullable) = false]; +} diff --git a/proto/sedachain/vesting/v1/vesting.proto b/proto/sedachain/vesting/v1/vesting.proto new file mode 100644 index 00000000..8556fafa --- /dev/null +++ b/proto/sedachain/vesting/v1/vesting.proto @@ -0,0 +1,19 @@ +syntax = "proto3"; +package sedachain.vesting.v1; + +import "cosmos/vesting/v1beta1/vesting.proto"; +import "gogoproto/gogo.proto"; +import "google/protobuf/timestamp.proto"; + +option go_package = "github.com/sedaprotocol/seda-chain/x/vesting/types"; + +// ClawbackContinuousVestingAccount implements the VestingAccount interface. +// It wraps a ContinuousVestingAccount provided by Cosmos SDK to provide +// additional support for clawback. +message ClawbackContinuousVestingAccount { + option (gogoproto.goproto_getters) = false; + option (gogoproto.goproto_stringer) = false; + + cosmos.vesting.v1beta1.ContinuousVestingAccount vesting_account = 1 [(gogoproto.embed) = true]; + string funder_address = 2; +} diff --git a/x/vesting/keeper/integration_test.go b/x/vesting/keeper/integration_test.go new file mode 100644 index 00000000..f4a59e23 --- /dev/null +++ b/x/vesting/keeper/integration_test.go @@ -0,0 +1,226 @@ +package keeper_test + +import ( + "fmt" + "testing" + "time" + + "cosmossdk.io/core/appmodule" + "cosmossdk.io/log" + storetypes "cosmossdk.io/store/types" + "github.com/stretchr/testify/require" + + cmtproto "github.com/cometbft/cometbft/proto/tendermint/types" + + "github.com/cosmos/cosmos-sdk/codec" + addresscodec "github.com/cosmos/cosmos-sdk/codec/address" + "github.com/cosmos/cosmos-sdk/runtime" + "github.com/cosmos/cosmos-sdk/testutil/integration" + sdk "github.com/cosmos/cosmos-sdk/types" + moduletestutil "github.com/cosmos/cosmos-sdk/types/module/testutil" + "github.com/cosmos/cosmos-sdk/x/auth" + authkeeper "github.com/cosmos/cosmos-sdk/x/auth/keeper" + authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" + "github.com/cosmos/cosmos-sdk/x/bank" + bankkeeper "github.com/cosmos/cosmos-sdk/x/bank/keeper" + banktestutil "github.com/cosmos/cosmos-sdk/x/bank/testutil" + banktypes "github.com/cosmos/cosmos-sdk/x/bank/types" + + minttypes "github.com/cosmos/cosmos-sdk/x/mint/types" + sdkstakingkeeper "github.com/cosmos/cosmos-sdk/x/staking/keeper" + stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types" + + "github.com/sedaprotocol/seda-chain/app" + "github.com/sedaprotocol/seda-chain/app/params" + "github.com/sedaprotocol/seda-chain/x/staking" + stakingkeeper "github.com/sedaprotocol/seda-chain/x/staking/keeper" + "github.com/sedaprotocol/seda-chain/x/vesting" + "github.com/sedaprotocol/seda-chain/x/vesting/keeper" + "github.com/sedaprotocol/seda-chain/x/vesting/types" +) + +const Bech32Prefix = "seda" + +var ( + fromAddr = sdk.AccAddress([]byte("from1________________")) + to1Addr = sdk.AccAddress([]byte("to1__________________")) + to2Addr = sdk.AccAddress([]byte("to2__________________")) + to3Addr = sdk.AccAddress([]byte("to3__________________")) + bondDenom = "aseda" + fooCoin = sdk.NewInt64Coin(bondDenom, 10000) + barCoin = sdk.NewInt64Coin(bondDenom, 7000) + zeroCoin = sdk.NewInt64Coin(bondDenom, 0) +) + +type fixture struct { + // ctx sdk.Context + + app *app.IntegationApp + // queryClient v1.QueryClient + // legacyQueryClient v1beta1.QueryClient + cdc codec.Codec + + accountKeeper authkeeper.AccountKeeper + bankKeeper bankkeeper.Keeper + stakingKeeper stakingkeeper.Keeper +} + +func initFixture(tb testing.TB) *fixture { + tb.Helper() + keys := storetypes.NewKVStoreKeys( + authtypes.StoreKey, banktypes.StoreKey, stakingtypes.StoreKey, types.StoreKey, //pooltypes.StoreKey, + ) + cdc := moduletestutil.MakeTestEncodingConfig(auth.AppModuleBasic{}, bank.AppModuleBasic{}, vesting.AppModuleBasic{}).Codec + + logger := log.NewTestLogger(tb) + cms := integration.CreateMultiStore(keys, logger) + + newCtx := sdk.NewContext(cms, cmtproto.Header{Time: time.Now().UTC()}, true, logger) + + authority := authtypes.NewModuleAddress(types.ModuleName) + + maccPerms := map[string][]string{ + minttypes.ModuleName: {authtypes.Minter}, + stakingtypes.BondedPoolName: {authtypes.Burner, authtypes.Staking}, + stakingtypes.NotBondedPoolName: {authtypes.Burner, authtypes.Staking}, + types.ModuleName: {authtypes.Burner}, + } + + accountKeeper := authkeeper.NewAccountKeeper( + cdc, + runtime.NewKVStoreService(keys[authtypes.StoreKey]), + authtypes.ProtoBaseAccount, + maccPerms, + addresscodec.NewBech32Codec(params.Bech32PrefixAccAddr), + params.Bech32PrefixAccAddr, + authority.String(), + ) + + blockedAddresses := map[string]bool{ + accountKeeper.GetAuthority(): false, + } + bankKeeper := bankkeeper.NewBaseKeeper( + cdc, + runtime.NewKVStoreService(keys[banktypes.StoreKey]), + accountKeeper, + blockedAddresses, + authority.String(), + log.NewNopLogger(), + ) + + sdkstakingKeeper := sdkstakingkeeper.NewKeeper(cdc, runtime.NewKVStoreService(keys[stakingtypes.StoreKey]), accountKeeper, bankKeeper, authority.String(), addresscodec.NewBech32Codec(params.Bech32PrefixValAddr), addresscodec.NewBech32Codec(params.Bech32PrefixConsAddr)) + stakingKeeper := stakingkeeper.NewKeeper(sdkstakingKeeper) + + // set default staking params + stakingParams := stakingtypes.DefaultParams() + stakingParams.BondDenom = "aseda" + err := stakingKeeper.SetParams(newCtx, stakingParams) + require.NoError(tb, err) + + // Create MsgServiceRouter, but don't populate it before creating the gov + // keeper. + // router := baseapp.NewMsgServiceRouter() + // router.SetInterfaceRegistry(cdc.InterfaceRegistry()) + + authModule := auth.NewAppModule(cdc, accountKeeper, app.RandomGenesisAccounts, nil) + bankModule := bank.NewAppModule(cdc, bankKeeper, accountKeeper, nil) + stakingModule := staking.NewAppModule(cdc, stakingKeeper, accountKeeper, bankKeeper, nil) + vestingModule := vesting.NewAppModule(accountKeeper, bankKeeper, stakingKeeper) + + integrationApp := app.NewIntegrationApp(newCtx, logger, keys, cdc, map[string]appmodule.AppModule{ + authtypes.ModuleName: authModule, + banktypes.ModuleName: bankModule, + stakingtypes.ModuleName: stakingModule, + types.ModuleName: vestingModule, + }) + + // sdkCtx := sdk.UnwrapSDKContext(integrationApp.Context()) + + // msgSrvr := keeper.NewMsgServerImpl(govKeeper) + // legacyMsgSrvr := keeper.NewLegacyMsgServerImpl(authority.String(), msgSrvr) + + // // Register MsgServer and QueryServer + types.RegisterMsgServer(integrationApp.MsgServiceRouter(), keeper.NewMsgServerImpl(accountKeeper, bankKeeper, stakingKeeper)) + // v1beta1.RegisterMsgServer(router, legacyMsgSrvr) + + // v1.RegisterQueryServer(integrationApp.QueryHelper(), keeper.NewQueryServer(govKeeper)) + // v1beta1.RegisterQueryServer(integrationApp.QueryHelper(), keeper.NewLegacyQueryServer(govKeeper)) + + // queryClient := v1.NewQueryClient(integrationApp.QueryHelper()) + // legacyQueryClient := v1beta1.NewQueryClient(integrationApp.QueryHelper()) + + return &fixture{ + app: integrationApp, + cdc: cdc, + // ctx: sdkCtx, + // queryClient: queryClient, + // legacyQueryClient: legacyQueryClient, + accountKeeper: accountKeeper, + bankKeeper: bankKeeper, + stakingKeeper: *stakingKeeper, + // govKeeper: govKeeper, + } +} + +func TestClawbackContinuousVesting(t *testing.T) { + f := initFixture(t) + + // _ = f.ctx + + funderAddr := sdk.MustAccAddressFromBech32("seda1gujynygp0tkwzfpt0g7dv4829jwyk8f0yhp88d") // TO-DO cosmos139f7kncmglres2nf3h4hc4tade85ekfr8sulz5 + accountAddr := sdk.MustAccAddressFromBech32("seda1ucv5709wlf9jn84ynyjzyzeavwvurmdyxat26l") // TO-DO cosmos1x33fy6rusfprkntvjsfregss7rvsvyy4lkwrqu + + originalVesting := sdk.NewCoins(fooCoin) + endTime := f.app.Context().BlockTime().Unix() + 100 + // bondedAmt := math.NewInt(0) + // unbondingAmt := math.NewInt(0) + // unbonded := originalVesting // TO-DO why? GetAllBalances + + // msg := &types.MsgClawback{ + // FunderAddress: funderAddr.String(), + // AccountAddress: accountAddr.String(), + // } + + // funderAcc := authtypes.NewBaseAccountWithAddress(funderAddr) + // baseAccount := authtypes.NewBaseAccountWithAddress(accountAddr) + // baseVestingAccount, err := sdkvestingtypes.NewBaseVestingAccount(baseAccount, originalVesting, endTime) + // require.NoError(t, err) + // vestingAccount := types.NewClawbackContinuousVestingAccountRaw(baseVestingAccount, f.ctx.BlockTime().Unix(), msg.FunderAddress) + // f.accountKeeper.SetAccount(f.ctx, vestingAccount) + + f.bankKeeper.SetSendEnabled(f.app.Context(), "aseda", true) + + err := banktestutil.FundAccount(f.app.Context(), f.bankKeeper, funderAddr, sdk.NewCoins(fooCoin)) + require.NoError(t, err) + + // 1. create clawback continuous vesting account + msg := &types.MsgCreateVestingAccount{ + FromAddress: funderAddr.String(), + ToAddress: accountAddr.String(), + Amount: originalVesting, + EndTime: endTime, + } + res, err := f.app.RunMsg(msg) + require.NoError(t, err) + fmt.Println(res) + + // 2. clawback after some time + f.app.AddTime(30) + clawbackMsg := &types.MsgClawback{ + FunderAddress: funderAddr.String(), + AccountAddress: accountAddr.String(), // TO-DO rename to RecipientAddress? + } + res, err = f.app.RunMsg(clawbackMsg) + require.NoError(t, err) + + result := types.MsgClawbackResponse{} + err = f.cdc.Unmarshal(res.Value, &result) + require.NoError(t, err) + fmt.Println(result) + + require.Equal(t, sdk.NewCoins(barCoin), result.Coins) + // createValidators(t, f, []int64{5, 5, 5}) +} + +// Test when 0 time has passed +// toXfer seems to be 0 diff --git a/x/vesting/testutil/expected_keepers_mocks.go b/x/vesting/testutil/expected_keepers_mocks.go new file mode 100644 index 00000000..4afcd75a --- /dev/null +++ b/x/vesting/testutil/expected_keepers_mocks.go @@ -0,0 +1,333 @@ +// Code generated by MockGen. DO NOT EDIT. +// Source: x/vesting/types/expected_keepers.go + +// Package testutil is a generated GoMock package. +package testutil + +import ( + context "context" + reflect "reflect" + + address "cosmossdk.io/core/address" + math "cosmossdk.io/math" + types "github.com/cosmos/cosmos-sdk/types" + types0 "github.com/cosmos/cosmos-sdk/x/staking/types" + gomock "github.com/golang/mock/gomock" +) + +// MockAccountKeeper is a mock of AccountKeeper interface. +type MockAccountKeeper struct { + ctrl *gomock.Controller + recorder *MockAccountKeeperMockRecorder +} + +// MockAccountKeeperMockRecorder is the mock recorder for MockAccountKeeper. +type MockAccountKeeperMockRecorder struct { + mock *MockAccountKeeper +} + +// NewMockAccountKeeper creates a new mock instance. +func NewMockAccountKeeper(ctrl *gomock.Controller) *MockAccountKeeper { + mock := &MockAccountKeeper{ctrl: ctrl} + mock.recorder = &MockAccountKeeperMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockAccountKeeper) EXPECT() *MockAccountKeeperMockRecorder { + return m.recorder +} + +// AddressCodec mocks base method. +func (m *MockAccountKeeper) AddressCodec() address.Codec { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "AddressCodec") + ret0, _ := ret[0].(address.Codec) + return ret0 +} + +// AddressCodec indicates an expected call of AddressCodec. +func (mr *MockAccountKeeperMockRecorder) AddressCodec() *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "AddressCodec", reflect.TypeOf((*MockAccountKeeper)(nil).AddressCodec)) +} + +// GetAccount mocks base method. +func (m *MockAccountKeeper) GetAccount(ctx context.Context, addr types.AccAddress) types.AccountI { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetAccount", ctx, addr) + ret0, _ := ret[0].(types.AccountI) + return ret0 +} + +// GetAccount indicates an expected call of GetAccount. +func (mr *MockAccountKeeperMockRecorder) GetAccount(ctx, addr interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetAccount", reflect.TypeOf((*MockAccountKeeper)(nil).GetAccount), ctx, addr) +} + +// NewAccount mocks base method. +func (m *MockAccountKeeper) NewAccount(ctx context.Context, acc types.AccountI) types.AccountI { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "NewAccount", ctx, acc) + ret0, _ := ret[0].(types.AccountI) + return ret0 +} + +// NewAccount indicates an expected call of NewAccount. +func (mr *MockAccountKeeperMockRecorder) NewAccount(ctx, acc interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "NewAccount", reflect.TypeOf((*MockAccountKeeper)(nil).NewAccount), ctx, acc) +} + +// SetAccount mocks base method. +func (m *MockAccountKeeper) SetAccount(ctx context.Context, acc types.AccountI) { + m.ctrl.T.Helper() + m.ctrl.Call(m, "SetAccount", ctx, acc) +} + +// SetAccount indicates an expected call of SetAccount. +func (mr *MockAccountKeeperMockRecorder) SetAccount(ctx, acc interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SetAccount", reflect.TypeOf((*MockAccountKeeper)(nil).SetAccount), ctx, acc) +} + +// MockBankKeeper is a mock of BankKeeper interface. +type MockBankKeeper struct { + ctrl *gomock.Controller + recorder *MockBankKeeperMockRecorder +} + +// MockBankKeeperMockRecorder is the mock recorder for MockBankKeeper. +type MockBankKeeperMockRecorder struct { + mock *MockBankKeeper +} + +// NewMockBankKeeper creates a new mock instance. +func NewMockBankKeeper(ctrl *gomock.Controller) *MockBankKeeper { + mock := &MockBankKeeper{ctrl: ctrl} + mock.recorder = &MockBankKeeperMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockBankKeeper) EXPECT() *MockBankKeeperMockRecorder { + return m.recorder +} + +// BlockedAddr mocks base method. +func (m *MockBankKeeper) BlockedAddr(addr types.AccAddress) bool { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "BlockedAddr", addr) + ret0, _ := ret[0].(bool) + return ret0 +} + +// BlockedAddr indicates an expected call of BlockedAddr. +func (mr *MockBankKeeperMockRecorder) BlockedAddr(addr interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "BlockedAddr", reflect.TypeOf((*MockBankKeeper)(nil).BlockedAddr), addr) +} + +// GetAllBalances mocks base method. +func (m *MockBankKeeper) GetAllBalances(ctx context.Context, addr types.AccAddress) types.Coins { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetAllBalances", ctx, addr) + ret0, _ := ret[0].(types.Coins) + return ret0 +} + +// GetAllBalances indicates an expected call of GetAllBalances. +func (mr *MockBankKeeperMockRecorder) GetAllBalances(ctx, addr interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetAllBalances", reflect.TypeOf((*MockBankKeeper)(nil).GetAllBalances), ctx, addr) +} + +// IsSendEnabledCoins mocks base method. +func (m *MockBankKeeper) IsSendEnabledCoins(ctx context.Context, coins ...types.Coin) error { + m.ctrl.T.Helper() + varargs := []interface{}{ctx} + for _, a := range coins { + varargs = append(varargs, a) + } + ret := m.ctrl.Call(m, "IsSendEnabledCoins", varargs...) + ret0, _ := ret[0].(error) + return ret0 +} + +// IsSendEnabledCoins indicates an expected call of IsSendEnabledCoins. +func (mr *MockBankKeeperMockRecorder) IsSendEnabledCoins(ctx interface{}, coins ...interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + varargs := append([]interface{}{ctx}, coins...) + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "IsSendEnabledCoins", reflect.TypeOf((*MockBankKeeper)(nil).IsSendEnabledCoins), varargs...) +} + +// SendCoins mocks base method. +func (m *MockBankKeeper) SendCoins(ctx context.Context, fromAddr, toAddr types.AccAddress, amt types.Coins) error { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "SendCoins", ctx, fromAddr, toAddr, amt) + ret0, _ := ret[0].(error) + return ret0 +} + +// SendCoins indicates an expected call of SendCoins. +func (mr *MockBankKeeperMockRecorder) SendCoins(ctx, fromAddr, toAddr, amt interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SendCoins", reflect.TypeOf((*MockBankKeeper)(nil).SendCoins), ctx, fromAddr, toAddr, amt) +} + +// SpendableCoins mocks base method. +func (m *MockBankKeeper) SpendableCoins(ctx context.Context, addr types.AccAddress) types.Coins { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "SpendableCoins", ctx, addr) + ret0, _ := ret[0].(types.Coins) + return ret0 +} + +// SpendableCoins indicates an expected call of SpendableCoins. +func (mr *MockBankKeeperMockRecorder) SpendableCoins(ctx, addr interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "SpendableCoins", reflect.TypeOf((*MockBankKeeper)(nil).SpendableCoins), ctx, addr) +} + +// MockStakingKeeper is a mock of StakingKeeper interface. +type MockStakingKeeper struct { + ctrl *gomock.Controller + recorder *MockStakingKeeperMockRecorder +} + +// MockStakingKeeperMockRecorder is the mock recorder for MockStakingKeeper. +type MockStakingKeeperMockRecorder struct { + mock *MockStakingKeeper +} + +// NewMockStakingKeeper creates a new mock instance. +func NewMockStakingKeeper(ctrl *gomock.Controller) *MockStakingKeeper { + mock := &MockStakingKeeper{ctrl: ctrl} + mock.recorder = &MockStakingKeeperMockRecorder{mock} + return mock +} + +// EXPECT returns an object that allows the caller to indicate expected use. +func (m *MockStakingKeeper) EXPECT() *MockStakingKeeperMockRecorder { + return m.recorder +} + +// BondDenom mocks base method. +func (m *MockStakingKeeper) BondDenom(ctx context.Context) (string, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "BondDenom", ctx) + ret0, _ := ret[0].(string) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// BondDenom indicates an expected call of BondDenom. +func (mr *MockStakingKeeperMockRecorder) BondDenom(ctx interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "BondDenom", reflect.TypeOf((*MockStakingKeeper)(nil).BondDenom), ctx) +} + +// GetDelegatorBonded mocks base method. +func (m *MockStakingKeeper) GetDelegatorBonded(ctx context.Context, delegator types.AccAddress) (math.Int, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetDelegatorBonded", ctx, delegator) + ret0, _ := ret[0].(math.Int) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetDelegatorBonded indicates an expected call of GetDelegatorBonded. +func (mr *MockStakingKeeperMockRecorder) GetDelegatorBonded(ctx, delegator interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetDelegatorBonded", reflect.TypeOf((*MockStakingKeeper)(nil).GetDelegatorBonded), ctx, delegator) +} + +// GetDelegatorDelegations mocks base method. +func (m *MockStakingKeeper) GetDelegatorDelegations(ctx context.Context, delegator types.AccAddress, maxRetrieve uint16) ([]types0.Delegation, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetDelegatorDelegations", ctx, delegator, maxRetrieve) + ret0, _ := ret[0].([]types0.Delegation) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetDelegatorDelegations indicates an expected call of GetDelegatorDelegations. +func (mr *MockStakingKeeperMockRecorder) GetDelegatorDelegations(ctx, delegator, maxRetrieve interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetDelegatorDelegations", reflect.TypeOf((*MockStakingKeeper)(nil).GetDelegatorDelegations), ctx, delegator, maxRetrieve) +} + +// GetDelegatorUnbonding mocks base method. +func (m *MockStakingKeeper) GetDelegatorUnbonding(ctx context.Context, delegator types.AccAddress) (math.Int, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetDelegatorUnbonding", ctx, delegator) + ret0, _ := ret[0].(math.Int) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetDelegatorUnbonding indicates an expected call of GetDelegatorUnbonding. +func (mr *MockStakingKeeperMockRecorder) GetDelegatorUnbonding(ctx, delegator interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetDelegatorUnbonding", reflect.TypeOf((*MockStakingKeeper)(nil).GetDelegatorUnbonding), ctx, delegator) +} + +// GetUnbondingDelegations mocks base method. +func (m *MockStakingKeeper) GetUnbondingDelegations(ctx context.Context, delegator types.AccAddress, maxRetrieve uint16) ([]types0.UnbondingDelegation, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetUnbondingDelegations", ctx, delegator, maxRetrieve) + ret0, _ := ret[0].([]types0.UnbondingDelegation) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetUnbondingDelegations indicates an expected call of GetUnbondingDelegations. +func (mr *MockStakingKeeperMockRecorder) GetUnbondingDelegations(ctx, delegator, maxRetrieve interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetUnbondingDelegations", reflect.TypeOf((*MockStakingKeeper)(nil).GetUnbondingDelegations), ctx, delegator, maxRetrieve) +} + +// GetValidator mocks base method. +func (m *MockStakingKeeper) GetValidator(ctx context.Context, addr types.ValAddress) (types0.Validator, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "GetValidator", ctx, addr) + ret0, _ := ret[0].(types0.Validator) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// GetValidator indicates an expected call of GetValidator. +func (mr *MockStakingKeeperMockRecorder) GetValidator(ctx, addr interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "GetValidator", reflect.TypeOf((*MockStakingKeeper)(nil).GetValidator), ctx, addr) +} + +// TransferDelegation mocks base method. +func (m *MockStakingKeeper) TransferDelegation(ctx context.Context, fromAddr, toAddr types.AccAddress, valAddr types.ValAddress, wantShares math.LegacyDec) (math.LegacyDec, error) { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "TransferDelegation", ctx, fromAddr, toAddr, valAddr, wantShares) + ret0, _ := ret[0].(math.LegacyDec) + ret1, _ := ret[1].(error) + return ret0, ret1 +} + +// TransferDelegation indicates an expected call of TransferDelegation. +func (mr *MockStakingKeeperMockRecorder) TransferDelegation(ctx, fromAddr, toAddr, valAddr, wantShares interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "TransferDelegation", reflect.TypeOf((*MockStakingKeeper)(nil).TransferDelegation), ctx, fromAddr, toAddr, valAddr, wantShares) +} + +// TransferUnbonding mocks base method. +func (m *MockStakingKeeper) TransferUnbonding(ctx context.Context, fromAddr, toAddr types.AccAddress, valAddr types.ValAddress, wantAmt math.Int) math.Int { + m.ctrl.T.Helper() + ret := m.ctrl.Call(m, "TransferUnbonding", ctx, fromAddr, toAddr, valAddr, wantAmt) + ret0, _ := ret[0].(math.Int) + return ret0 +} + +// TransferUnbonding indicates an expected call of TransferUnbonding. +func (mr *MockStakingKeeperMockRecorder) TransferUnbonding(ctx, fromAddr, toAddr, valAddr, wantAmt interface{}) *gomock.Call { + mr.mock.ctrl.T.Helper() + return mr.mock.ctrl.RecordCallWithMethodType(mr.mock, "TransferUnbonding", reflect.TypeOf((*MockStakingKeeper)(nil).TransferUnbonding), ctx, fromAddr, toAddr, valAddr, wantAmt) +}