From c7534584ddc3263bd50bac9f54a00b9718d0a673 Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Juli=C3=A1n=20Toledano?= Date: Fri, 5 Apr 2024 15:09:45 +0200 Subject: [PATCH] refactor(x/bank)!: remove Address.String() (#19954) Co-authored-by: Marko --- simapp/simd/cmd/testnet.go | 5 +- tests/integration/bank/app_test.go | 111 ++++++++++------- tests/integration/bank/bench_test.go | 15 ++- .../bank/keeper/deterministic_test.go | 32 +++-- tests/sims/authz/operations_test.go | 4 +- types/query/pagination_test.go | 54 ++++---- x/accounts/defaults/lockup/lockup.go | 2 +- x/authz/client/cli/tx.go | 2 +- x/authz/keeper/keeper_test.go | 6 +- x/authz/keeper/msg_server_test.go | 20 +-- x/authz/migrations/v2/store_test.go | 2 +- x/authz/module/abci_test.go | 2 +- x/authz/msgs_test.go | 2 +- x/authz/simulation/decoder_test.go | 2 +- x/authz/simulation/genesis.go | 6 +- x/authz/simulation/operations.go | 7 +- x/bank/CHANGELOG.md | 5 + x/bank/client/cli/tx.go | 11 +- x/bank/keeper/collections_test.go | 10 +- x/bank/keeper/genesis.go | 8 +- x/bank/keeper/genesis_test.go | 19 ++- x/bank/keeper/grpc_query.go | 6 +- x/bank/keeper/grpc_query_test.go | 31 +++-- x/bank/keeper/keeper_test.go | 116 ++++++++++++------ x/bank/keeper/msg_server_test.go | 67 ++++++---- x/bank/simulation/genesis.go | 17 ++- x/bank/simulation/operations.go | 32 +++-- x/bank/simulation/proposals.go | 9 +- x/bank/simulation/proposals_test.go | 9 +- x/bank/types/balance.go | 10 +- x/bank/types/balance_test.go | 32 +++-- x/bank/types/inputs_outputs.go | 8 +- x/bank/types/msgs_test.go | 35 ++++-- x/bank/types/querier.go | 13 +- x/bank/types/send_authorization.go | 14 ++- x/bank/types/send_authorization_test.go | 20 +-- x/genutil/genaccounts.go | 6 +- 37 files changed, 499 insertions(+), 251 deletions(-) diff --git a/simapp/simd/cmd/testnet.go b/simapp/simd/cmd/testnet.go index 1bc881362d66..957cc455e51a 100644 --- a/simapp/simd/cmd/testnet.go +++ b/simapp/simd/cmd/testnet.go @@ -391,7 +391,10 @@ func initGenFiles( var bankGenState banktypes.GenesisState clientCtx.Codec.MustUnmarshalJSON(appGenState[banktypes.ModuleName], &bankGenState) - bankGenState.Balances = banktypes.SanitizeGenesisBalances(genBalances) + bankGenState.Balances, err = banktypes.SanitizeGenesisBalances(genBalances, clientCtx.AddressCodec) + if err != nil { + return err + } for _, bal := range bankGenState.Balances { bankGenState.Supply = bankGenState.Supply.Add(bal.Coins...) } diff --git a/tests/integration/bank/app_test.go b/tests/integration/bank/app_test.go index eeca54284fff..d1b2e91dbe36 100644 --- a/tests/integration/bank/app_test.go +++ b/tests/integration/bank/app_test.go @@ -67,34 +67,6 @@ var ( halfCoins = sdk.Coins{sdk.NewInt64Coin("foocoin", 5)} sendMsg1 = types.NewMsgSend(addr1.String(), addr2.String(), coins) - - multiSendMsg1 = &types.MsgMultiSend{ - Inputs: []types.Input{types.NewInput(addr1, coins)}, - Outputs: []types.Output{types.NewOutput(addr2, coins)}, - } - multiSendMsg2 = &types.MsgMultiSend{ - Inputs: []types.Input{types.NewInput(addr1, coins)}, - Outputs: []types.Output{ - types.NewOutput(addr2, halfCoins), - types.NewOutput(addr3, halfCoins), - }, - } - multiSendMsg3 = &types.MsgMultiSend{ - Inputs: []types.Input{types.NewInput(addr2, coins)}, - Outputs: []types.Output{ - types.NewOutput(addr1, coins), - }, - } - multiSendMsg4 = &types.MsgMultiSend{ - Inputs: []types.Input{types.NewInput(addr1, coins)}, - Outputs: []types.Output{ - types.NewOutput(moduleAccAddr, coins), - }, - } - invalidMultiSendMsg = &types.MsgMultiSend{ - Inputs: []types.Input{types.NewInput(addr1, coins), types.NewInput(addr2, coins)}, - Outputs: []types.Output{}, - } ) type suite struct { @@ -191,17 +163,25 @@ func TestSendNotEnoughBalance(t *testing.T) { } func TestMsgMultiSendWithAccounts(t *testing.T) { + addr1Str, err := cdctestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr1) + require.NoError(t, err) acc := &authtypes.BaseAccount{ - Address: addr1.String(), + Address: addr1Str, } + addr2Str, err := cdctestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr2) + require.NoError(t, err) + + moduleStrAddr, err := cdctestutil.CodecOptions{}.GetAddressCodec().BytesToString(moduleAccAddr) + require.NoError(t, err) + genAccs := []authtypes.GenesisAccount{acc} s := createTestSuite(t, genAccs) baseApp := s.App.BaseApp ctx := baseApp.NewContext(false) require.NoError(t, testutil.FundAccount(ctx, s.BankKeeper, addr1, sdk.NewCoins(sdk.NewInt64Coin("foocoin", 67)))) - _, err := baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: baseApp.LastBlockHeight() + 1}) + _, err = baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: baseApp.LastBlockHeight() + 1}) require.NoError(t, err) _, err = baseApp.Commit() require.NoError(t, err) @@ -212,8 +192,11 @@ func TestMsgMultiSendWithAccounts(t *testing.T) { testCases := []appTestCase{ { - desc: "make a valid tx", - msgs: []sdk.Msg{multiSendMsg1}, + desc: "make a valid tx", + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{types.NewOutput(addr2Str, coins)}, + }}, accNums: []uint64{0}, accSeqs: []uint64{0}, expSimPass: true, @@ -225,8 +208,11 @@ func TestMsgMultiSendWithAccounts(t *testing.T) { }, }, { - desc: "wrong accNum should pass Simulate, but not Deliver", - msgs: []sdk.Msg{multiSendMsg1}, + desc: "wrong accNum should pass Simulate, but not Deliver", + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{types.NewOutput(addr2Str, coins)}, + }}, accNums: []uint64{1}, // wrong account number accSeqs: []uint64{1}, expSimPass: true, // doesn't check signature @@ -234,8 +220,13 @@ func TestMsgMultiSendWithAccounts(t *testing.T) { privKeys: []cryptotypes.PrivKey{priv1}, }, { - desc: "wrong accSeq should not pass Simulate", - msgs: []sdk.Msg{multiSendMsg4}, + desc: "wrong accSeq should not pass Simulate", + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{ + types.NewOutput(moduleStrAddr, coins), + }, + }}, accNums: []uint64{0}, accSeqs: []uint64{0}, // wrong account sequence expSimPass: false, @@ -243,8 +234,11 @@ func TestMsgMultiSendWithAccounts(t *testing.T) { privKeys: []cryptotypes.PrivKey{priv1}, }, { - desc: "multiple inputs not allowed", - msgs: []sdk.Msg{invalidMultiSendMsg}, + desc: "multiple inputs not allowed", + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins), types.NewInput(addr2Str, coins)}, + Outputs: []types.Output{}, + }}, accNums: []uint64{0}, accSeqs: []uint64{0}, expSimPass: false, @@ -272,12 +266,19 @@ func TestMsgMultiSendWithAccounts(t *testing.T) { } func TestMsgMultiSendMultipleOut(t *testing.T) { + ac := cdctestutil.CodecOptions{}.GetAddressCodec() + addr1Str, err := ac.BytesToString(addr1) + require.NoError(t, err) acc1 := &authtypes.BaseAccount{ - Address: addr1.String(), + Address: addr1Str, } + addr2Str, err := ac.BytesToString(addr2) + require.NoError(t, err) acc2 := &authtypes.BaseAccount{ - Address: addr2.String(), + Address: addr2Str, } + addr3Str, err := ac.BytesToString(addr3) + require.NoError(t, err) genAccs := []authtypes.GenesisAccount{acc1, acc2} s := createTestSuite(t, genAccs) @@ -286,14 +287,20 @@ func TestMsgMultiSendMultipleOut(t *testing.T) { require.NoError(t, testutil.FundAccount(ctx, s.BankKeeper, addr1, sdk.NewCoins(sdk.NewInt64Coin("foocoin", 42)))) require.NoError(t, testutil.FundAccount(ctx, s.BankKeeper, addr2, sdk.NewCoins(sdk.NewInt64Coin("foocoin", 42)))) - _, err := baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: baseApp.LastBlockHeight() + 1}) + _, err = baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: baseApp.LastBlockHeight() + 1}) require.NoError(t, err) _, err = baseApp.Commit() require.NoError(t, err) testCases := []appTestCase{ { - msgs: []sdk.Msg{multiSendMsg2}, + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{ + types.NewOutput(addr2Str, halfCoins), + types.NewOutput(addr3Str, halfCoins), + }, + }}, accNums: []uint64{0}, accSeqs: []uint64{0}, expSimPass: true, @@ -320,9 +327,15 @@ func TestMsgMultiSendMultipleOut(t *testing.T) { } func TestMsgMultiSendDependent(t *testing.T) { + ac := cdctestutil.CodecOptions{}.GetAddressCodec() + addr1Str, err := ac.BytesToString(addr1) + require.NoError(t, err) + addr2Str, err := ac.BytesToString(addr2) + require.NoError(t, err) + acc1 := authtypes.NewBaseAccountWithAddress(addr1) acc2 := authtypes.NewBaseAccountWithAddress(addr2) - err := acc2.SetAccountNumber(1) + err = acc2.SetAccountNumber(1) require.NoError(t, err) genAccs := []authtypes.GenesisAccount{acc1, acc2} @@ -338,7 +351,10 @@ func TestMsgMultiSendDependent(t *testing.T) { testCases := []appTestCase{ { - msgs: []sdk.Msg{multiSendMsg1}, + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{types.NewOutput(addr2Str, coins)}, + }}, accNums: []uint64{0}, accSeqs: []uint64{0}, expSimPass: true, @@ -350,7 +366,12 @@ func TestMsgMultiSendDependent(t *testing.T) { }, }, { - msgs: []sdk.Msg{multiSendMsg3}, + msgs: []sdk.Msg{&types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr2Str, coins)}, + Outputs: []types.Output{ + types.NewOutput(addr1Str, coins), + }, + }}, accNums: []uint64{1}, accSeqs: []uint64{0}, expSimPass: true, diff --git a/tests/integration/bank/bench_test.go b/tests/integration/bank/bench_test.go index b953a3f39ec9..89b4d458cfee 100644 --- a/tests/integration/bank/bench_test.go +++ b/tests/integration/bank/bench_test.go @@ -12,6 +12,7 @@ import ( authtypes "cosmossdk.io/x/auth/types" _ "cosmossdk.io/x/bank" "cosmossdk.io/x/bank/testutil" + "cosmossdk.io/x/bank/types" stakingtypes "cosmossdk.io/x/staking/types" "github.com/cosmos/cosmos-sdk/client" @@ -123,17 +124,22 @@ func BenchmarkOneBankMultiSendTxPerBlock(b *testing.B) { // b.Skip("Skipping benchmark with buggy code reported at https://github.com/cosmos/cosmos-sdk/issues/10023") b.ReportAllocs() + addr1Str, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr1) + require.NoError(b, err) acc := authtypes.BaseAccount{ Address: addr1.String(), } + addr2Str, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr2) + require.NoError(b, err) + // construct genesis state genAccs := []authtypes.GenesisAccount{&acc} s := createTestSuite(&testing.T{}, genAccs) baseApp := s.App.BaseApp ctx := baseApp.NewContext(false) - _, err := baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: 1}) + _, err = baseApp.FinalizeBlock(&abci.RequestFinalizeBlock{Height: 1}) require.NoError(b, err) require.NoError(b, testutil.FundAccount(ctx, s.BankKeeper, addr1, sdk.NewCoins(sdk.NewInt64Coin("foocoin", 100000000000)))) @@ -144,8 +150,13 @@ func BenchmarkOneBankMultiSendTxPerBlock(b *testing.B) { txGen := moduletestutil.MakeTestTxConfig(codectestutil.CodecOptions{}) txEncoder := txGen.TxEncoder() + multiSendMsg := &types.MsgMultiSend{ + Inputs: []types.Input{types.NewInput(addr1Str, coins)}, + Outputs: []types.Output{types.NewOutput(addr2Str, coins)}, + } + // pre-compute all txs - txs, err := genSequenceOfTxs(txGen, []sdk.Msg{multiSendMsg1}, []uint64{0}, []uint64{uint64(0)}, b.N, priv1) + txs, err := genSequenceOfTxs(txGen, []sdk.Msg{multiSendMsg}, []uint64{0}, []uint64{uint64(0)}, b.N, priv1) require.NoError(b, err) b.ResetTimer() diff --git a/tests/integration/bank/keeper/deterministic_test.go b/tests/integration/bank/keeper/deterministic_test.go index 635e061dd915..78d736143c35 100644 --- a/tests/integration/bank/keeper/deterministic_test.go +++ b/tests/integration/bank/keeper/deterministic_test.go @@ -150,25 +150,35 @@ func TestGRPCQueryBalance(t *testing.T) { coin := getCoin(rt) fundAccount(f, addr, coin) - req := banktypes.NewQueryBalanceRequest(addr, coin.GetDenom()) + addrStr, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr) + assert.NilError(t, err) + + req := banktypes.NewQueryBalanceRequest(addrStr, coin.GetDenom()) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.Balance, 0, true) }) + addr1Str, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr1) + assert.NilError(t, err) + fundAccount(f, addr1, coin1) - req := banktypes.NewQueryBalanceRequest(addr1, coin1.GetDenom()) + req := banktypes.NewQueryBalanceRequest(addr1Str, coin1.GetDenom()) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.Balance, 1087, false) } func TestGRPCQueryAllBalances(t *testing.T) { t.Parallel() f := initDeterministicFixture(t) + addressCodec := codectestutil.CodecOptions{}.GetAddressCodec() rapid.Check(t, func(rt *rapid.T) { addr := testdata.AddressGenerator(rt).Draw(rt, "address") numCoins := rapid.IntRange(1, 10).Draw(rt, "num-count") coins := make(sdk.Coins, 0, numCoins) + addrStr, err := addressCodec.BytesToString(addr) + assert.NilError(t, err) + for i := 0; i < numCoins; i++ { coin := getCoin(rt) @@ -178,7 +188,7 @@ func TestGRPCQueryAllBalances(t *testing.T) { fundAccount(f, addr, coins...) - req := banktypes.NewQueryAllBalancesRequest(addr, testdata.PaginationGenerator(rt, uint64(numCoins)).Draw(rt, "pagination"), false) + req := banktypes.NewQueryAllBalancesRequest(addrStr, testdata.PaginationGenerator(rt, uint64(numCoins)).Draw(rt, "pagination"), false) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.AllBalances, 0, true) }) @@ -188,7 +198,10 @@ func TestGRPCQueryAllBalances(t *testing.T) { ) fundAccount(f, addr1, coins...) - req := banktypes.NewQueryAllBalancesRequest(addr1, nil, false) + addr1Str, err := addressCodec.BytesToString(addr1) + assert.NilError(t, err) + + req := banktypes.NewQueryAllBalancesRequest(addr1Str, nil, false) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.AllBalances, 357, false) } @@ -199,6 +212,8 @@ func TestGRPCQuerySpendableBalances(t *testing.T) { rapid.Check(t, func(rt *rapid.T) { addr := testdata.AddressGenerator(rt).Draw(rt, "address") + addrStr, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr) + assert.NilError(t, err) // Denoms must be unique, otherwise sdk.NewCoins will panic. denoms := rapid.SliceOfNDistinct(rapid.StringMatching(denomRegex), 1, 10, rapid.ID[string]).Draw(rt, "denoms") @@ -213,10 +228,10 @@ func TestGRPCQuerySpendableBalances(t *testing.T) { coins = sdk.NewCoins(append(coins, coin)...) } - err := banktestutil.FundAccount(f.ctx, f.bankKeeper, addr, coins) + err = banktestutil.FundAccount(f.ctx, f.bankKeeper, addr, coins) assert.NilError(t, err) - req := banktypes.NewQuerySpendableBalancesRequest(addr, testdata.PaginationGenerator(rt, uint64(len(denoms))).Draw(rt, "pagination")) + req := banktypes.NewQuerySpendableBalancesRequest(addrStr, testdata.PaginationGenerator(rt, uint64(len(denoms))).Draw(rt, "pagination")) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.SpendableBalances, 0, true) }) @@ -228,7 +243,10 @@ func TestGRPCQuerySpendableBalances(t *testing.T) { err := banktestutil.FundAccount(f.ctx, f.bankKeeper, addr1, coins) assert.NilError(t, err) - req := banktypes.NewQuerySpendableBalancesRequest(addr1, nil) + addr1Str, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr1) + assert.NilError(t, err) + + req := banktypes.NewQuerySpendableBalancesRequest(addr1Str, nil) testdata.DeterministicIterations(t, f.ctx, req, f.queryClient.SpendableBalances, 1777, false) } diff --git a/tests/sims/authz/operations_test.go b/tests/sims/authz/operations_test.go index c241d0afcdbd..60e4ca724112 100644 --- a/tests/sims/authz/operations_test.go +++ b/tests/sims/authz/operations_test.go @@ -169,7 +169,7 @@ func (suite *SimTestSuite) TestSimulateRevoke() { granter := accounts[0] grantee := accounts[1] - a := banktypes.NewSendAuthorization(initCoins, nil) + a := banktypes.NewSendAuthorization(initCoins, nil, suite.accountKeeper.AddressCodec()) expire := time.Now().Add(30 * time.Hour) err := suite.authzKeeper.SaveGrant(suite.ctx, grantee.Address, granter.Address, a, &expire) @@ -200,7 +200,7 @@ func (suite *SimTestSuite) TestSimulateExec() { granter := accounts[0] grantee := accounts[1] - a := banktypes.NewSendAuthorization(initCoins, nil) + a := banktypes.NewSendAuthorization(initCoins, nil, suite.accountKeeper.AddressCodec()) expire := suite.ctx.HeaderInfo().Time.Add(1 * time.Hour) err := suite.authzKeeper.SaveGrant(suite.ctx, grantee.Address, granter.Address, a, &expire) diff --git a/types/query/pagination_test.go b/types/query/pagination_test.go index 3daa5ba09427..7893ef78d354 100644 --- a/types/query/pagination_test.go +++ b/types/query/pagination_test.go @@ -121,9 +121,12 @@ func (s *paginationTestSuite) TestPagination() { s.accountKeeper.SetAccount(s.ctx, acc1) s.Require().NoError(testutil.FundAccount(s.ctx, s.bankKeeper, addr1, balances)) + addr1Str, err := s.accountKeeper.AddressCodec().BytesToString(addr1) + s.Require().NoError(err) + s.T().Log("verify empty page request results a max of defaultLimit records and counts total records") pageReq := &query.PageRequest{} - request := types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request := types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err := queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Pagination.Total, uint64(numBalances)) @@ -132,7 +135,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify page request with limit > defaultLimit, returns less or equal to `limit` records") pageReq = &query.PageRequest{Limit: overLimit} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Pagination.Total, uint64(0)) @@ -141,7 +144,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with custom limit and countTotal true") pageReq = &query.PageRequest{Limit: underLimit, CountTotal: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), underLimit) @@ -150,7 +153,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with custom limit and countTotal false") pageReq = &query.PageRequest{Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), defaultLimit) @@ -159,7 +162,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with custom limit, key and countTotal false") pageReq = &query.PageRequest{Key: res.Pagination.NextKey, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), defaultLimit) @@ -168,7 +171,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate for last page, results in records less than max limit") pageReq = &query.PageRequest{Key: res.Pagination.NextKey, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().LessOrEqual(res.Balances.Len(), defaultLimit) @@ -178,7 +181,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with offset and limit") pageReq = &query.PageRequest{Offset: 200, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().LessOrEqual(res.Balances.Len(), defaultLimit) @@ -188,7 +191,7 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with offset and limit") pageReq = &query.PageRequest{Offset: 100, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().LessOrEqual(res.Balances.Len(), defaultLimit) @@ -197,14 +200,14 @@ func (s *paginationTestSuite) TestPagination() { s.T().Log("verify paginate with offset and key - error") pageReq = &query.PageRequest{Key: res.Pagination.NextKey, Offset: 100, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) _, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().Error(err) s.Require().Equal("rpc error: code = InvalidArgument desc = paginate: invalid request, either offset or key is expected, got both", err.Error()) s.T().Log("verify paginate with offset greater than total results") pageReq = &query.PageRequest{Offset: 300, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().LessOrEqual(res.Balances.Len(), 0) @@ -229,9 +232,12 @@ func (s *paginationTestSuite) TestReversePagination() { s.accountKeeper.SetAccount(s.ctx, acc1) s.Require().NoError(testutil.FundAccount(s.ctx, s.bankKeeper, addr1, balances)) + addr1Str, err := s.accountKeeper.AddressCodec().BytesToString(addr1) + s.Require().NoError(err) + s.T().Log("verify paginate with custom limit and countTotal, Reverse false") pageReq := &query.PageRequest{Limit: 2, CountTotal: true, Reverse: true, Key: nil} - request := types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request := types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res1, err := queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(2, res1.Balances.Len()) @@ -239,7 +245,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with custom limit and countTotal, Reverse false") pageReq = &query.PageRequest{Limit: 150} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res1, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res1.Balances.Len(), 150) @@ -248,7 +254,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with custom limit, key and Reverse true") pageReq = &query.PageRequest{Limit: defaultLimit, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err := queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), defaultLimit) @@ -257,7 +263,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with custom limit, key and Reverse true") pageReq = &query.PageRequest{Offset: 100, Limit: defaultLimit, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), defaultLimit) @@ -266,7 +272,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate for last page, Reverse true") pageReq = &query.PageRequest{Offset: 200, Limit: defaultLimit, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), lastPageRecords) @@ -275,7 +281,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify page request with limit > defaultLimit, returns less or equal to `limit` records") pageReq = &query.PageRequest{Limit: overLimit, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Pagination.Total, uint64(0)) @@ -284,7 +290,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with custom limit, key, countTotal false and Reverse true") pageReq = &query.PageRequest{Key: res1.Pagination.NextKey, Limit: 50, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), 50) @@ -296,7 +302,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with custom limit, key, countTotal false and Reverse true") pageReq = &query.PageRequest{Key: res.Pagination.NextKey, Limit: 50, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), 50) @@ -308,7 +314,7 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate for last page Reverse true") pageReq = &query.PageRequest{Key: res.Pagination.NextKey, Limit: defaultLimit, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().Equal(res.Balances.Len(), 51) @@ -320,14 +326,14 @@ func (s *paginationTestSuite) TestReversePagination() { s.T().Log("verify paginate with offset and key - error") pageReq = &query.PageRequest{Key: res1.Pagination.NextKey, Offset: 100, Limit: defaultLimit, CountTotal: false} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) _, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().Error(err) s.Require().Equal("rpc error: code = InvalidArgument desc = paginate: invalid request, either offset or key is expected, got both", err.Error()) s.T().Log("verify paginate with offset greater than total results") pageReq = &query.PageRequest{Offset: 300, Limit: defaultLimit, CountTotal: false, Reverse: true} - request = types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request = types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), request) s.Require().NoError(err) s.Require().LessOrEqual(res.Balances.Len(), 0) @@ -350,9 +356,13 @@ func (s *paginationTestSuite) TestPaginate() { if err != nil { // should return no error fmt.Println(err) } + + addr1Str, err := s.accountKeeper.AddressCodec().BytesToString(addr1) + s.Require().NoError(err) + // Paginate example pageReq := &query.PageRequest{Key: nil, Limit: 1, CountTotal: true} - request := types.NewQueryAllBalancesRequest(addr1, pageReq, false) + request := types.NewQueryAllBalancesRequest(addr1Str, pageReq, false) balResult := sdk.NewCoins() authStore := s.ctx.KVStore(s.app.UnsafeFindStoreKey(types.StoreKey)) balancesStore := prefix.NewStore(authStore, types.BalancesPrefix) diff --git a/x/accounts/defaults/lockup/lockup.go b/x/accounts/defaults/lockup/lockup.go index 6917f2407b5d..c3daa2eb48f7 100644 --- a/x/accounts/defaults/lockup/lockup.go +++ b/x/accounts/defaults/lockup/lockup.go @@ -460,7 +460,7 @@ func (bva *BaseLockup) TrackUndelegation(ctx context.Context, amount sdk.Coins) func (bva BaseLockup) getBalance(ctx context.Context, sender, denom string) (*sdk.Coin, error) { // Query account balance for the sent denom - balanceQueryReq := banktypes.NewQueryBalanceRequest(sdk.AccAddress(sender), denom) + balanceQueryReq := banktypes.NewQueryBalanceRequest(sender, denom) resp, err := accountstd.QueryModule[banktypes.QueryBalanceResponse](ctx, balanceQueryReq) if err != nil { return nil, err diff --git a/x/authz/client/cli/tx.go b/x/authz/client/cli/tx.go index 904b210d88f6..d065c57cc288 100644 --- a/x/authz/client/cli/tx.go +++ b/x/authz/client/cli/tx.go @@ -159,7 +159,7 @@ Examples: return err } - authorization = bank.NewSendAuthorization(spendLimit, allowed) + authorization = bank.NewSendAuthorization(spendLimit, allowed, clientCtx.AddressCodec) case "generic": msgType, err := cmd.Flags().GetString(FlagMsgType) diff --git a/x/authz/keeper/keeper_test.go b/x/authz/keeper/keeper_test.go index c790b6fde446..23d25f2af98b 100644 --- a/x/authz/keeper/keeper_test.go +++ b/x/authz/keeper/keeper_test.go @@ -147,7 +147,7 @@ func (s *TestSuite) TestKeeperIter() { granteeAddr := addrs[1] granter2Addr := addrs[2] e := ctx.HeaderInfo().Time.AddDate(1, 0, 0) - sendAuthz := banktypes.NewSendAuthorization(coins100, nil) + sendAuthz := banktypes.NewSendAuthorization(coins100, nil, s.accountKeeper.AddressCodec()) err := s.authzKeeper.SaveGrant(ctx, granteeAddr, granterAddr, sendAuthz, &e) s.Require().NoError(err) @@ -175,7 +175,7 @@ func (s *TestSuite) TestDispatchAction() { s.Require().NoError(err) recipientStrAddr, err := s.accountKeeper.AddressCodec().BytesToString(addrs[2]) s.Require().NoError(err) - a := banktypes.NewSendAuthorization(coins100, nil) + a := banktypes.NewSendAuthorization(coins100, nil, s.accountKeeper.AddressCodec()) testCases := []struct { name string @@ -422,7 +422,7 @@ func (s *TestSuite) TestGetAuthorization() { genAuthMulti := authz.NewGenericAuthorization(sdk.MsgTypeURL(&banktypes.MsgMultiSend{})) genAuthSend := authz.NewGenericAuthorization(sdk.MsgTypeURL(&banktypes.MsgSend{})) - sendAuth := banktypes.NewSendAuthorization(coins10, nil) + sendAuth := banktypes.NewSendAuthorization(coins10, nil, s.accountKeeper.AddressCodec()) start := s.ctx.HeaderInfo().Time expired := start.Add(time.Duration(1) * time.Second) diff --git a/x/authz/keeper/msg_server_test.go b/x/authz/keeper/msg_server_test.go index 6fb013bb7fba..5e4a25279b87 100644 --- a/x/authz/keeper/msg_server_test.go +++ b/x/authz/keeper/msg_server_test.go @@ -50,7 +50,7 @@ func (suite *TestSuite) TestGrant() { { name: "identical grantee and granter", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granteeStrAddr, @@ -64,7 +64,7 @@ func (suite *TestSuite) TestGrant() { { name: "invalid granter", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: "invalid", @@ -78,7 +78,7 @@ func (suite *TestSuite) TestGrant() { { name: "invalid grantee", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granterStrAddr, @@ -107,7 +107,7 @@ func (suite *TestSuite) TestGrant() { name: "invalid grant, past time", malleate: func() *authz.MsgGrant { pTime := curBlockTime.Add(-time.Hour) - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneHour) // we only need the authorization + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneHour) // we only need the authorization suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granterStrAddr, @@ -129,7 +129,7 @@ func (suite *TestSuite) TestGrant() { acc := authtypes.NewBaseAccountWithAddress(newAcc) suite.accountKeeper.EXPECT().NewAccountWithAddress(gomock.Any(), newAcc).Return(acc).AnyTimes() - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) addr, err := suite.accountKeeper.AddressCodec().BytesToString(newAcc) @@ -145,7 +145,7 @@ func (suite *TestSuite) TestGrant() { { name: "valid grant", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granterStrAddr, @@ -157,7 +157,7 @@ func (suite *TestSuite) TestGrant() { { name: "valid grant, same grantee, granter pair but different msgType", malleate: func() *authz.MsgGrant { - g, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), &oneHour) + g, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &oneHour) suite.Require().NoError(err) _, err = suite.msgSrvr.Grant(suite.ctx, &authz.MsgGrant{ Granter: granterStrAddr, @@ -178,7 +178,7 @@ func (suite *TestSuite) TestGrant() { { name: "valid grant with allow list", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, []sdk.AccAddress{granter}), &oneYear) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, []sdk.AccAddress{granter}, suite.accountKeeper.AddressCodec()), &oneYear) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granterStrAddr, @@ -190,7 +190,7 @@ func (suite *TestSuite) TestGrant() { { name: "valid grant with nil expiration time", malleate: func() *authz.MsgGrant { - grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil), nil) + grant, err := authz.NewGrant(curBlockTime, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), nil) suite.Require().NoError(err) return &authz.MsgGrant{ Granter: granterStrAddr, @@ -396,7 +396,7 @@ func (suite *TestSuite) TestPruneExpiredGrants() { timeNow := suite.ctx.BlockTime() expiration := timeNow.Add(time.Hour) coins := sdk.NewCoins(sdk.NewCoin("steak", sdkmath.NewInt(10))) - grant, err := authz.NewGrant(timeNow, banktypes.NewSendAuthorization(coins, nil), &expiration) + grant, err := authz.NewGrant(timeNow, banktypes.NewSendAuthorization(coins, nil, suite.accountKeeper.AddressCodec()), &expiration) suite.Require().NoError(err) _, err = suite.msgSrvr.Grant(suite.ctx, &authz.MsgGrant{ diff --git a/x/authz/migrations/v2/store_test.go b/x/authz/migrations/v2/store_test.go index 4440ae5b4fbe..fe328faae8e8 100644 --- a/x/authz/migrations/v2/store_test.go +++ b/x/authz/migrations/v2/store_test.go @@ -42,7 +42,7 @@ func TestMigration(t *testing.T) { blockTime := ctx.HeaderInfo().Time oneDay := blockTime.AddDate(0, 0, 1) oneYear := blockTime.AddDate(1, 0, 0) - sendAuthz := banktypes.NewSendAuthorization(coins100, nil) + sendAuthz := banktypes.NewSendAuthorization(coins100, nil, codectestutil.CodecOptions{}.GetAddressCodec()) grants := []struct { granter sdk.AccAddress diff --git a/x/authz/module/abci_test.go b/x/authz/module/abci_test.go index b8765e1fbe0d..53f0701f287e 100644 --- a/x/authz/module/abci_test.go +++ b/x/authz/module/abci_test.go @@ -54,7 +54,7 @@ func TestExpiredGrantsQueue(t *testing.T) { expiration := ctx.HeaderInfo().Time.AddDate(0, 1, 0) expiration2 := expiration.AddDate(1, 0, 0) smallCoins := sdk.NewCoins(sdk.NewInt64Coin("stake", 10)) - sendAuthz := banktypes.NewSendAuthorization(smallCoins, nil) + sendAuthz := banktypes.NewSendAuthorization(smallCoins, nil, codectestutil.CodecOptions{}.GetAddressCodec()) ctrl := gomock.NewController(t) accountKeeper := authztestutil.NewMockAccountKeeper(ctrl) diff --git a/x/authz/msgs_test.go b/x/authz/msgs_test.go index 194f93d417f3..8675683b5526 100644 --- a/x/authz/msgs_test.go +++ b/x/authz/msgs_test.go @@ -69,7 +69,7 @@ func TestAminoJSON(t *testing.T) { require.NoError(t, err) grant, err := authz.NewGrant(blockTime, authz.NewGenericAuthorization(typeURL), &expiresAt) require.NoError(t, err) - sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewCoin("stake", sdkmath.NewInt(1000))), nil) + sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewCoin("stake", sdkmath.NewInt(1000))), nil, codectestutil.CodecOptions{}.GetValidatorCodec()) sendGrant, err := authz.NewGrant(blockTime, sendAuthz, &expiresAt) require.NoError(t, err) valAddr, err := valAddressCodec.StringToBytes("cosmosvaloper1xcy3els9ua75kdm783c3qu0rfa2eples6eavqq") diff --git a/x/authz/simulation/decoder_test.go b/x/authz/simulation/decoder_test.go index dbeee176732a..ff14fd76e316 100644 --- a/x/authz/simulation/decoder_test.go +++ b/x/authz/simulation/decoder_test.go @@ -27,7 +27,7 @@ func TestDecodeStore(t *testing.T) { now := time.Now().UTC() e := now.Add(1) - sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewInt64Coin("foo", 123)), nil) + sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewInt64Coin("foo", 123)), nil, codectestutil.CodecOptions{}.GetAddressCodec()) grant, _ := authz.NewGrant(now, sendAuthz, &e) grantBz, err := encCfg.Codec.Marshal(&grant) require.NoError(t, err) diff --git a/x/authz/simulation/genesis.go b/x/authz/simulation/genesis.go index 073bdffabc8e..59b2d299a46c 100644 --- a/x/authz/simulation/genesis.go +++ b/x/authz/simulation/genesis.go @@ -32,7 +32,7 @@ func genGrant(r *rand.Rand, accounts []simtypes.Account, genT time.Time, cdc add authorizations[i] = authz.GrantAuthorization{ Granter: granterAddr, Grantee: granteeAddr, - Authorization: generateRandomGrant(r), + Authorization: generateRandomGrant(r, cdc), Expiration: expiration, } } @@ -40,9 +40,9 @@ func genGrant(r *rand.Rand, accounts []simtypes.Account, genT time.Time, cdc add return authorizations } -func generateRandomGrant(r *rand.Rand) *codectypes.Any { +func generateRandomGrant(r *rand.Rand, addressCodec address.Codec) *codectypes.Any { authorizations := make([]*codectypes.Any, 2) - sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewCoin("stake", sdkmath.NewInt(1000))), nil) + sendAuthz := banktypes.NewSendAuthorization(sdk.NewCoins(sdk.NewCoin("stake", sdkmath.NewInt(1000))), nil, addressCodec) authorizations[0] = newAnyAuthorization(sendAuthz) authorizations[1] = newAnyAuthorization(authz.NewGenericAuthorization(sdk.MsgTypeURL(&v1.MsgSubmitProposal{}))) diff --git a/x/authz/simulation/operations.go b/x/authz/simulation/operations.go index 657383d37b5e..9e25d14aa6ea 100644 --- a/x/authz/simulation/operations.go +++ b/x/authz/simulation/operations.go @@ -4,6 +4,7 @@ import ( "math/rand" "time" + "cosmossdk.io/core/address" "cosmossdk.io/x/authz" "cosmossdk.io/x/authz/keeper" banktype "cosmossdk.io/x/bank/types" @@ -121,7 +122,7 @@ func SimulateMsgGrant( if !t1.Before(ctx.HeaderInfo().Time) { expiration = &t1 } - randomAuthz := generateRandomAuthorization(r, spendLimit) + randomAuthz := generateRandomAuthorization(r, spendLimit, ak.AddressCodec()) granterAddr, err := ak.AddressCodec().BytesToString(granter.Address) if err != nil { @@ -158,9 +159,9 @@ func SimulateMsgGrant( } } -func generateRandomAuthorization(r *rand.Rand, spendLimit sdk.Coins) authz.Authorization { +func generateRandomAuthorization(r *rand.Rand, spendLimit sdk.Coins, addressCodec address.Codec) authz.Authorization { authorizations := make([]authz.Authorization, 2) - sendAuthz := banktype.NewSendAuthorization(spendLimit, nil) + sendAuthz := banktype.NewSendAuthorization(spendLimit, nil, addressCodec) authorizations[0] = sendAuthz authorizations[1] = authz.NewGenericAuthorization(sdk.MsgTypeURL(&banktype.MsgSend{})) diff --git a/x/bank/CHANGELOG.md b/x/bank/CHANGELOG.md index 3d1944d2c446..234561bd9912 100644 --- a/x/bank/CHANGELOG.md +++ b/x/bank/CHANGELOG.md @@ -35,6 +35,11 @@ Ref: https://keepachangelog.com/en/1.0.0/ ### API Breaking Changes +* [#19954](https://github.com/cosmos/cosmos-sdk/pull/19954) Removal of the Address.String() method and related changes: + * Changed `NewInput`, `NewOutput`, `NewQueryBalanceRequest`, `NewQueryAllBalancesRequest`, `NewQuerySpendableBalancesRequest` to accept a string instead of an `AccAddress`. + * Added an address codec as an argument to `NewSendAuthorization`. + * Added an address codec as an argument to `SanitizeGenesisBalances` which also returns an error. + * (simulation) `RandomGenesisBalances` also returns an error. * [#17569](https://github.com/cosmos/cosmos-sdk/pull/17569) `BurnCoins` takes an address instead of a module name * [#19477](https://github.com/cosmos/cosmos-sdk/pull/19477) `appmodule.Environment` is passed to bank `NewKeeper` * [#19627](https://github.com/cosmos/cosmos-sdk/pull/19627) The genesis api has been updated to match `appmodule.HasGenesis`. diff --git a/x/bank/client/cli/tx.go b/x/bank/client/cli/tx.go index 02f68cd6eb80..a480d3b1a2cc 100644 --- a/x/bank/client/cli/tx.go +++ b/x/bank/client/cli/tx.go @@ -81,12 +81,12 @@ When using '--dry-run' a key name cannot be used, only a bech32 address.`, var output []types.Output for _, arg := range args[1 : len(args)-1] { - toAddr, err := clientCtx.AddressCodec.StringToBytes(arg) + _, err = clientCtx.AddressCodec.StringToBytes(arg) if err != nil { return err } - output = append(output, types.NewOutput(toAddr, sendCoins)) + output = append(output, types.NewOutput(arg, sendCoins)) } // amount to be send from the from address @@ -99,7 +99,12 @@ When using '--dry-run' a key name cannot be used, only a bech32 address.`, amount = coins.MulInt(totalAddrs) } - msg := types.NewMsgMultiSend(types.NewInput(clientCtx.FromAddress, amount), output) + fromAddr, err := clientCtx.AddressCodec.BytesToString(clientCtx.FromAddress) + if err != nil { + return err + } + + msg := types.NewMsgMultiSend(types.NewInput(fromAddr, amount), output) return tx.GenerateOrBroadcastTxCLI(clientCtx, cmd.Flags(), msg) }, diff --git a/x/bank/keeper/collections_test.go b/x/bank/keeper/collections_test.go index 8e77b664f395..a5c37ffa63b0 100644 --- a/x/bank/keeper/collections_test.go +++ b/x/bank/keeper/collections_test.go @@ -38,12 +38,18 @@ func TestBankStateCompatibility(t *testing.T) { authKeeper := banktestutil.NewMockAccountKeeper(ctrl) authKeeper.EXPECT().AddressCodec().Return(address.NewBech32Codec("cosmos")).AnyTimes() + ac := codectestutil.CodecOptions{}.GetAddressCodec() + addr, err := ac.BytesToString(accAddrs[4]) + require.NoError(t, err) + authority, err := ac.BytesToString(authtypes.NewModuleAddress(banktypes.GovModuleName)) + require.NoError(t, err) + k := keeper.NewBaseKeeper( env, encCfg.Codec, authKeeper, - map[string]bool{accAddrs[4].String(): true}, - authtypes.NewModuleAddress(banktypes.GovModuleName).String(), + map[string]bool{addr: true}, + authority, ) // test we can decode balances without problems diff --git a/x/bank/keeper/genesis.go b/x/bank/keeper/genesis.go index dd094055c79a..3f7ec88c1e5f 100644 --- a/x/bank/keeper/genesis.go +++ b/x/bank/keeper/genesis.go @@ -13,7 +13,8 @@ import ( // InitGenesis initializes the bank module's state from a given genesis state. func (k BaseKeeper) InitGenesis(ctx context.Context, genState *types.GenesisState) error { - if err := k.SetParams(ctx, genState.Params); err != nil { + var err error + if err = k.SetParams(ctx, genState.Params); err != nil { return err } @@ -22,7 +23,10 @@ func (k BaseKeeper) InitGenesis(ctx context.Context, genState *types.GenesisStat } totalSupplyMap := sdk.NewMapCoins(sdk.Coins{}) - genState.Balances = types.SanitizeGenesisBalances(genState.Balances) + genState.Balances, err = types.SanitizeGenesisBalances(genState.Balances, k.ak.AddressCodec()) + if err != nil { + return err + } for _, balance := range genState.Balances { addr := balance.GetAddress() diff --git a/x/bank/keeper/genesis_test.go b/x/bank/keeper/genesis_test.go index 5462ca52802f..0432d1b0fd94 100644 --- a/x/bank/keeper/genesis_test.go +++ b/x/bank/keeper/genesis_test.go @@ -4,6 +4,7 @@ import ( sdkmath "cosmossdk.io/math" "cosmossdk.io/x/bank/types" + codectestutil "github.com/cosmos/cosmos-sdk/codec/testutil" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/query" ) @@ -21,7 +22,7 @@ func (suite *KeeperTestSuite) TestExportGenesis() { for i := range []int{1, 2} { suite.bankKeeper.SetDenomMetaData(ctx, expectedMetadata[i]) - accAddr, err1 := sdk.AccAddressFromBech32(expectedBalances[i].Address) + accAddr, err1 := suite.authKeeper.AddressCodec().StringToBytes(expectedBalances[i].Address) if err1 != nil { panic(err1) } @@ -49,17 +50,25 @@ func (suite *KeeperTestSuite) TestExportGenesis() { } func (suite *KeeperTestSuite) getTestBalancesAndSupply() ([]types.Balance, sdk.Coins) { - addr2, _ := sdk.AccAddressFromBech32("cosmos1f9xjhxm0plzrh9cskf4qee4pc2xwp0n0556gh0") - addr1, _ := sdk.AccAddressFromBech32("cosmos1t5u0jfg3ljsjrh2m9e47d4ny2hea7eehxrzdgd") + ac := codectestutil.CodecOptions{}.GetAddressCodec() + addr2, err := suite.authKeeper.AddressCodec().StringToBytes("cosmos1f9xjhxm0plzrh9cskf4qee4pc2xwp0n0556gh0") + suite.Require().NoError(err) + addr1, _ := suite.authKeeper.AddressCodec().StringToBytes("cosmos1t5u0jfg3ljsjrh2m9e47d4ny2hea7eehxrzdgd") + suite.Require().NoError(err) addr1Balance := sdk.Coins{sdk.NewInt64Coin("testcoin3", 10)} addr2Balance := sdk.Coins{sdk.NewInt64Coin("testcoin1", 32), sdk.NewInt64Coin("testcoin2", 34)} totalSupply := addr1Balance totalSupply = totalSupply.Add(addr2Balance...) + addr2Str, err := ac.BytesToString(addr2) + suite.Require().NoError(err) + addr1Str, err := ac.BytesToString(addr1) + suite.Require().NoError(err) + return []types.Balance{ - {Address: addr2.String(), Coins: addr2Balance}, - {Address: addr1.String(), Coins: addr1Balance}, + {Address: addr2Str, Coins: addr2Balance}, + {Address: addr1Str, Coins: addr1Balance}, }, totalSupply } diff --git a/x/bank/keeper/grpc_query.go b/x/bank/keeper/grpc_query.go index 22bbcdac580e..b24fc91434c9 100644 --- a/x/bank/keeper/grpc_query.go +++ b/x/bank/keeper/grpc_query.go @@ -292,7 +292,11 @@ func (k BaseKeeper) DenomOwners( if err != nil { return nil, err } - return &types.DenomOwner{Address: key.K2().String(), Balance: sdk.NewCoin(req.Denom, amt)}, nil + addr, err := k.ak.AddressCodec().BytesToString(key.K2()) + if err != nil { + return nil, err + } + return &types.DenomOwner{Address: addr, Balance: sdk.NewCoin(req.Denom, amt)}, nil }, query.WithCollectionPaginationPairPrefix[string, sdk.AccAddress](req.Denom), ) diff --git a/x/bank/keeper/grpc_query_test.go b/x/bank/keeper/grpc_query_test.go index a33d91903573..a5b4e352c88c 100644 --- a/x/bank/keeper/grpc_query_test.go +++ b/x/bank/keeper/grpc_query_test.go @@ -11,6 +11,7 @@ import ( "cosmossdk.io/x/bank/testutil" "cosmossdk.io/x/bank/types" + codectestutil "github.com/cosmos/cosmos-sdk/codec/testutil" "github.com/cosmos/cosmos-sdk/testutil/testdata" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/query" @@ -20,6 +21,9 @@ func (suite *KeeperTestSuite) TestQueryBalance() { ctx, queryClient := suite.ctx, suite.queryClient _, _, addr := testdata.KeyTestPubAddr() + addrStr, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr) + suite.Require().NoError(err) + origCoins := sdk.NewCoins(newBarCoin(30)) suite.mockFundAccount(addr) suite.Require().NoError(testutil.FundAccount(ctx, suite.bankKeeper, addr, origCoins)) @@ -38,13 +42,13 @@ func (suite *KeeperTestSuite) TestQueryBalance() { }, { "invalid denom", - types.NewQueryBalanceRequest(addr, "0000"), + types.NewQueryBalanceRequest(addrStr, "0000"), "invalid denom", nil, }, { "empty address", - types.NewQueryBalanceRequest(sdk.AccAddress{}, barDenom), + types.NewQueryBalanceRequest("", barDenom), "empty address string is not allowed", nil, }, @@ -56,13 +60,13 @@ func (suite *KeeperTestSuite) TestQueryBalance() { }, { "query missing denom", - &types.QueryBalanceRequest{Address: addr.String()}, + &types.QueryBalanceRequest{Address: addrStr}, "invalid denom", nil, }, { "valid query empty result", - types.NewQueryBalanceRequest(addr, fooDenom), + types.NewQueryBalanceRequest(addrStr, fooDenom), "", func(res *types.QueryBalanceResponse) { suite.True(res.Balance.IsZero()) @@ -70,7 +74,7 @@ func (suite *KeeperTestSuite) TestQueryBalance() { }, { "valid query", - types.NewQueryBalanceRequest(addr, barDenom), + types.NewQueryBalanceRequest(addrStr, barDenom), "", func(res *types.QueryBalanceResponse) { suite.True(res.Balance.IsEqual(newBarCoin(30))) @@ -103,12 +107,15 @@ func (suite *KeeperTestSuite) TestQueryAllBalances() { _, err := queryClient.AllBalances(gocontext.Background(), &types.QueryAllBalancesRequest{}) suite.Require().Error(err) + addrStr, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr) + suite.Require().NoError(err) + pageReq := &query.PageRequest{ Key: nil, Limit: 1, CountTotal: false, } - req := types.NewQueryAllBalancesRequest(addr, pageReq, false) + req := types.NewQueryAllBalancesRequest(addrStr, pageReq, false) res, err := queryClient.AllBalances(gocontext.Background(), req) suite.Require().NoError(err) suite.Require().NotNil(res) @@ -137,7 +144,7 @@ func (suite *KeeperTestSuite) TestQueryAllBalances() { Limit: 1, CountTotal: true, } - req = types.NewQueryAllBalancesRequest(addr, pageReq, false) + req = types.NewQueryAllBalancesRequest(addrStr, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), req) suite.Require().NoError(err) suite.Equal(res.Balances.Len(), 1) @@ -151,7 +158,7 @@ func (suite *KeeperTestSuite) TestQueryAllBalances() { Limit: 1, CountTotal: true, } - req = types.NewQueryAllBalancesRequest(addr, pageReq, false) + req = types.NewQueryAllBalancesRequest(addrStr, pageReq, false) res, err = queryClient.AllBalances(gocontext.Background(), req) suite.Require().NoError(err) suite.Equal(res.Balances.Len(), 1) @@ -163,7 +170,7 @@ func (suite *KeeperTestSuite) TestQueryAllBalances() { Limit: 1, CountTotal: true, } - req = types.NewQueryAllBalancesRequest(addr, pageReq, true) + req = types.NewQueryAllBalancesRequest(addrStr, pageReq, true) res, err = queryClient.AllBalances(gocontext.Background(), req) suite.Require().NoError(err) suite.Equal(res.Balances.Len(), 1) @@ -173,12 +180,14 @@ func (suite *KeeperTestSuite) TestQueryAllBalances() { func (suite *KeeperTestSuite) TestSpendableBalances() { _, _, addr := testdata.KeyTestPubAddr() + addrStr, err := codectestutil.CodecOptions{}.GetAddressCodec().BytesToString(addr) + suite.Require().NoError(err) ctx := sdk.UnwrapSDKContext(suite.ctx) ctx = ctx.WithHeaderInfo(header.Info{Time: time.Now()}) queryClient := suite.mockQueryClient(ctx) - _, err := queryClient.SpendableBalances(ctx, &types.QuerySpendableBalancesRequest{}) + _, err = queryClient.SpendableBalances(ctx, &types.QuerySpendableBalancesRequest{}) suite.Require().Error(err) pageReq := &query.PageRequest{ @@ -186,7 +195,7 @@ func (suite *KeeperTestSuite) TestSpendableBalances() { Limit: 2, CountTotal: false, } - req := types.NewQuerySpendableBalancesRequest(addr, pageReq) + req := types.NewQuerySpendableBalancesRequest(addrStr, pageReq) acc := authtypes.NewBaseAccountWithAddress(addr) suite.mockSpendableCoins(ctx, acc) diff --git a/x/bank/keeper/keeper_test.go b/x/bank/keeper/keeper_test.go index e44423e352ff..86043fc81074 100644 --- a/x/bank/keeper/keeper_test.go +++ b/x/bank/keeper/keeper_test.go @@ -134,6 +134,12 @@ func (suite *KeeperTestSuite) SetupTest() { env := runtime.NewEnvironment(runtime.NewKVStoreService(key), log.NewNopLogger()) + ac := codectestutil.CodecOptions{}.GetAddressCodec() + addr, err := ac.BytesToString(accAddrs[4]) + suite.Require().NoError(err) + authority, err := ac.BytesToString(authtypes.NewModuleAddress(banktypes.GovModuleName)) + suite.Require().NoError(err) + // gomock initializations ctrl := gomock.NewController(suite.T()) authKeeper := banktestutil.NewMockAccountKeeper(ctrl) @@ -144,8 +150,8 @@ func (suite *KeeperTestSuite) SetupTest() { env, encCfg.Codec, suite.authKeeper, - map[string]bool{accAddrs[4].String(): true}, - authtypes.NewModuleAddress(banktypes.GovModuleName).String(), + map[string]bool{addr: true}, + authority, ) banktypes.RegisterInterfaces(encCfg.InterfaceRegistry) @@ -310,11 +316,15 @@ func (suite *KeeperTestSuite) TestGetAuthority() { authority, ) } + govAddr, err := suite.authKeeper.AddressCodec().BytesToString(authtypes.NewModuleAddress(banktypes.GovModuleName)) + suite.Require().NoError(err) + modAddr, err := suite.authKeeper.AddressCodec().BytesToString(authtypes.NewModuleAddress(banktypes.MintModuleName)) + suite.Require().NoError(err) tests := map[string]string{ "some random account": "cosmos139f7kncmglres2nf3h4hc4tade85ekfr8sulz5", - "gov module account": authtypes.NewModuleAddress(banktypes.GovModuleName).String(), - "another module account": authtypes.NewModuleAddress(banktypes.MintModuleName).String(), + "gov module account": govAddr, + "another module account": modAddr, } for name, expected := range tests { @@ -630,12 +640,17 @@ func (suite *KeeperTestSuite) TestInputOutputNewAccount() { require.Empty(suite.bankKeeper.GetAllBalances(ctx, accAddrs[1])) + acc0StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[0]) + suite.Require().NoError(err) + acc1StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[1]) + suite.Require().NoError(err) + suite.mockInputOutputCoins([]sdk.AccountI{authtypes.NewBaseAccountWithAddress(accAddrs[0])}, []sdk.AccAddress{accAddrs[1]}) input := banktypes.Input{ - Address: accAddrs[0].String(), Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10)), + Address: acc0StrAddr, Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10)), } outputs := []banktypes.Output{ - {Address: accAddrs[1].String(), Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, + {Address: acc1StrAddr, Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, } require.NoError(suite.bankKeeper.InputOutputCoins(ctx, input, outputs)) @@ -651,12 +666,20 @@ func (suite *KeeperTestSuite) TestInputOutputCoins() { balances := sdk.NewCoins(newFooCoin(90), newBarCoin(30)) acc0 := authtypes.NewBaseAccountWithAddress(accAddrs[0]) + + acc0StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[0]) + suite.Require().NoError(err) + acc1StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[1]) + suite.Require().NoError(err) + acc2StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[2]) + suite.Require().NoError(err) + input := banktypes.Input{ - Address: accAddrs[0].String(), Coins: sdk.NewCoins(newFooCoin(60), newBarCoin(20)), + Address: acc0StrAddr, Coins: sdk.NewCoins(newFooCoin(60), newBarCoin(20)), } outputs := []banktypes.Output{ - {Address: accAddrs[1].String(), Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, - {Address: accAddrs[2].String(), Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, + {Address: acc1StrAddr, Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, + {Address: acc2StrAddr, Coins: sdk.NewCoins(newFooCoin(30), newBarCoin(10))}, } require.Error(suite.bankKeeper.InputOutputCoins(ctx, input, []banktypes.Output{})) @@ -668,12 +691,12 @@ func (suite *KeeperTestSuite) TestInputOutputCoins() { require.NoError(banktestutil.FundAccount(ctx, suite.bankKeeper, accAddrs[0], balances)) insufficientInput := banktypes.Input{ - Address: accAddrs[0].String(), + Address: acc0StrAddr, Coins: sdk.NewCoins(newFooCoin(300), newBarCoin(100)), } insufficientOutputs := []banktypes.Output{ - {Address: accAddrs[1].String(), Coins: sdk.NewCoins(newFooCoin(300), newBarCoin(100))}, - {Address: accAddrs[2].String(), Coins: sdk.NewCoins(newFooCoin(300), newBarCoin(100))}, + {Address: acc1StrAddr, Coins: sdk.NewCoins(newFooCoin(300), newBarCoin(100))}, + {Address: acc2StrAddr, Coins: sdk.NewCoins(newFooCoin(300), newBarCoin(100))}, } require.Error(suite.bankKeeper.InputOutputCoins(ctx, insufficientInput, insufficientOutputs)) @@ -756,10 +779,16 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { setupCtx := suite.ctx balances := sdk.NewCoins(newFooCoin(1000), newBarCoin(500)) fromAddr := accAddrs[0] + fromStrAddr, err := suite.authKeeper.AddressCodec().BytesToString(fromAddr) + suite.Require().NoError(err) fromAcc := authtypes.NewBaseAccountWithAddress(fromAddr) inputAccs := []sdk.AccountI{fromAcc} toAddr1 := accAddrs[1] + toAddr1Str, err := suite.authKeeper.AddressCodec().BytesToString(toAddr1) + suite.Require().NoError(err) toAddr2 := accAddrs[2] + toAddr2Str, err := suite.authKeeper.AddressCodec().BytesToString(toAddr2) + suite.Require().NoError(err) suite.mockFundAccount(accAddrs[0]) suite.Require().NoError(banktestutil.FundAccount(setupCtx, suite.bankKeeper, accAddrs[0], balances)) @@ -778,7 +807,7 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { name: "nil restriction", fn: nil, inputCoins: sdk.NewCoins(newFooCoin(5)), - outputs: []banktypes.Output{{Address: toAddr1.String(), Coins: sdk.NewCoins(newFooCoin(5))}}, + outputs: []banktypes.Output{{Address: toAddr1Str, Coins: sdk.NewCoins(newFooCoin(5))}}, outputAddrs: []sdk.AccAddress{toAddr1}, expBals: expBals{ from: sdk.NewCoins(newFooCoin(995), newBarCoin(500)), @@ -790,7 +819,7 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { name: "passthrough restriction single output", fn: restrictionPassthrough(), inputCoins: sdk.NewCoins(newFooCoin(10)), - outputs: []banktypes.Output{{Address: toAddr1.String(), Coins: sdk.NewCoins(newFooCoin(10))}}, + outputs: []banktypes.Output{{Address: toAddr1Str, Coins: sdk.NewCoins(newFooCoin(10))}}, outputAddrs: []sdk.AccAddress{toAddr1}, expArgs: []*restrictionArgs{ { @@ -810,7 +839,7 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { name: "new to restriction single output", fn: restrictionNewTo(toAddr2), inputCoins: sdk.NewCoins(newFooCoin(26)), - outputs: []banktypes.Output{{Address: toAddr1.String(), Coins: sdk.NewCoins(newFooCoin(26))}}, + outputs: []banktypes.Output{{Address: toAddr1Str, Coins: sdk.NewCoins(newFooCoin(26))}}, outputAddrs: []sdk.AccAddress{toAddr2}, expArgs: []*restrictionArgs{ { @@ -830,7 +859,7 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { name: "error restriction single output", fn: restrictionError("restriction test error"), inputCoins: sdk.NewCoins(newBarCoin(88)), - outputs: []banktypes.Output{{Address: toAddr1.String(), Coins: sdk.NewCoins(newBarCoin(88))}}, + outputs: []banktypes.Output{{Address: toAddr1Str, Coins: sdk.NewCoins(newBarCoin(88))}}, outputAddrs: []sdk.AccAddress{}, expArgs: []*restrictionArgs{ { @@ -852,8 +881,8 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { fn: restrictionPassthrough(), inputCoins: sdk.NewCoins(newFooCoin(11), newBarCoin(12)), outputs: []banktypes.Output{ - {Address: toAddr1.String(), Coins: sdk.NewCoins(newFooCoin(11))}, - {Address: toAddr2.String(), Coins: sdk.NewCoins(newBarCoin(12))}, + {Address: toAddr1Str, Coins: sdk.NewCoins(newFooCoin(11))}, + {Address: toAddr2Str, Coins: sdk.NewCoins(newBarCoin(12))}, }, outputAddrs: []sdk.AccAddress{toAddr1, toAddr2}, expArgs: []*restrictionArgs{ @@ -881,8 +910,8 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { fn: restrictionError("", "second restriction error"), inputCoins: sdk.NewCoins(newFooCoin(44)), outputs: []banktypes.Output{ - {Address: toAddr1.String(), Coins: sdk.NewCoins(newFooCoin(12))}, - {Address: toAddr2.String(), Coins: sdk.NewCoins(newFooCoin(32))}, + {Address: toAddr1Str, Coins: sdk.NewCoins(newFooCoin(12))}, + {Address: toAddr2Str, Coins: sdk.NewCoins(newFooCoin(32))}, }, outputAddrs: []sdk.AccAddress{toAddr1}, expArgs: []*restrictionArgs{ @@ -911,8 +940,8 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { fn: restrictionNewTo(toAddr2, toAddr1), inputCoins: sdk.NewCoins(newBarCoin(35)), outputs: []banktypes.Output{ - {Address: toAddr1.String(), Coins: sdk.NewCoins(newBarCoin(10))}, - {Address: toAddr2.String(), Coins: sdk.NewCoins(newBarCoin(25))}, + {Address: toAddr1Str, Coins: sdk.NewCoins(newBarCoin(10))}, + {Address: toAddr2Str, Coins: sdk.NewCoins(newBarCoin(25))}, }, outputAddrs: []sdk.AccAddress{toAddr1, toAddr2}, expArgs: []*restrictionArgs{ @@ -946,7 +975,7 @@ func (suite *KeeperTestSuite) TestInputOutputCoinsWithRestrictions() { ctx := suite.ctx suite.mockInputOutputCoins(inputAccs, tc.outputAddrs) input := banktypes.Input{ - Address: fromAddr.String(), + Address: fromStrAddr, Coins: tc.inputCoins, } @@ -1331,6 +1360,12 @@ func (suite *KeeperTestSuite) TestMsgSendEvents() { require := suite.Require() acc0 := authtypes.NewBaseAccountWithAddress(accAddrs[0]) + + acc0StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[0]) + suite.Require().NoError(err) + acc1StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[1]) + suite.Require().NoError(err) + newCoins := sdk.NewCoins(sdk.NewInt64Coin(fooDenom, 50)) suite.mockFundAccount(accAddrs[0]) require.NoError(banktestutil.FundAccount(suite.ctx, suite.bankKeeper, accAddrs[0], newCoins)) @@ -1343,11 +1378,11 @@ func (suite *KeeperTestSuite) TestMsgSendEvents() { } event1.Attributes = append( event1.Attributes, - abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: accAddrs[1].String()}, + abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: acc1StrAddr}, ) event1.Attributes = append( event1.Attributes, - abci.EventAttribute{Key: banktypes.AttributeKeySender, Value: accAddrs[0].String()}, + abci.EventAttribute{Key: banktypes.AttributeKeySender, Value: acc0StrAddr}, ) event1.Attributes = append( event1.Attributes, @@ -1368,16 +1403,23 @@ func (suite *KeeperTestSuite) TestMsgMultiSendEvents() { require.NoError(suite.bankKeeper.SetParams(ctx, banktypes.DefaultParams())) + acc0StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[0]) + suite.Require().NoError(err) + acc2StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[2]) + suite.Require().NoError(err) + acc3StrAddr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[3]) + suite.Require().NoError(err) + coins := sdk.NewCoins(sdk.NewInt64Coin(fooDenom, 50), sdk.NewInt64Coin(barDenom, 100)) newCoins := sdk.NewCoins(sdk.NewInt64Coin(fooDenom, 50)) newCoins2 := sdk.NewCoins(sdk.NewInt64Coin(barDenom, 100)) input := banktypes.Input{ - Address: accAddrs[0].String(), + Address: acc0StrAddr, Coins: coins, } outputs := []banktypes.Output{ - {Address: accAddrs[2].String(), Coins: newCoins}, - {Address: accAddrs[3].String(), Coins: newCoins2}, + {Address: acc2StrAddr, Coins: newCoins}, + {Address: acc3StrAddr, Coins: newCoins2}, } suite.authKeeper.EXPECT().GetAccount(suite.ctx, accAddrs[0]).Return(acc0) @@ -1417,7 +1459,7 @@ func (suite *KeeperTestSuite) TestMsgMultiSendEvents() { } event1.Attributes = append( event1.Attributes, - abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: accAddrs[2].String()}, + abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: acc2StrAddr}, ) event1.Attributes = append( event1.Attributes, @@ -1428,7 +1470,7 @@ func (suite *KeeperTestSuite) TestMsgMultiSendEvents() { } event2.Attributes = append( event2.Attributes, - abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: accAddrs[3].String()}, + abci.EventAttribute{Key: banktypes.AttributeKeyRecipient, Value: acc3StrAddr}, ) event2.Attributes = append( event2.Attributes, @@ -1851,16 +1893,17 @@ func (suite *KeeperTestSuite) TestBalanceTrackingEvents() { case banktypes.EventTypeCoinSpent: coinsSpent, err := sdk.ParseCoinsNormalized(e.Attributes[1].Value) require.NoError(err) - spender, err := sdk.AccAddressFromBech32(e.Attributes[0].Value) + _, err = suite.authKeeper.AddressCodec().StringToBytes(e.Attributes[0].Value) require.NoError(err) - balances[spender.String()] = balances[spender.String()].Sub(coinsSpent...) + + balances[e.Attributes[0].Value] = balances[e.Attributes[0].Value].Sub(coinsSpent...) case banktypes.EventTypeCoinReceived: coinsRecv, err := sdk.ParseCoinsNormalized(e.Attributes[1].Value) require.NoError(err) - receiver, err := sdk.AccAddressFromBech32(e.Attributes[0].Value) + _, err = suite.authKeeper.AddressCodec().StringToBytes(e.Attributes[0].Value) require.NoError(err) - balances[receiver.String()] = balances[receiver.String()].Add(coinsRecv...) + balances[e.Attributes[0].Value] = balances[e.Attributes[0].Value].Add(coinsRecv...) } } @@ -1876,7 +1919,10 @@ func (suite *KeeperTestSuite) TestBalanceTrackingEvents() { return false } - balance, exists := balances[address.String()] + addr, err := suite.authKeeper.AddressCodec().BytesToString(address) + suite.Require().NoError(err) + + balance, exists := balances[addr] require.True(exists) expectedUtxo := sdk.NewCoin("utxo", balance.AmountOf(coin.Denom)) diff --git a/x/bank/keeper/msg_server_test.go b/x/bank/keeper/msg_server_test.go index 45e5270f71e6..ea27bbcbf1fc 100644 --- a/x/bank/keeper/msg_server_test.go +++ b/x/bank/keeper/msg_server_test.go @@ -72,6 +72,11 @@ func (suite *KeeperTestSuite) TestMsgSend() { atom0 := sdk.NewCoins(sdk.NewInt64Coin("atom", 0)) atom123eth0 := sdk.Coins{sdk.NewInt64Coin("atom", 123), sdk.NewInt64Coin("eth", 0)} + acc4Addr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[4]) + suite.Require().NoError(err) + minterAccAddr, err := suite.authKeeper.AddressCodec().BytesToString(minterAcc.GetAddress()) + suite.Require().NoError(err) + testCases := []struct { name string input *banktypes.MsgSend @@ -81,8 +86,8 @@ func (suite *KeeperTestSuite) TestMsgSend() { { name: "invalid send to blocked address", input: &banktypes.MsgSend{ - FromAddress: minterAcc.GetAddress().String(), - ToAddress: accAddrs[4].String(), + FromAddress: minterAccAddr, + ToAddress: acc4Addr, Amount: origCoins, }, expErr: true, @@ -91,7 +96,7 @@ func (suite *KeeperTestSuite) TestMsgSend() { { name: "invalid coins", input: &banktypes.MsgSend{ - FromAddress: minterAcc.GetAddress().String(), + FromAddress: minterAccAddr, ToAddress: baseAcc.Address, Amount: atom0, }, @@ -101,7 +106,7 @@ func (suite *KeeperTestSuite) TestMsgSend() { { name: "123atom,0eth: invalid coins", input: &banktypes.MsgSend{ - FromAddress: minterAcc.GetAddress().String(), + FromAddress: minterAccAddr, ToAddress: baseAcc.Address, Amount: atom123eth0, }, @@ -121,7 +126,7 @@ func (suite *KeeperTestSuite) TestMsgSend() { { name: "invalid to address: empty address string is not allowed: invalid address", input: &banktypes.MsgSend{ - FromAddress: minterAcc.GetAddress().String(), + FromAddress: minterAccAddr, ToAddress: "", Amount: origCoins, }, @@ -131,7 +136,7 @@ func (suite *KeeperTestSuite) TestMsgSend() { { name: "all good", input: &banktypes.MsgSend{ - FromAddress: minterAcc.GetAddress().String(), + FromAddress: minterAccAddr, ToAddress: baseAcc.Address, Amount: origCoins, }, @@ -165,6 +170,15 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { sendCoins := sdk.NewCoins(sdk.NewInt64Coin(origDenom, 50)) suite.bankKeeper.SetSendEnabled(suite.ctx, origDenom, true) + acc0Addr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[0]) + suite.Require().NoError(err) + acc1Addr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[1]) + suite.Require().NoError(err) + acc4Addr, err := suite.authKeeper.AddressCodec().BytesToString(accAddrs[4]) + suite.Require().NoError(err) + minterAccAddr, err := suite.authKeeper.AddressCodec().BytesToString(minterAcc.GetAddress()) + suite.Require().NoError(err) + testCases := []struct { name string input *banktypes.MsgMultiSend @@ -181,7 +195,7 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { name: "no inputs to send transaction", input: &banktypes.MsgMultiSend{ Outputs: []banktypes.Output{ - {Address: accAddrs[4].String(), Coins: sendCoins}, + {Address: acc4Addr, Coins: sendCoins}, }, }, expErr: true, @@ -191,8 +205,8 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { name: "more than one inputs to send transaction", input: &banktypes.MsgMultiSend{ Inputs: []banktypes.Input{ - {Address: minterAcc.GetAddress().String(), Coins: origCoins}, - {Address: minterAcc.GetAddress().String(), Coins: origCoins}, + {Address: minterAccAddr, Coins: origCoins}, + {Address: minterAccAddr, Coins: origCoins}, }, }, expErr: true, @@ -202,7 +216,7 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { name: "no outputs to send transaction", input: &banktypes.MsgMultiSend{ Inputs: []banktypes.Input{ - {Address: minterAcc.GetAddress().String(), Coins: origCoins}, + {Address: minterAccAddr, Coins: origCoins}, }, }, expErr: true, @@ -212,11 +226,11 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { name: "invalid send to blocked address", input: &banktypes.MsgMultiSend{ Inputs: []banktypes.Input{ - {Address: minterAcc.GetAddress().String(), Coins: origCoins}, + {Address: minterAccAddr, Coins: origCoins}, }, Outputs: []banktypes.Output{ - {Address: accAddrs[0].String(), Coins: sendCoins}, - {Address: accAddrs[4].String(), Coins: sendCoins}, + {Address: acc0Addr, Coins: sendCoins}, + {Address: acc4Addr, Coins: sendCoins}, }, }, expErr: true, @@ -226,11 +240,11 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { name: "invalid send to blocked address", input: &banktypes.MsgMultiSend{ Inputs: []banktypes.Input{ - {Address: minterAcc.GetAddress().String(), Coins: origCoins}, + {Address: minterAccAddr, Coins: origCoins}, }, Outputs: []banktypes.Output{ - {Address: accAddrs[0].String(), Coins: sendCoins}, - {Address: accAddrs[1].String(), Coins: sendCoins}, + {Address: acc0Addr, Coins: sendCoins}, + {Address: acc1Addr, Coins: sendCoins}, }, }, expErr: false, @@ -258,6 +272,8 @@ func (suite *KeeperTestSuite) TestMsgMultiSend() { } func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { + govAccAddr, err := suite.authKeeper.AddressCodec().BytesToString(govAcc.GetAddress()) + suite.Require().NoError(err) testCases := []struct { name string req *banktypes.MsgSetSendEnabled @@ -267,7 +283,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "all good", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("atom1", true), }, @@ -277,7 +293,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "all good with two denoms", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("atom1", true), banktypes.NewSendEnabled("atom2", true), @@ -288,7 +304,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "duplicate denoms", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("atom", true), banktypes.NewSendEnabled("atom", true), @@ -301,7 +317,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "bad first denom name, (invalid send enabled denom present in list)", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("not a denom", true), banktypes.NewSendEnabled("somecoin", true), @@ -314,7 +330,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "bad second denom name, (invalid send enabled denom present in list)", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("somecoin", true), banktypes.NewSendEnabled("not a denom", true), @@ -327,7 +343,7 @@ func (suite *KeeperTestSuite) TestMsgSetSendEnabled() { { name: "invalid UseDefaultFor denom", req: banktypes.NewMsgSetSendEnabled( - govAcc.GetAddress().String(), + govAccAddr, []*banktypes.SendEnabled{ banktypes.NewSendEnabled("atom", true), }, @@ -367,6 +383,9 @@ func (suite *KeeperTestSuite) TestMsgBurn() { origCoins := sdk.NewInt64Coin("eth", 100) atom0 := sdk.NewInt64Coin("atom", 0) + multiPermAccAddr, err := suite.authKeeper.AddressCodec().BytesToString(multiPermAcc.GetAddress()) + suite.Require().NoError(err) + testCases := []struct { name string input *banktypes.MsgBurn @@ -376,7 +395,7 @@ func (suite *KeeperTestSuite) TestMsgBurn() { { name: "invalid coins", input: &banktypes.MsgBurn{ - FromAddress: multiPermAcc.GetAddress().String(), + FromAddress: multiPermAccAddr, Amount: []*sdk.Coin{&atom0}, }, expErr: true, @@ -395,7 +414,7 @@ func (suite *KeeperTestSuite) TestMsgBurn() { { name: "all good", input: &banktypes.MsgBurn{ - FromAddress: multiPermAcc.GetAddress().String(), + FromAddress: multiPermAccAddr, Amount: []*sdk.Coin{&origCoins}, }, expErr: false, diff --git a/x/bank/simulation/genesis.go b/x/bank/simulation/genesis.go index 7c9c6ba46e38..9e8b8512b827 100644 --- a/x/bank/simulation/genesis.go +++ b/x/bank/simulation/genesis.go @@ -59,17 +59,21 @@ func RandomGenesisSendEnabled(r *rand.Rand, bondDenom string) []types.SendEnable // RandomGenesisBalances returns a slice of account balances. Each account has // a balance of simState.InitialStake for simState.BondDenom. -func RandomGenesisBalances(simState *module.SimulationState) []types.Balance { +func RandomGenesisBalances(simState *module.SimulationState) ([]types.Balance, error) { genesisBalances := []types.Balance{} for _, acc := range simState.Accounts { + addr, err := simState.AddressCodec.BytesToString(acc.Address) + if err != nil { + return nil, err + } genesisBalances = append(genesisBalances, types.Balance{ - Address: acc.Address.String(), + Address: addr, Coins: sdk.NewCoins(sdk.NewCoin(simState.BondDenom, simState.InitialStake)), }) } - return genesisBalances + return genesisBalances, nil } // RandomizedGenState generates a random GenesisState for bank @@ -83,9 +87,14 @@ func RandomizedGenState(simState *module.SimulationState) { totalSupply := simState.InitialStake.Mul(sdkmath.NewInt((numAccs + simState.NumBonded))) supply := sdk.NewCoins(sdk.NewCoin(simState.BondDenom, totalSupply)) + balances, err := RandomGenesisBalances(simState) + if err != nil { + panic(err) + } + bankGenesis := types.GenesisState{ Params: types.NewParams(defaultSendEnabledParam), - Balances: RandomGenesisBalances(simState), + Balances: balances, Supply: supply, SendEnabled: sendEnabled, } diff --git a/x/bank/simulation/operations.go b/x/bank/simulation/operations.go index 0c9c6269101f..b3933b6d01e1 100644 --- a/x/bank/simulation/operations.go +++ b/x/bank/simulation/operations.go @@ -218,8 +218,13 @@ func SimulateMsgMultiSend(txGen client.TxConfig, ak types.AccountKeeper, bk keep // generate random input fields, ignore to address from, _, coins, skip := randomSendFields(r, ctx, accs, bk, ak) + fromAddr, err := ak.AddressCodec().BytesToString(from.Address) + if err != nil { + return simtypes.NoOpMsg(types.ModuleName, msgType, "could not retrieve address"), nil, err + } + // make sure account is fresh and not used in previous input - for usedAddrs[from.Address.String()] { + for usedAddrs[fromAddr] { from, _, coins, skip = randomSendFields(r, ctx, accs, bk, ak) } @@ -228,13 +233,13 @@ func SimulateMsgMultiSend(txGen client.TxConfig, ak types.AccountKeeper, bk keep } // set input address in used address map - usedAddrs[from.Address.String()] = true + usedAddrs[fromAddr] = true // set signer privkey privs[i] = from.PrivKey // set next input and accumulate total sent coins - inputs[i] = types.NewInput(from.Address, coins) + inputs[i] = types.NewInput(fromAddr, coins) totalSentCoins = totalSentCoins.Add(coins...) } @@ -244,7 +249,11 @@ func SimulateMsgMultiSend(txGen client.TxConfig, ak types.AccountKeeper, bk keep } for o := range outputs { - outAddr, _ := simtypes.RandomAcc(r, accs) + out, _ := simtypes.RandomAcc(r, accs) + outAddr, err := ak.AddressCodec().BytesToString(out.Address) + if err != nil { + return simtypes.NoOpMsg(types.ModuleName, msgType, "could not retrieve output address"), nil, err + } var outCoins sdk.Coins // split total sent coins into random subsets for output @@ -257,7 +266,7 @@ func SimulateMsgMultiSend(txGen client.TxConfig, ak types.AccountKeeper, bk keep totalSentCoins = totalSentCoins.Sub(outCoins...) } - outputs[o] = types.NewOutput(outAddr.Address, outCoins) + outputs[o] = types.NewOutput(outAddr, outCoins) } // remove any output that has no coins @@ -305,9 +314,13 @@ func SimulateMsgMultiSendToModuleAccount( for i := range inputs { sender := accs[i] privs[i] = sender.PrivKey + senderAddr, err := ak.AddressCodec().BytesToString(sender.Address) + if err != nil { + return simtypes.NoOpMsg(types.ModuleName, msgType, err.Error()), nil, err + } spendable := bk.SpendableCoins(ctx, sender.Address) coins := simtypes.RandSubsetCoins(r, spendable) - inputs[i] = types.NewInput(sender.Address, coins) + inputs[i] = types.NewInput(senderAddr, coins) totalSentCoins = totalSentCoins.Add(coins...) } if err := bk.IsSendEnabledCoins(ctx, totalSentCoins...); err != nil { @@ -315,6 +328,11 @@ func SimulateMsgMultiSendToModuleAccount( } moduleAccounts := getModuleAccounts(ak, ctx, moduleAccount) for i := range outputs { + outAddr, err := ak.AddressCodec().BytesToString(moduleAccounts[i].Address) + if err != nil { + return simtypes.NoOpMsg(types.ModuleName, msgType, "could not retrieve output address"), nil, err + } + var outCoins sdk.Coins // split total sent coins into random subsets for output if i == len(outputs)-1 { @@ -325,7 +343,7 @@ func SimulateMsgMultiSendToModuleAccount( outCoins = simtypes.RandSubsetCoins(r, totalSentCoins) totalSentCoins = totalSentCoins.Sub(outCoins...) } - outputs[i] = types.NewOutput(moduleAccounts[i].Address, outCoins) + outputs[i] = types.NewOutput(outAddr, outCoins) } // remove any output that has no coins for i := 0; i < len(outputs); { diff --git a/x/bank/simulation/proposals.go b/x/bank/simulation/proposals.go index 6672be0dc2d2..7e2683fed6cb 100644 --- a/x/bank/simulation/proposals.go +++ b/x/bank/simulation/proposals.go @@ -31,15 +31,18 @@ func ProposalMsgs() []simtypes.WeightedProposalMsg { } // SimulateMsgUpdateParams returns a random MsgUpdateParams -func SimulateMsgUpdateParams(r *rand.Rand, _ []simtypes.Account, _ coreaddress.Codec) (sdk.Msg, error) { +func SimulateMsgUpdateParams(r *rand.Rand, _ []simtypes.Account, ac coreaddress.Codec) (sdk.Msg, error) { // use the default gov module account address as authority - var authority sdk.AccAddress = address.Module("gov") + authority, err := ac.BytesToString(address.Module("gov")) + if err != nil { + return nil, err + } params := types.DefaultParams() params.DefaultSendEnabled = r.Intn(2) == 0 return &types.MsgUpdateParams{ - Authority: authority.String(), + Authority: authority, Params: params, }, nil } diff --git a/x/bank/simulation/proposals_test.go b/x/bank/simulation/proposals_test.go index db035620a805..3d60a17bbb91 100644 --- a/x/bank/simulation/proposals_test.go +++ b/x/bank/simulation/proposals_test.go @@ -10,12 +10,13 @@ import ( "cosmossdk.io/x/bank/types" codectestutil "github.com/cosmos/cosmos-sdk/codec/testutil" - sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/address" simtypes "github.com/cosmos/cosmos-sdk/types/simulation" ) func TestProposalMsgs(t *testing.T) { + ac := codectestutil.CodecOptions{}.GetAddressCodec() + // initialize parameters s := rand.NewSource(1) r := rand.New(s) @@ -32,12 +33,14 @@ func TestProposalMsgs(t *testing.T) { assert.Equal(t, simulation.OpWeightMsgUpdateParams, w0.AppParamsKey()) assert.Equal(t, simulation.DefaultWeightMsgUpdateParams, w0.DefaultWeight()) - msg, err := w0.MsgSimulatorFn()(r, accounts, codectestutil.CodecOptions{}.GetAddressCodec()) + msg, err := w0.MsgSimulatorFn()(r, accounts, ac) assert.NilError(t, err) msgUpdateParams, ok := msg.(*types.MsgUpdateParams) assert.Assert(t, ok) - assert.Equal(t, sdk.AccAddress(address.Module("gov")).String(), msgUpdateParams.Authority) + authority, err := ac.BytesToString(address.Module("gov")) + assert.NilError(t, err) + assert.Equal(t, authority, msgUpdateParams.Authority) assert.Assert(t, len(msgUpdateParams.Params.SendEnabled) == 0) //nolint:staticcheck // we're testing the old way here assert.Equal(t, true, msgUpdateParams.Params.DefaultSendEnabled) } diff --git a/x/bank/types/balance.go b/x/bank/types/balance.go index a9863984498e..32c90d7c953f 100644 --- a/x/bank/types/balance.go +++ b/x/bank/types/balance.go @@ -6,6 +6,7 @@ import ( "fmt" "sort" + "cosmossdk.io/core/address" "cosmossdk.io/x/bank/exported" "github.com/cosmos/cosmos-sdk/codec" @@ -53,7 +54,7 @@ func (b balanceByAddress) Swap(i, j int) { } // SanitizeGenesisBalances checks for duplicates and sorts addresses and coin sets. -func SanitizeGenesisBalances(balances []Balance) []Balance { +func SanitizeGenesisBalances(balances []Balance, addressCodec address.Codec) ([]Balance, error) { // Given that this function sorts balances, using the standard library's // Quicksort based algorithms, we have algorithmic complexities of: // * Best case: O(nlogn) @@ -68,7 +69,10 @@ func SanitizeGenesisBalances(balances []Balance) []Balance { // 2. Track any duplicate addresses to avoid false positives on invariant checks. seen := make(map[string]struct{}) for i := range balances { - addr, _ := sdk.AccAddressFromBech32(balances[i].Address) + addr, err := addressCodec.StringToBytes(balances[i].Address) + if err != nil { + return nil, err + } addresses[i] = addr if _, exists := seen[string(addr)]; exists { panic(fmt.Sprintf("genesis state has a duplicate account: %q aka %x", balances[i].Address, addr)) @@ -79,7 +83,7 @@ func SanitizeGenesisBalances(balances []Balance) []Balance { // 3. Sort balances. sort.Sort(balanceByAddress{addresses: addresses, balances: balances}) - return balances + return balances, nil } // GenesisBalancesIterator implements genesis account iteration. diff --git a/x/bank/types/balance_test.go b/x/bank/types/balance_test.go index 2e0d3e7c5181..c208f88c218c 100644 --- a/x/bank/types/balance_test.go +++ b/x/bank/types/balance_test.go @@ -9,6 +9,7 @@ import ( "cosmossdk.io/math" bank "cosmossdk.io/x/bank/types" + codectestutil "github.com/cosmos/cosmos-sdk/codec/testutil" "github.com/cosmos/cosmos-sdk/crypto/keys/ed25519" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -147,15 +148,19 @@ func TestSanitizeBalances(t *testing.T) { coins := sdk.Coins{coin} addrs, _ := makeRandomAddressesAndPublicKeys(20) + ac := codectestutil.CodecOptions{}.GetAddressCodec() var balances []bank.Balance for _, addr := range addrs { + addrStr, err := ac.BytesToString(addr) + require.NoError(t, err) balances = append(balances, bank.Balance{ - Address: addr.String(), + Address: addrStr, Coins: coins, }) } // 2. Sort the values. - sorted := bank.SanitizeGenesisBalances(balances) + sorted, err := bank.SanitizeGenesisBalances(balances, ac) + require.NoError(t, err) // 3. Compare and ensure that all the values are sorted in ascending order. // Invariant after sorting: @@ -180,9 +185,12 @@ func TestSanitizeBalancesDuplicates(t *testing.T) { addrs, _ := makeRandomAddressesAndPublicKeys(13) var balances []bank.Balance + ac := codectestutil.CodecOptions{}.GetAddressCodec() for _, addr := range addrs { + addrStr, err := ac.BytesToString(addr) + require.NoError(t, err) balances = append(balances, bank.Balance{ - Address: addr.String(), + Address: addrStr, Coins: coins, }) } @@ -190,7 +198,7 @@ func TestSanitizeBalancesDuplicates(t *testing.T) { // 2. Add duplicate dupIdx := 3 balances = append(balances, balances[dupIdx]) - addr, _ := sdk.AccAddressFromBech32(balances[dupIdx].Address) + addr, _ := ac.StringToBytes(balances[dupIdx].Address) expectedError := fmt.Sprintf("genesis state has a duplicate account: %q aka %x", balances[dupIdx].Address, addr) // 3. Add more balances @@ -198,15 +206,18 @@ func TestSanitizeBalancesDuplicates(t *testing.T) { coins2 := sdk.Coins{coin2, coin} addrs2, _ := makeRandomAddressesAndPublicKeys(31) for _, addr := range addrs2 { + addrStr, err := ac.BytesToString(addr) + require.NoError(t, err) balances = append(balances, bank.Balance{ - Address: addr.String(), + Address: addrStr, Coins: coins2, }) } // 4. Execute SanitizeGenesisBalances and expect an error require.PanicsWithValue(t, expectedError, func() { - bank.SanitizeGenesisBalances(balances) + _, err := bank.SanitizeGenesisBalances(balances, ac) + require.NoError(t, err) }, "SanitizeGenesisBalances should panic with duplicate accounts") } @@ -238,15 +249,20 @@ func benchmarkSanitizeBalances(b *testing.B, nAddresses int) { addrs, _ := makeRandomAddressesAndPublicKeys(nAddresses) b.ResetTimer() + var err error + ac := codectestutil.CodecOptions{}.GetAddressCodec() for i := 0; i < b.N; i++ { var balances []bank.Balance for _, addr := range addrs { + addrStr, err := ac.BytesToString(addr) + require.NoError(b, err) balances = append(balances, bank.Balance{ - Address: addr.String(), + Address: addrStr, Coins: coins, }) } - sink = bank.SanitizeGenesisBalances(balances) + sink, err = bank.SanitizeGenesisBalances(balances, ac) + require.NoError(b, err) } if sink == nil { b.Fatal("Benchmark did not run") diff --git a/x/bank/types/inputs_outputs.go b/x/bank/types/inputs_outputs.go index 5d98f72a87de..d448f7bcc075 100644 --- a/x/bank/types/inputs_outputs.go +++ b/x/bank/types/inputs_outputs.go @@ -51,9 +51,9 @@ func (in Input) ValidateBasic() error { } // NewInput - create a transaction input, used with MsgMultiSend -func NewInput(addr sdk.AccAddress, coins sdk.Coins) Input { +func NewInput(addr string, coins sdk.Coins) Input { return Input{ - Address: addr.String(), + Address: addr, Coins: coins, } } @@ -76,9 +76,9 @@ func (out Output) ValidateBasic() error { } // NewOutput - create a transaction output, used with MsgMultiSend -func NewOutput(addr sdk.AccAddress, coins sdk.Coins) Output { +func NewOutput(addr string, coins sdk.Coins) Output { return Output{ - Address: addr.String(), + Address: addr, Coins: coins, } } diff --git a/x/bank/types/msgs_test.go b/x/bank/types/msgs_test.go index a6c59826bebb..3a85e5d367da 100644 --- a/x/bank/types/msgs_test.go +++ b/x/bank/types/msgs_test.go @@ -7,6 +7,7 @@ import ( "github.com/stretchr/testify/require" "github.com/cosmos/cosmos-sdk/codec" + "github.com/cosmos/cosmos-sdk/codec/testutil" "github.com/cosmos/cosmos-sdk/codec/types" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -22,10 +23,15 @@ func TestMsgSendGetSignBytes(t *testing.T) { } func TestInputValidation(t *testing.T) { - addr1 := sdk.AccAddress([]byte("_______alice________")) - addr2 := sdk.AccAddress([]byte("________bob_________")) - addrEmpty := sdk.AccAddress([]byte("")) - addrLong := sdk.AccAddress([]byte("Purposefully long address")) + ac := testutil.CodecOptions{}.GetAddressCodec() + addr1, err := ac.BytesToString([]byte("_______alice________")) + require.NoError(t, err) + addr2, err := ac.BytesToString([]byte("________bob_________")) + require.NoError(t, err) + addrEmpty, err := ac.BytesToString([]byte("")) + require.NoError(t, err) + addrLong, err := ac.BytesToString([]byte("Purposefully long address")) + require.NoError(t, err) someCoins := sdk.NewCoins(sdk.NewInt64Coin("atom", 123)) multiCoins := sdk.NewCoins(sdk.NewInt64Coin("atom", 123), sdk.NewInt64Coin("eth", 20)) @@ -63,10 +69,15 @@ func TestInputValidation(t *testing.T) { } func TestOutputValidation(t *testing.T) { - addr1 := sdk.AccAddress([]byte("_______alice________")) - addr2 := sdk.AccAddress([]byte("________bob_________")) - addrEmpty := sdk.AccAddress([]byte("")) - addrLong := sdk.AccAddress([]byte("Purposefully long address")) + ac := testutil.CodecOptions{}.GetAddressCodec() + addr1, err := ac.BytesToString([]byte("_______alice________")) + require.NoError(t, err) + addr2, err := ac.BytesToString([]byte("________bob_________")) + require.NoError(t, err) + addrEmpty, err := ac.BytesToString([]byte("")) + require.NoError(t, err) + addrLong, err := ac.BytesToString([]byte("Purposefully long address")) + require.NoError(t, err) someCoins := sdk.NewCoins(sdk.NewInt64Coin("atom", 123)) multiCoins := sdk.NewCoins(sdk.NewInt64Coin("atom", 123), sdk.NewInt64Coin("eth", 20)) @@ -104,8 +115,12 @@ func TestOutputValidation(t *testing.T) { } func TestMsgMultiSendGetSignBytes(t *testing.T) { - addr1 := sdk.AccAddress([]byte("input")) - addr2 := sdk.AccAddress([]byte("output")) + ac := testutil.CodecOptions{}.GetAddressCodec() + addr1, err := ac.BytesToString([]byte("input")) + require.NoError(t, err) + addr2, err := ac.BytesToString([]byte("output")) + require.NoError(t, err) + coins := sdk.NewCoins(sdk.NewInt64Coin("atom", 10)) msg := &MsgMultiSend{ Inputs: []Input{NewInput(addr1, coins)}, diff --git a/x/bank/types/querier.go b/x/bank/types/querier.go index 6a2dcb097432..532676c084ab 100644 --- a/x/bank/types/querier.go +++ b/x/bank/types/querier.go @@ -1,7 +1,6 @@ package types import ( - sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/query" ) @@ -14,19 +13,19 @@ const ( ) // NewQueryBalanceRequest creates a new instance of QueryBalanceRequest. -func NewQueryBalanceRequest(addr sdk.AccAddress, denom string) *QueryBalanceRequest { - return &QueryBalanceRequest{Address: addr.String(), Denom: denom} +func NewQueryBalanceRequest(addr, denom string) *QueryBalanceRequest { + return &QueryBalanceRequest{Address: addr, Denom: denom} } // NewQueryAllBalancesRequest creates a new instance of QueryAllBalancesRequest. -func NewQueryAllBalancesRequest(addr sdk.AccAddress, req *query.PageRequest, resolveDenom bool) *QueryAllBalancesRequest { - return &QueryAllBalancesRequest{Address: addr.String(), Pagination: req, ResolveDenom: resolveDenom} +func NewQueryAllBalancesRequest(addr string, req *query.PageRequest, resolveDenom bool) *QueryAllBalancesRequest { + return &QueryAllBalancesRequest{Address: addr, Pagination: req, ResolveDenom: resolveDenom} } // NewQuerySpendableBalancesRequest creates a new instance of a // QuerySpendableBalancesRequest. -func NewQuerySpendableBalancesRequest(addr sdk.AccAddress, req *query.PageRequest) *QuerySpendableBalancesRequest { - return &QuerySpendableBalancesRequest{Address: addr.String(), Pagination: req} +func NewQuerySpendableBalancesRequest(addr string, req *query.PageRequest) *QuerySpendableBalancesRequest { + return &QuerySpendableBalancesRequest{Address: addr, Pagination: req} } // NewQuerySpendableBalanceByDenomRequest creates a new instance of a diff --git a/x/bank/types/send_authorization.go b/x/bank/types/send_authorization.go index cdc1fc62a24c..05c5299894e9 100644 --- a/x/bank/types/send_authorization.go +++ b/x/bank/types/send_authorization.go @@ -3,6 +3,8 @@ package types import ( context "context" + "cosmossdk.io/core/address" + sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/authz" sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" @@ -14,9 +16,9 @@ import ( const gasCostPerIteration = uint64(10) // NewSendAuthorization creates a new SendAuthorization object. -func NewSendAuthorization(spendLimit sdk.Coins, allowed []sdk.AccAddress) *SendAuthorization { +func NewSendAuthorization(spendLimit sdk.Coins, allowed []sdk.AccAddress, addressCodec address.Codec) *SendAuthorization { return &SendAuthorization{ - AllowList: toBech32Addresses(allowed), + AllowList: toBech32Addresses(allowed, addressCodec), SpendLimit: spendLimit, } } @@ -82,14 +84,18 @@ func (a SendAuthorization) ValidateBasic() error { return nil } -func toBech32Addresses(allowed []sdk.AccAddress) []string { +func toBech32Addresses(allowed []sdk.AccAddress, addressCodec address.Codec) []string { if len(allowed) == 0 { return nil } allowedAddrs := make([]string, len(allowed)) for i, addr := range allowed { - allowedAddrs[i] = addr.String() + addrStr, err := addressCodec.BytesToString(addr) + if err != nil { + panic(err) // TODO: + } + allowedAddrs[i] = addrStr } return allowedAddrs diff --git a/x/bank/types/send_authorization_test.go b/x/bank/types/send_authorization_test.go index fbecc2300669..4d0ad0382c1a 100644 --- a/x/bank/types/send_authorization_test.go +++ b/x/bank/types/send_authorization_test.go @@ -1,7 +1,7 @@ package types_test import ( - fmt "fmt" + "fmt" "testing" "github.com/stretchr/testify/require" @@ -11,6 +11,7 @@ import ( storetypes "cosmossdk.io/store/types" "cosmossdk.io/x/bank/types" + codectestutil "github.com/cosmos/cosmos-sdk/codec/testutil" "github.com/cosmos/cosmos-sdk/testutil" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -25,10 +26,11 @@ var ( ) func TestSendAuthorization(t *testing.T) { + ac := codectestutil.CodecOptions{}.GetAddressCodec() ctx := testutil.DefaultContextWithDB(t, storetypes.NewKVStoreKey(types.StoreKey), storetypes.NewTransientStoreKey("transient_test")).Ctx.WithHeaderInfo(header.Info{}) allowList := make([]sdk.AccAddress, 1) allowList[0] = toAddr - authorization := types.NewSendAuthorization(coins1000, nil) + authorization := types.NewSendAuthorization(coins1000, nil, ac) t.Log("verify authorization returns valid method name") require.Equal(t, authorization.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") @@ -41,7 +43,7 @@ func TestSendAuthorization(t *testing.T) { require.True(t, resp.Delete) require.Nil(t, resp.Updated) - authorization = types.NewSendAuthorization(coins1000, nil) + authorization = types.NewSendAuthorization(coins1000, nil, ac) require.Equal(t, authorization.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") require.NoError(t, authorization.ValidateBasic()) send = types.NewMsgSend(fromAddrStr, toAddrStr, coins500) @@ -52,7 +54,7 @@ func TestSendAuthorization(t *testing.T) { require.NoError(t, err) require.False(t, resp.Delete) require.NotNil(t, resp.Updated) - sendAuth := types.NewSendAuthorization(coins500, nil) + sendAuth := types.NewSendAuthorization(coins500, nil, ac) require.Equal(t, sendAuth.String(), resp.Updated.String()) t.Log("expect updated authorization nil after spending remaining amount") @@ -62,7 +64,7 @@ func TestSendAuthorization(t *testing.T) { require.Nil(t, resp.Updated) t.Log("allow list and no address") - authzWithAllowList := types.NewSendAuthorization(coins1000, allowList) + authzWithAllowList := types.NewSendAuthorization(coins1000, allowList, ac) require.Equal(t, authzWithAllowList.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") require.NoError(t, authorization.ValidateBasic()) send = types.NewMsgSend(fromAddrStr, unknownAddrStr, coins500) @@ -75,7 +77,7 @@ func TestSendAuthorization(t *testing.T) { require.Contains(t, err.Error(), fmt.Sprintf("cannot send to %s address", unknownAddrStr)) t.Log("send to address in allow list") - authzWithAllowList = types.NewSendAuthorization(coins1000, allowList) + authzWithAllowList = types.NewSendAuthorization(coins1000, allowList, ac) require.Equal(t, authzWithAllowList.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") require.NoError(t, authorization.ValidateBasic()) send = types.NewMsgSend(fromAddrStr, toAddrStr, coins500) @@ -85,10 +87,10 @@ func TestSendAuthorization(t *testing.T) { require.True(t, resp.Accept) require.NotNil(t, resp.Updated) // coins1000-coins500 = coins500 - require.Equal(t, types.NewSendAuthorization(coins500, allowList).String(), resp.Updated.String()) + require.Equal(t, types.NewSendAuthorization(coins500, allowList, ac).String(), resp.Updated.String()) t.Log("send everything to address not in allow list") - authzWithAllowList = types.NewSendAuthorization(coins1000, allowList) + authzWithAllowList = types.NewSendAuthorization(coins1000, allowList, ac) require.Equal(t, authzWithAllowList.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") require.NoError(t, authorization.ValidateBasic()) send = types.NewMsgSend(fromAddrStr, unknownAddrStr, coins1000) @@ -98,7 +100,7 @@ func TestSendAuthorization(t *testing.T) { require.Contains(t, err.Error(), fmt.Sprintf("cannot send to %s address", unknownAddrStr)) t.Log("send everything to address in allow list") - authzWithAllowList = types.NewSendAuthorization(coins1000, allowList) + authzWithAllowList = types.NewSendAuthorization(coins1000, allowList, ac) require.Equal(t, authzWithAllowList.MsgTypeURL(), "/cosmos.bank.v1beta1.MsgSend") require.NoError(t, authorization.ValidateBasic()) send = types.NewMsgSend(fromAddrStr, toAddrStr, coins1000) diff --git a/x/genutil/genaccounts.go b/x/genutil/genaccounts.go index 500eb1bb132f..4c09ac71b1c5 100644 --- a/x/genutil/genaccounts.go +++ b/x/genutil/genaccounts.go @@ -131,8 +131,10 @@ func AddGenesisAccount( bankGenState.Balances = append(bankGenState.Balances, balances) } - bankGenState.Balances = banktypes.SanitizeGenesisBalances(bankGenState.Balances) - + bankGenState.Balances, err = banktypes.SanitizeGenesisBalances(bankGenState.Balances, addressCodec) + if err != nil { + return fmt.Errorf("failed to sanitize genesis balance: %w", err) + } bankGenState.Supply = bankGenState.Supply.Add(balances.Coins...) bankGenStateBz, err := cdc.MarshalJSON(bankGenState)