From 24edb2ae8d64d6a78a263186e500f5686524d00b Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Fri, 26 Jun 2020 14:28:45 -0400 Subject: [PATCH 01/20] init --- x/bank/client/cli/cli_test.go | 437 +++++++++++++++++++--------------- x/bank/client/cli/query.go | 22 +- 2 files changed, 258 insertions(+), 201 deletions(-) diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go index 743d348731ad..27c60791eb35 100644 --- a/x/bank/client/cli/cli_test.go +++ b/x/bank/client/cli/cli_test.go @@ -1,223 +1,266 @@ -// +build cli_test - package cli_test import ( + "bytes" "fmt" "testing" - "github.com/stretchr/testify/require" + "github.com/stretchr/testify/suite" - "github.com/cosmos/cosmos-sdk/tests" - "github.com/cosmos/cosmos-sdk/tests/cli" - sdk "github.com/cosmos/cosmos-sdk/types" - "github.com/cosmos/cosmos-sdk/x/bank/client/testutil" + "github.com/cosmos/cosmos-sdk/testutil" + "github.com/cosmos/cosmos-sdk/x/bank/client/cli" ) -func TestCLISend(t *testing.T) { - t.Parallel() - f := cli.InitFixtures(t) - - // start simd server - proc := f.SDStart() - t.Cleanup(func() { proc.Stop(false) }) - - // Save key addresses for later uspackage testse - fooAddr := f.KeyAddress(cli.KeyFoo) - barAddr := f.KeyAddress(cli.KeyBar) - - startTokens := sdk.TokensFromConsensusPower(50) - require.Equal(t, startTokens, testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - - sendTokens := sdk.TokensFromConsensusPower(10) - - // It does not allow to send in offline mode - success, _, stdErr := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y", "--offline") - require.Contains(t, stdErr, "no RPC client is defined in offline mode") - require.False(f.T, success) - tests.WaitForNextNBlocksTM(1, f.Port) - - // Send some tokens from one account to the other - testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") - tests.WaitForNextNBlocksTM(1, f.Port) - - // Ensure account balances match expected - require.Equal(t, sendTokens.String(), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom).String()) - require.Equal(t, startTokens.Sub(sendTokens).String(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom).String()) - - // Test --dry-run - success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--dry-run") - require.True(t, success) - - // Test --generate-only - success, stdout, stderr := testutil.TxSend( - f, fooAddr.String(), barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--generate-only=true", - ) - require.Empty(t, stderr) - require.True(t, success) - msg := cli.UnmarshalStdTx(f.T, f.Cdc, stdout) - t.Log(msg) - require.NotZero(t, msg.Fee.Gas) - require.Len(t, msg.Msgs, 1) - require.Len(t, msg.GetSignatures(), 0) - - // Check state didn't change - require.Equal(t, startTokens.Sub(sendTokens), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - - // test autosequencing - testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") - tests.WaitForNextNBlocksTM(1, f.Port) - - // Ensure account balances match expected - require.Equal(t, sendTokens.MulRaw(2), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) - require.Equal(t, startTokens.Sub(sendTokens.MulRaw(2)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - - // test memo - testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--memo='testmemo'", "-y") - tests.WaitForNextNBlocksTM(1, f.Port) - - // Ensure account balances match expected - require.Equal(t, sendTokens.MulRaw(3), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) - require.Equal(t, startTokens.Sub(sendTokens.MulRaw(3)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - - f.Cleanup() -} +type IntegrationTestSuite struct { + suite.Suite -func TestCLIMinimumFees(t *testing.T) { - t.Parallel() - f := cli.InitFixtures(t) - - // start simd server with minimum fees - minGasPrice, _ := sdk.NewDecFromStr("0.000006") - fees := fmt.Sprintf( - "--minimum-gas-prices=%s,%s", - sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice), - sdk.NewDecCoinFromDec(cli.Fee2Denom, minGasPrice), - ) - proc := f.SDStart(fees) - t.Cleanup(func() { proc.Stop(false) }) - - barAddr := f.KeyAddress(cli.KeyBar) - - // Send a transaction that will get rejected - success, stdOut, _ := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), "-y") - require.Contains(t, stdOut, "insufficient fees") - require.True(f.T, success) - tests.WaitForNextNBlocksTM(1, f.Port) - - // Ensure tx w/ correct fees pass - txFees := fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)) - success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), txFees, "-y") - require.True(f.T, success) - tests.WaitForNextNBlocksTM(1, f.Port) - - // Ensure tx w/ improper fees fails - txFees = fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 1)) - success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 10), txFees, "-y") - require.Contains(t, stdOut, "insufficient fees") - require.True(f.T, success) - - // Cleanup testing directories - f.Cleanup() + cfg testutil.Config + network *testutil.Network } -func TestCLIGasPrices(t *testing.T) { - t.Parallel() - f := cli.InitFixtures(t) - - // start simd server with minimum fees - minGasPrice, _ := sdk.NewDecFromStr("0.000006") - proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) - t.Cleanup(func() { proc.Stop(false) }) - - barAddr := f.KeyAddress(cli.KeyBar) - - // insufficient gas prices (tx fails) - badGasPrice, _ := sdk.NewDecFromStr("0.000003") - success, stdOut, _ := testutil.TxSend( - f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), - fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, badGasPrice)), "-y") - require.Contains(t, stdOut, "insufficient fees") - require.True(t, success) +func (s *IntegrationTestSuite) SetupSuite() { + s.T().Log("setting up integration test suite") - // wait for a block confirmation - tests.WaitForNextNBlocksTM(1, f.Port) + cfg := testutil.DefaultConfig() + cfg.NumValidators = 2 - // sufficient gas prices (tx passes) - success, _, _ = testutil.TxSend( - f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), - fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice)), "-y") - require.True(t, success) + s.cfg = cfg + s.network = testutil.NewTestNetwork(s.T(), cfg) - // wait for a block confirmation - tests.WaitForNextNBlocksTM(1, f.Port) - - f.Cleanup() + _, err := s.network.WaitForHeight(1) + s.Require().NoError(err) } -func TestCLIFeesDeduction(t *testing.T) { - t.Parallel() - f := cli.InitFixtures(t) - - // start simd server with minimum fees - minGasPrice, _ := sdk.NewDecFromStr("0.000006") - proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) - t.Cleanup(func() { proc.Stop(false) }) - - // Save key addresses for later use - fooAddr := f.KeyAddress(cli.KeyFoo) - barAddr := f.KeyAddress(cli.KeyBar) - - fooAmt := testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom) - - // test simulation - success, _, _ := testutil.TxSend( - f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 1000), - fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "--dry-run") - require.True(t, success) - - // Wait for a block - tests.WaitForNextNBlocksTM(1, f.Port) - - // ensure state didn't change - require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) - - // insufficient funds (coins + fees) tx fails - largeCoins := sdk.TokensFromConsensusPower(10000000) - success, stdOut, _ := testutil.TxSend( - f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.FooDenom, largeCoins), - fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") - require.Contains(t, stdOut, "insufficient funds") - require.True(t, success) +func (s *IntegrationTestSuite) TearDownSuite() { + s.T().Log("tearing down integration test suite") + s.network.Cleanup() +} - // Wait for a block - tests.WaitForNextNBlocksTM(1, f.Port) +func (s *IntegrationTestSuite) TestGetBalancesCmd() { + buf := new(bytes.Buffer) + val := s.network.Validators[0] + clientCtx := val.ClientCtx.WithOutput(buf) - // ensure state didn't change - require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) + cmd := cli.GetBalancesCmd(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) + s.Require().Error(cmd.Execute()) - // test success (transfer = coins + fees) - success, _, _ = testutil.TxSend( - f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 500), - fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") - require.True(t, success) + buf.Reset() - f.Cleanup() + cmd.SetArgs([]string{val.Address.String()}) + s.Require().NoError(cmd.Execute()) + fmt.Println(string(buf.Bytes())) } -func TestCLIQuerySupply(t *testing.T) { - t.Parallel() - f := cli.InitFixtures(t) - - // start simd server - proc := f.SDStart() - t.Cleanup(func() { proc.Stop(false) }) +func TestIntegrationTestSuite(t *testing.T) { + suite.Run(t, new(IntegrationTestSuite)) +} - totalSupply := testutil.QueryTotalSupply(f) - totalSupplyOf := testutil.QueryTotalSupplyOf(f, cli.FooDenom) +// func TestCLISend(t *testing.T) { +// t.Parallel() +// f := cli.InitFixtures(t) + +// // start simd server +// proc := f.SDStart() +// t.Cleanup(func() { proc.Stop(false) }) + +// // Save key addresses for later uspackage testse +// fooAddr := f.KeyAddress(cli.KeyFoo) +// barAddr := f.KeyAddress(cli.KeyBar) + +// startTokens := sdk.TokensFromConsensusPower(50) +// require.Equal(t, startTokens, testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) + +// sendTokens := sdk.TokensFromConsensusPower(10) + +// // It does not allow to send in offline mode +// success, _, stdErr := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y", "--offline") +// require.Contains(t, stdErr, "no RPC client is defined in offline mode") +// require.False(f.T, success) +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Send some tokens from one account to the other +// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Ensure account balances match expected +// require.Equal(t, sendTokens.String(), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom).String()) +// require.Equal(t, startTokens.Sub(sendTokens).String(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom).String()) + +// // Test --dry-run +// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--dry-run") +// require.True(t, success) + +// // Test --generate-only +// success, stdout, stderr := testutil.TxSend( +// f, fooAddr.String(), barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--generate-only=true", +// ) +// require.Empty(t, stderr) +// require.True(t, success) +// msg := cli.UnmarshalStdTx(f.T, f.Cdc, stdout) +// t.Log(msg) +// require.NotZero(t, msg.Fee.Gas) +// require.Len(t, msg.Msgs, 1) +// require.Len(t, msg.GetSignatures(), 0) + +// // Check state didn't change +// require.Equal(t, startTokens.Sub(sendTokens), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) + +// // test autosequencing +// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Ensure account balances match expected +// require.Equal(t, sendTokens.MulRaw(2), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) +// require.Equal(t, startTokens.Sub(sendTokens.MulRaw(2)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) + +// // test memo +// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--memo='testmemo'", "-y") +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Ensure account balances match expected +// require.Equal(t, sendTokens.MulRaw(3), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) +// require.Equal(t, startTokens.Sub(sendTokens.MulRaw(3)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) + +// f.Cleanup() +// } + +// func TestCLIMinimumFees(t *testing.T) { +// t.Parallel() +// f := cli.InitFixtures(t) + +// // start simd server with minimum fees +// minGasPrice, _ := sdk.NewDecFromStr("0.000006") +// fees := fmt.Sprintf( +// "--minimum-gas-prices=%s,%s", +// sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice), +// sdk.NewDecCoinFromDec(cli.Fee2Denom, minGasPrice), +// ) +// proc := f.SDStart(fees) +// t.Cleanup(func() { proc.Stop(false) }) + +// barAddr := f.KeyAddress(cli.KeyBar) + +// // Send a transaction that will get rejected +// success, stdOut, _ := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), "-y") +// require.Contains(t, stdOut, "insufficient fees") +// require.True(f.T, success) +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Ensure tx w/ correct fees pass +// txFees := fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)) +// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), txFees, "-y") +// require.True(f.T, success) +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // Ensure tx w/ improper fees fails +// txFees = fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 1)) +// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 10), txFees, "-y") +// require.Contains(t, stdOut, "insufficient fees") +// require.True(f.T, success) + +// // Cleanup testing directories +// f.Cleanup() +// } + +// func TestCLIGasPrices(t *testing.T) { +// t.Parallel() +// f := cli.InitFixtures(t) + +// // start simd server with minimum fees +// minGasPrice, _ := sdk.NewDecFromStr("0.000006") +// proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) +// t.Cleanup(func() { proc.Stop(false) }) + +// barAddr := f.KeyAddress(cli.KeyBar) + +// // insufficient gas prices (tx fails) +// badGasPrice, _ := sdk.NewDecFromStr("0.000003") +// success, stdOut, _ := testutil.TxSend( +// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), +// fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, badGasPrice)), "-y") +// require.Contains(t, stdOut, "insufficient fees") +// require.True(t, success) + +// // wait for a block confirmation +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // sufficient gas prices (tx passes) +// success, _, _ = testutil.TxSend( +// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), +// fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice)), "-y") +// require.True(t, success) + +// // wait for a block confirmation +// tests.WaitForNextNBlocksTM(1, f.Port) + +// f.Cleanup() +// } + +// func TestCLIFeesDeduction(t *testing.T) { +// t.Parallel() +// f := cli.InitFixtures(t) + +// // start simd server with minimum fees +// minGasPrice, _ := sdk.NewDecFromStr("0.000006") +// proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) +// t.Cleanup(func() { proc.Stop(false) }) + +// // Save key addresses for later use +// fooAddr := f.KeyAddress(cli.KeyFoo) +// barAddr := f.KeyAddress(cli.KeyBar) + +// fooAmt := testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom) + +// // test simulation +// success, _, _ := testutil.TxSend( +// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 1000), +// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "--dry-run") +// require.True(t, success) + +// // Wait for a block +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // ensure state didn't change +// require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) + +// // insufficient funds (coins + fees) tx fails +// largeCoins := sdk.TokensFromConsensusPower(10000000) +// success, stdOut, _ := testutil.TxSend( +// f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.FooDenom, largeCoins), +// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") +// require.Contains(t, stdOut, "insufficient funds") +// require.True(t, success) + +// // Wait for a block +// tests.WaitForNextNBlocksTM(1, f.Port) + +// // ensure state didn't change +// require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) + +// // test success (transfer = coins + fees) +// success, _, _ = testutil.TxSend( +// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 500), +// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") +// require.True(t, success) + +// f.Cleanup() +// } + +// func TestCLIQuerySupply(t *testing.T) { +// t.Parallel() +// f := cli.InitFixtures(t) + +// // start simd server +// proc := f.SDStart() +// t.Cleanup(func() { proc.Stop(false) }) + +// totalSupply := testutil.QueryTotalSupply(f) +// totalSupplyOf := testutil.QueryTotalSupplyOf(f, cli.FooDenom) - require.Equal(t, cli.TotalCoins, totalSupply) - require.True(sdk.IntEq(t, cli.TotalCoins.AmountOf(cli.FooDenom), totalSupplyOf)) +// require.Equal(t, cli.TotalCoins, totalSupply) +// require.True(sdk.IntEq(t, cli.TotalCoins.AmountOf(cli.FooDenom), totalSupplyOf)) - f.Cleanup() -} +// f.Cleanup() +// } diff --git a/x/bank/client/cli/query.go b/x/bank/client/cli/query.go index a310c76112ef..4b3b08b4464a 100644 --- a/x/bank/client/cli/query.go +++ b/x/bank/client/cli/query.go @@ -6,7 +6,6 @@ import ( "strings" "github.com/spf13/cobra" - "github.com/spf13/viper" "github.com/cosmos/cosmos-sdk/client" "github.com/cosmos/cosmos-sdk/client/flags" @@ -20,6 +19,9 @@ const ( flagDenom = "denom" ) +// GetQueryCmd returns the parent command for all x/bank CLi query commands. The +// provided clientCtx should have, at a minimum, a verifier, Tendermint RPC client, +// and marshaler set. func GetQueryCmd(clientCtx client.Context) *cobra.Command { cmd := &cobra.Command{ Use: types.ModuleName, @@ -43,23 +45,34 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { Short: "Query for account balances by address", Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - queryClient := types.NewQueryClient(clientCtx.Init()) + height, err := cmd.Flags().GetInt64(flags.FlagHeight) + if err != nil { + return err + } + + denom, err := cmd.Flags().GetString(flagDenom) + if err != nil { + return err + } + + clientCtx = clientCtx.WithHeight(height) + queryClient := types.NewQueryClient(clientCtx) addr, err := sdk.AccAddressFromBech32(args[0]) if err != nil { return err } - denom := viper.GetString(flagDenom) pageReq := &query.PageRequest{} if denom == "" { params := types.NewQueryAllBalancesRequest(addr, pageReq) + res, err := queryClient.AllBalances(context.Background(), params) if err != nil { return err } - return clientCtx.PrintOutput(res.Balances) + return clientCtx.PrintOutput(res.Balances) } params := types.NewQueryBalanceRequest(addr, denom) @@ -67,6 +80,7 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { if err != nil { return err } + return clientCtx.PrintOutput(res.Balance) }, } From 876bcaa2a64679ea1fbf59eb35744986b43ad5da Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Fri, 26 Jun 2020 14:30:10 -0400 Subject: [PATCH 02/20] remove old tests --- x/bank/client/cli/cli_test.go | 208 ---------------------------------- 1 file changed, 208 deletions(-) diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go index 27c60791eb35..b36f06d14ef0 100644 --- a/x/bank/client/cli/cli_test.go +++ b/x/bank/client/cli/cli_test.go @@ -56,211 +56,3 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { func TestIntegrationTestSuite(t *testing.T) { suite.Run(t, new(IntegrationTestSuite)) } - -// func TestCLISend(t *testing.T) { -// t.Parallel() -// f := cli.InitFixtures(t) - -// // start simd server -// proc := f.SDStart() -// t.Cleanup(func() { proc.Stop(false) }) - -// // Save key addresses for later uspackage testse -// fooAddr := f.KeyAddress(cli.KeyFoo) -// barAddr := f.KeyAddress(cli.KeyBar) - -// startTokens := sdk.TokensFromConsensusPower(50) -// require.Equal(t, startTokens, testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - -// sendTokens := sdk.TokensFromConsensusPower(10) - -// // It does not allow to send in offline mode -// success, _, stdErr := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y", "--offline") -// require.Contains(t, stdErr, "no RPC client is defined in offline mode") -// require.False(f.T, success) -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Send some tokens from one account to the other -// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Ensure account balances match expected -// require.Equal(t, sendTokens.String(), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom).String()) -// require.Equal(t, startTokens.Sub(sendTokens).String(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom).String()) - -// // Test --dry-run -// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--dry-run") -// require.True(t, success) - -// // Test --generate-only -// success, stdout, stderr := testutil.TxSend( -// f, fooAddr.String(), barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--generate-only=true", -// ) -// require.Empty(t, stderr) -// require.True(t, success) -// msg := cli.UnmarshalStdTx(f.T, f.Cdc, stdout) -// t.Log(msg) -// require.NotZero(t, msg.Fee.Gas) -// require.Len(t, msg.Msgs, 1) -// require.Len(t, msg.GetSignatures(), 0) - -// // Check state didn't change -// require.Equal(t, startTokens.Sub(sendTokens), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - -// // test autosequencing -// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "-y") -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Ensure account balances match expected -// require.Equal(t, sendTokens.MulRaw(2), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) -// require.Equal(t, startTokens.Sub(sendTokens.MulRaw(2)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - -// // test memo -// testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.Denom, sendTokens), "--memo='testmemo'", "-y") -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Ensure account balances match expected -// require.Equal(t, sendTokens.MulRaw(3), testutil.QueryBalances(f, barAddr).AmountOf(cli.Denom)) -// require.Equal(t, startTokens.Sub(sendTokens.MulRaw(3)), testutil.QueryBalances(f, fooAddr).AmountOf(cli.Denom)) - -// f.Cleanup() -// } - -// func TestCLIMinimumFees(t *testing.T) { -// t.Parallel() -// f := cli.InitFixtures(t) - -// // start simd server with minimum fees -// minGasPrice, _ := sdk.NewDecFromStr("0.000006") -// fees := fmt.Sprintf( -// "--minimum-gas-prices=%s,%s", -// sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice), -// sdk.NewDecCoinFromDec(cli.Fee2Denom, minGasPrice), -// ) -// proc := f.SDStart(fees) -// t.Cleanup(func() { proc.Stop(false) }) - -// barAddr := f.KeyAddress(cli.KeyBar) - -// // Send a transaction that will get rejected -// success, stdOut, _ := testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), "-y") -// require.Contains(t, stdOut, "insufficient fees") -// require.True(f.T, success) -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Ensure tx w/ correct fees pass -// txFees := fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)) -// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.Fee2Denom, 10), txFees, "-y") -// require.True(f.T, success) -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // Ensure tx w/ improper fees fails -// txFees = fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 1)) -// success, _, _ = testutil.TxSend(f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 10), txFees, "-y") -// require.Contains(t, stdOut, "insufficient fees") -// require.True(f.T, success) - -// // Cleanup testing directories -// f.Cleanup() -// } - -// func TestCLIGasPrices(t *testing.T) { -// t.Parallel() -// f := cli.InitFixtures(t) - -// // start simd server with minimum fees -// minGasPrice, _ := sdk.NewDecFromStr("0.000006") -// proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) -// t.Cleanup(func() { proc.Stop(false) }) - -// barAddr := f.KeyAddress(cli.KeyBar) - -// // insufficient gas prices (tx fails) -// badGasPrice, _ := sdk.NewDecFromStr("0.000003") -// success, stdOut, _ := testutil.TxSend( -// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), -// fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, badGasPrice)), "-y") -// require.Contains(t, stdOut, "insufficient fees") -// require.True(t, success) - -// // wait for a block confirmation -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // sufficient gas prices (tx passes) -// success, _, _ = testutil.TxSend( -// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 50), -// fmt.Sprintf("--gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice)), "-y") -// require.True(t, success) - -// // wait for a block confirmation -// tests.WaitForNextNBlocksTM(1, f.Port) - -// f.Cleanup() -// } - -// func TestCLIFeesDeduction(t *testing.T) { -// t.Parallel() -// f := cli.InitFixtures(t) - -// // start simd server with minimum fees -// minGasPrice, _ := sdk.NewDecFromStr("0.000006") -// proc := f.SDStart(fmt.Sprintf("--minimum-gas-prices=%s", sdk.NewDecCoinFromDec(cli.FeeDenom, minGasPrice))) -// t.Cleanup(func() { proc.Stop(false) }) - -// // Save key addresses for later use -// fooAddr := f.KeyAddress(cli.KeyFoo) -// barAddr := f.KeyAddress(cli.KeyBar) - -// fooAmt := testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom) - -// // test simulation -// success, _, _ := testutil.TxSend( -// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 1000), -// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "--dry-run") -// require.True(t, success) - -// // Wait for a block -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // ensure state didn't change -// require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) - -// // insufficient funds (coins + fees) tx fails -// largeCoins := sdk.TokensFromConsensusPower(10000000) -// success, stdOut, _ := testutil.TxSend( -// f, cli.KeyFoo, barAddr, sdk.NewCoin(cli.FooDenom, largeCoins), -// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") -// require.Contains(t, stdOut, "insufficient funds") -// require.True(t, success) - -// // Wait for a block -// tests.WaitForNextNBlocksTM(1, f.Port) - -// // ensure state didn't change -// require.Equal(t, fooAmt.Int64(), testutil.QueryBalances(f, fooAddr).AmountOf(cli.FooDenom).Int64()) - -// // test success (transfer = coins + fees) -// success, _, _ = testutil.TxSend( -// f, cli.KeyFoo, barAddr, sdk.NewInt64Coin(cli.FooDenom, 500), -// fmt.Sprintf("--fees=%s", sdk.NewInt64Coin(cli.FeeDenom, 2)), "-y") -// require.True(t, success) - -// f.Cleanup() -// } - -// func TestCLIQuerySupply(t *testing.T) { -// t.Parallel() -// f := cli.InitFixtures(t) - -// // start simd server -// proc := f.SDStart() -// t.Cleanup(func() { proc.Stop(false) }) - -// totalSupply := testutil.QueryTotalSupply(f) -// totalSupplyOf := testutil.QueryTotalSupplyOf(f, cli.FooDenom) - -// require.Equal(t, cli.TotalCoins, totalSupply) -// require.True(sdk.IntEq(t, cli.TotalCoins.AmountOf(cli.FooDenom), totalSupplyOf)) - -// f.Cleanup() -// } From 98b922678840bb61211bb182b7a14d24ea0f68b5 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Fri, 26 Jun 2020 15:42:45 -0400 Subject: [PATCH 03/20] bank/cli: TestGetBalancesCmd --- x/bank/client/cli/cli_test.go | 58 ------------------ x/bank/client/cli/query.go | 6 +- x/bank/client/cli/query_test.go | 104 ++++++++++++++++++++++++++++++++ 3 files changed, 107 insertions(+), 61 deletions(-) delete mode 100644 x/bank/client/cli/cli_test.go create mode 100644 x/bank/client/cli/query_test.go diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go deleted file mode 100644 index b36f06d14ef0..000000000000 --- a/x/bank/client/cli/cli_test.go +++ /dev/null @@ -1,58 +0,0 @@ -package cli_test - -import ( - "bytes" - "fmt" - "testing" - - "github.com/stretchr/testify/suite" - - "github.com/cosmos/cosmos-sdk/testutil" - "github.com/cosmos/cosmos-sdk/x/bank/client/cli" -) - -type IntegrationTestSuite struct { - suite.Suite - - cfg testutil.Config - network *testutil.Network -} - -func (s *IntegrationTestSuite) SetupSuite() { - s.T().Log("setting up integration test suite") - - cfg := testutil.DefaultConfig() - cfg.NumValidators = 2 - - s.cfg = cfg - s.network = testutil.NewTestNetwork(s.T(), cfg) - - _, err := s.network.WaitForHeight(1) - s.Require().NoError(err) -} - -func (s *IntegrationTestSuite) TearDownSuite() { - s.T().Log("tearing down integration test suite") - s.network.Cleanup() -} - -func (s *IntegrationTestSuite) TestGetBalancesCmd() { - buf := new(bytes.Buffer) - val := s.network.Validators[0] - clientCtx := val.ClientCtx.WithOutput(buf) - - cmd := cli.GetBalancesCmd(clientCtx) - cmd.SetErr(buf) - cmd.SetOut(buf) - s.Require().Error(cmd.Execute()) - - buf.Reset() - - cmd.SetArgs([]string{val.Address.String()}) - s.Require().NoError(cmd.Execute()) - fmt.Println(string(buf.Bytes())) -} - -func TestIntegrationTestSuite(t *testing.T) { - suite.Run(t, new(IntegrationTestSuite)) -} diff --git a/x/bank/client/cli/query.go b/x/bank/client/cli/query.go index 4b3b08b4464a..47b685001df0 100644 --- a/x/bank/client/cli/query.go +++ b/x/bank/client/cli/query.go @@ -16,7 +16,7 @@ import ( ) const ( - flagDenom = "denom" + FlagDenom = "denom" ) // GetQueryCmd returns the parent command for all x/bank CLi query commands. The @@ -50,7 +50,7 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { return err } - denom, err := cmd.Flags().GetString(flagDenom) + denom, err := cmd.Flags().GetString(FlagDenom) if err != nil { return err } @@ -85,7 +85,7 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { }, } - cmd.Flags().String(flagDenom, "", "The specific balance denomination to query for") + cmd.Flags().String(FlagDenom, "", "The specific balance denomination to query for") return flags.GetCommands(cmd)[0] } diff --git a/x/bank/client/cli/query_test.go b/x/bank/client/cli/query_test.go new file mode 100644 index 000000000000..37f407e42d69 --- /dev/null +++ b/x/bank/client/cli/query_test.go @@ -0,0 +1,104 @@ +package cli_test + +import ( + "bytes" + "fmt" + "testing" + + "github.com/stretchr/testify/suite" + + "github.com/cosmos/cosmos-sdk/testutil" + sdk "github.com/cosmos/cosmos-sdk/types" + "github.com/cosmos/cosmos-sdk/x/bank/client/cli" +) + +type IntegrationTestSuite struct { + suite.Suite + + cfg testutil.Config + network *testutil.Network +} + +func (s *IntegrationTestSuite) SetupSuite() { + s.T().Log("setting up integration test suite") + + cfg := testutil.DefaultConfig() + cfg.NumValidators = 2 + + s.cfg = cfg + s.network = testutil.NewTestNetwork(s.T(), cfg) + + _, err := s.network.WaitForHeight(1) + s.Require().NoError(err) +} + +func (s *IntegrationTestSuite) TearDownSuite() { + s.T().Log("tearing down integration test suite") + s.network.Cleanup() +} + +func (s *IntegrationTestSuite) TestGetBalancesCmd() { + buf := new(bytes.Buffer) + val := s.network.Validators[0] + clientCtx := val.ClientCtx.WithOutput(buf) + + cmd := cli.GetBalancesCmd(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) + + testCases := []struct { + name string + args []string + expectErr bool + respType fmt.Stringer + expected fmt.Stringer + }{ + {"no address provided", nil, true, nil, nil}, + { + "total account balance", + []string{val.Address.String()}, + false, + &sdk.Coins{}, + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), s.cfg.AccountTokens), + sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Sub(s.cfg.BondedTokens)), + ), + }, + { + "total account balance of a specific denom", + []string{val.Address.String(), fmt.Sprintf("--%s=%s", cli.FlagDenom, s.cfg.BondDenom)}, + false, + &sdk.Coin{}, + sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Sub(s.cfg.BondedTokens)), + }, + { + "total account balance of a bogus denom", + []string{val.Address.String(), fmt.Sprintf("--%s=foobar", cli.FlagDenom)}, + false, + &sdk.Coin{}, + sdk.NewCoin("foobar", sdk.ZeroInt()), + }, + } + + for _, tc := range testCases { + tc := tc + + s.Run(tc.name, func() { + buf.Reset() + cmd.SetArgs(tc.args) + + err := cmd.Execute() + if tc.expectErr { + s.Require().Error(err) + } else { + s.Require().NoError(err) + s.Require().NoError(clientCtx.JSONMarshaler.UnmarshalJSON(buf.Bytes(), tc.respType)) + s.Require().Equal(tc.expected.String(), tc.respType.String()) + } + }) + } +} + +func TestIntegrationTestSuite(t *testing.T) { + suite.Run(t, new(IntegrationTestSuite)) +} From 26eb2e490c3814c30a6d28857f329011aac29388 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Fri, 26 Jun 2020 15:44:02 -0400 Subject: [PATCH 04/20] default to 1 val --- x/bank/client/cli/query_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/x/bank/client/cli/query_test.go b/x/bank/client/cli/query_test.go index 37f407e42d69..bcd9a3b6b323 100644 --- a/x/bank/client/cli/query_test.go +++ b/x/bank/client/cli/query_test.go @@ -23,7 +23,7 @@ func (s *IntegrationTestSuite) SetupSuite() { s.T().Log("setting up integration test suite") cfg := testutil.DefaultConfig() - cfg.NumValidators = 2 + cfg.NumValidators = 1 s.cfg = cfg s.network = testutil.NewTestNetwork(s.T(), cfg) From 963e41394b12032b7b12c2e8e323270d36aeee88 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Fri, 26 Jun 2020 17:17:43 -0400 Subject: [PATCH 05/20] add query tests --- proto/cosmos/bank/query.proto | 54 +++++++++++----------- x/bank/client/cli/query.go | 42 +++++++++++++---- x/bank/client/cli/query_test.go | 79 +++++++++++++++++++++++++++++++- x/bank/client/rest/query_test.go | 3 +- x/bank/keeper/grpc_query.go | 7 +-- x/bank/types/query.pb.go | 79 ++++++++++++++++---------------- 6 files changed, 182 insertions(+), 82 deletions(-) diff --git a/proto/cosmos/bank/query.proto b/proto/cosmos/bank/query.proto index 773786e4a964..5c63cbc349f8 100644 --- a/proto/cosmos/bank/query.proto +++ b/proto/cosmos/bank/query.proto @@ -9,49 +9,49 @@ option go_package = "github.com/cosmos/cosmos-sdk/x/bank/types"; // Query provides defines the gRPC querier service service Query { - // Balance queries the balance of a single coin for a single account - rpc Balance (QueryBalanceRequest) returns (QueryBalanceResponse) { } + // Balance queries the balance of a single coin for a single account + rpc Balance(QueryBalanceRequest) returns (QueryBalanceResponse) {} - // AllBalances queries the balance of all coins for a single account - rpc AllBalances (QueryAllBalancesRequest) returns (QueryAllBalancesResponse) { } + // AllBalances queries the balance of all coins for a single account + rpc AllBalances(QueryAllBalancesRequest) returns (QueryAllBalancesResponse) {} - // TotalSupply queries the total supply of all coins - rpc TotalSupply (QueryTotalSupplyRequest) returns (QueryTotalSupplyResponse) { } + // TotalSupply queries the total supply of all coins + rpc TotalSupply(QueryTotalSupplyRequest) returns (QueryTotalSupplyResponse) {} - // SupplyOf queries the supply of a single coin - rpc SupplyOf (QuerySupplyOfRequest) returns (QuerySupplyOfResponse) { } + // SupplyOf queries the supply of a single coin + rpc SupplyOf(QuerySupplyOfRequest) returns (QuerySupplyOfResponse) {} } // QueryBalanceRequest is the request type for the Query/Balance RPC method message QueryBalanceRequest { - // address is the address to query balances for - bytes address = 1 [(gogoproto.casttype) = "github.com/cosmos/cosmos-sdk/types.AccAddress"]; + // address is the address to query balances for + bytes address = 1 [(gogoproto.casttype) = "github.com/cosmos/cosmos-sdk/types.AccAddress"]; - // denom is the coin denom to query balances for - string denom = 2; + // denom is the coin denom to query balances for + string denom = 2; } // QueryBalanceResponse is the response type for the Query/Balance RPC method message QueryBalanceResponse { - - // balance is the balance of the coin - cosmos.Coin balance = 1; + // balance is the balance of the coin + cosmos.Coin balance = 1; } // QueryBalanceRequest is the request type for the Query/AllBalances RPC method message QueryAllBalancesRequest { - // address is the address to query balances for - bytes address = 1 [(gogoproto.casttype) = "github.com/cosmos/cosmos-sdk/types.AccAddress"]; + // address is the address to query balances for + bytes address = 1 [(gogoproto.casttype) = "github.com/cosmos/cosmos-sdk/types.AccAddress"]; - cosmos.query.PageRequest req = 2; + cosmos.query.PageRequest req = 2; } // QueryAllBalancesResponse is the response type for the Query/AllBalances RPC method message QueryAllBalancesResponse { - // balances is the balances of the coins - repeated cosmos.Coin balances = 1 [(gogoproto.nullable) = false, (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins"]; + // balances is the balances of the coins + repeated cosmos.Coin balances = 1 + [(gogoproto.nullable) = false, (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins"]; - cosmos.query.PageResponse res = 2; + cosmos.query.PageResponse res = 2; } // QueryTotalSupplyRequest is the request type for the Query/TotalSupply RPC method @@ -59,17 +59,19 @@ message QueryTotalSupplyRequest {} // QueryTotalSupplyResponse is the response type for the Query/TotalSupply RPC method message QueryTotalSupplyResponse { - // supply is the supply of the coins - repeated cosmos.Coin supply = 1 [(gogoproto.nullable) = false, (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins"]; + // supply is the supply of the coins + repeated cosmos.Coin supply = 1 + [(gogoproto.nullable) = false, (gogoproto.castrepeated) = "github.com/cosmos/cosmos-sdk/types.Coins"]; } // QuerySupplyOfRequest is the request type for the Query/SupplyOf RPC method message QuerySupplyOfRequest { - string denom = 1; + string denom = 1; } // QuerySupplyOfResponse is the response type for the Query/SupplyOf RPC method message QuerySupplyOfResponse { - // amount is the supply of the coin - string amount = 1 [(gogoproto.customtype) = "github.com/cosmos/cosmos-sdk/types.Int", (gogoproto.nullable) = false]; + // amount is the supply of the coin + cosmos.Coin amount = 1 + [(gogoproto.customtype) = "github.com/cosmos/cosmos-sdk/types.Coin", (gogoproto.nullable) = false]; } diff --git a/x/bank/client/cli/query.go b/x/bank/client/cli/query.go index 47b685001df0..bd1c4cc95c4f 100644 --- a/x/bank/client/cli/query.go +++ b/x/bank/client/cli/query.go @@ -43,7 +43,17 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { cmd := &cobra.Command{ Use: "balances [address]", Short: "Query for account balances by address", - Args: cobra.ExactArgs(1), + Long: strings.TrimSpace( + fmt.Sprintf(`Query the total balance of an account or of a specific denomination. + +Example: + $ %s query %s balances [address] + $ %s query %s balances [address] --denom=[denom] +`, + version.ClientName, types.ModuleName, version.ClientName, types.ModuleName, + ), + ), + Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { height, err := cmd.Flags().GetInt64(flags.FlagHeight) if err != nil { @@ -91,40 +101,52 @@ func GetBalancesCmd(clientCtx client.Context) *cobra.Command { func GetCmdQueryTotalSupply(clientCtx client.Context) *cobra.Command { cmd := &cobra.Command{ - Use: "total [denom]", - Args: cobra.MaximumNArgs(1), + Use: "total", Short: "Query the total supply of coins of the chain", Long: strings.TrimSpace( - fmt.Sprintf(`Query total supply of coins that are held by accounts in the - chain. + fmt.Sprintf(`Query total supply of coins that are held by accounts in the chain. Example: -$ %s query %s total + $ %s query %s total To query for the total supply of a specific coin denomination use: -$ %s query %s total stake + $ %s query %s total --denom=[denom] `, version.ClientName, types.ModuleName, version.ClientName, types.ModuleName, ), ), RunE: func(cmd *cobra.Command, args []string) error { - queryClient := types.NewQueryClient(clientCtx.Init()) + height, err := cmd.Flags().GetInt64(flags.FlagHeight) + if err != nil { + return err + } - if len(args) == 0 { + denom, err := cmd.Flags().GetString(FlagDenom) + if err != nil { + return err + } + + clientCtx = clientCtx.WithHeight(height) + queryClient := types.NewQueryClient(clientCtx) + + if denom == "" { res, err := queryClient.TotalSupply(context.Background(), &types.QueryTotalSupplyRequest{}) if err != nil { return err } + return clientCtx.PrintOutput(res.Supply) } - res, err := queryClient.SupplyOf(context.Background(), &types.QuerySupplyOfRequest{Denom: args[0]}) + res, err := queryClient.SupplyOf(context.Background(), &types.QuerySupplyOfRequest{Denom: denom}) if err != nil { return err } + return clientCtx.PrintOutput(res.Amount) }, } + cmd.Flags().String(FlagDenom, "", "The specific balance denomination to query for") return flags.GetCommands(cmd)[0] } diff --git a/x/bank/client/cli/query_test.go b/x/bank/client/cli/query_test.go index bcd9a3b6b323..4f9574cd7e29 100644 --- a/x/bank/client/cli/query_test.go +++ b/x/bank/client/cli/query_test.go @@ -7,6 +7,7 @@ import ( "github.com/stretchr/testify/suite" + "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/testutil" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/x/bank/client/cli" @@ -56,7 +57,10 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { {"no address provided", nil, true, nil, nil}, { "total account balance", - []string{val.Address.String()}, + []string{ + val.Address.String(), + fmt.Sprintf("--%s=1", flags.FlagHeight), + }, false, &sdk.Coins{}, sdk.NewCoins( @@ -66,7 +70,11 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { }, { "total account balance of a specific denom", - []string{val.Address.String(), fmt.Sprintf("--%s=%s", cli.FlagDenom, s.cfg.BondDenom)}, + []string{ + val.Address.String(), + fmt.Sprintf("--%s=%s", cli.FlagDenom, s.cfg.BondDenom), + fmt.Sprintf("--%s=1", flags.FlagHeight), + }, false, &sdk.Coin{}, sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Sub(s.cfg.BondedTokens)), @@ -99,6 +107,73 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { } } +func (s *IntegrationTestSuite) TestGetCmdQueryTotalSupply() { + buf := new(bytes.Buffer) + val := s.network.Validators[0] + clientCtx := val.ClientCtx.WithOutput(buf) + + cmd := cli.GetCmdQueryTotalSupply(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) + + testCases := []struct { + name string + args []string + expectErr bool + respType fmt.Stringer + expected fmt.Stringer + }{ + { + "total supply", + []string{fmt.Sprintf("--%s=1", flags.FlagHeight)}, + false, + &sdk.Coins{}, + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), s.cfg.AccountTokens), + sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Add(sdk.NewInt(10))), + ), + }, + { + "total supply of a specific denomination", + []string{ + fmt.Sprintf("--%s=1", flags.FlagHeight), + fmt.Sprintf("--%s=%s", cli.FlagDenom, s.cfg.BondDenom), + }, + false, + &sdk.Coin{}, + sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Add(sdk.NewInt(10))), + }, + { + "total supply of a bogus denom", + []string{ + fmt.Sprintf("--%s=1", flags.FlagHeight), + fmt.Sprintf("--%s=foobar", cli.FlagDenom), + }, + false, + &sdk.Coin{}, + sdk.NewCoin("foobar", sdk.ZeroInt()), + }, + } + + for _, tc := range testCases { + tc := tc + + s.Run(tc.name, func() { + buf.Reset() + cmd.SetArgs(tc.args) + + err := cmd.Execute() + if tc.expectErr { + s.Require().Error(err) + } else { + s.Require().NoError(err) + s.Require().NoError(clientCtx.JSONMarshaler.UnmarshalJSON(buf.Bytes(), tc.respType), buf.String()) + s.Require().Equal(tc.expected.String(), tc.respType.String()) + } + }) + } +} + func TestIntegrationTestSuite(t *testing.T) { suite.Run(t, new(IntegrationTestSuite)) } diff --git a/x/bank/client/rest/query_test.go b/x/bank/client/rest/query_test.go index d682c868503a..d9206c413023 100644 --- a/x/bank/client/rest/query_test.go +++ b/x/bank/client/rest/query_test.go @@ -96,7 +96,8 @@ func (s *IntegrationTestSuite) TestTotalSupplyHandlerFn() { { "total supply", fmt.Sprintf("%s/bank/total?height=1", baseURL), - &sdk.Coins{}, sdk.NewCoins( + &sdk.Coins{}, + sdk.NewCoins( sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), s.cfg.AccountTokens), sdk.NewCoin(s.cfg.BondDenom, s.cfg.StakingTokens.Add(sdk.NewInt(10))), ), diff --git a/x/bank/keeper/grpc_query.go b/x/bank/keeper/grpc_query.go index b0422682d6a0..9600935440c8 100644 --- a/x/bank/keeper/grpc_query.go +++ b/x/bank/keeper/grpc_query.go @@ -3,11 +3,12 @@ package keeper import ( "context" - "github.com/cosmos/cosmos-sdk/store/prefix" - "github.com/cosmos/cosmos-sdk/types/query" "google.golang.org/grpc/codes" "google.golang.org/grpc/status" + "github.com/cosmos/cosmos-sdk/store/prefix" + "github.com/cosmos/cosmos-sdk/types/query" + sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/x/bank/types" ) @@ -90,5 +91,5 @@ func (q BaseKeeper) SupplyOf(c context.Context, req *types.QuerySupplyOfRequest) ctx := sdk.UnwrapSDKContext(c) supply := q.GetSupply(ctx).GetTotal().AmountOf(req.Denom) - return &types.QuerySupplyOfResponse{Amount: supply}, nil + return &types.QuerySupplyOfResponse{Amount: sdk.NewCoin(req.Denom, supply)}, nil } diff --git a/x/bank/types/query.pb.go b/x/bank/types/query.pb.go index 4c49242bd5aa..20e450ef04c5 100644 --- a/x/bank/types/query.pb.go +++ b/x/bank/types/query.pb.go @@ -371,7 +371,7 @@ func (m *QuerySupplyOfRequest) GetDenom() string { // QuerySupplyOfResponse is the response type for the Query/SupplyOf RPC method type QuerySupplyOfResponse struct { // amount is the supply of the coin - Amount github_com_cosmos_cosmos_sdk_types.Int `protobuf:"bytes,1,opt,name=amount,proto3,customtype=github.com/cosmos/cosmos-sdk/types.Int" json:"amount"` + Amount github_com_cosmos_cosmos_sdk_types.Coin `protobuf:"bytes,1,opt,name=amount,proto3,customtype=github.com/cosmos/cosmos-sdk/types.Coin" json:"amount"` } func (m *QuerySupplyOfResponse) Reset() { *m = QuerySupplyOfResponse{} } @@ -421,40 +421,40 @@ func init() { func init() { proto.RegisterFile("cosmos/bank/query.proto", fileDescriptor_1b02ea4db7d9aa9f) } var fileDescriptor_1b02ea4db7d9aa9f = []byte{ - // 527 bytes of a gzipped FileDescriptorProto - 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xb4, 0x94, 0xc1, 0x6e, 0xd3, 0x30, - 0x18, 0xc7, 0x93, 0x4d, 0x6b, 0x87, 0xbb, 0x93, 0x57, 0xb4, 0x2e, 0x12, 0x69, 0xb1, 0x60, 0x2a, - 0x62, 0x4b, 0xa0, 0xdc, 0x91, 0xda, 0x49, 0x48, 0x88, 0x03, 0x23, 0x43, 0x1c, 0x26, 0x24, 0x94, - 0xa6, 0x26, 0x54, 0x4b, 0xed, 0x34, 0x4e, 0xa4, 0xf5, 0x2d, 0x90, 0x78, 0x05, 0x4e, 0x3c, 0xc9, - 0x8e, 0x3b, 0x22, 0x0e, 0x05, 0xb5, 0x37, 0x1e, 0x81, 0x13, 0xb2, 0xfd, 0x65, 0x4a, 0xdb, 0xa8, - 0xec, 0xc0, 0x6e, 0x89, 0xfd, 0xff, 0xfe, 0xfe, 0x7d, 0xfe, 0x7f, 0x09, 0xda, 0x0b, 0xb8, 0x18, - 0x71, 0xe1, 0xf6, 0x7d, 0x76, 0xee, 0x8e, 0x33, 0x9a, 0x4c, 0x9c, 0x38, 0xe1, 0x29, 0xc7, 0x35, - 0xbd, 0xe1, 0xc8, 0x0d, 0xeb, 0x1e, 0xa8, 0x94, 0xc0, 0x8d, 0xfd, 0x70, 0xc8, 0xfc, 0x74, 0xc8, - 0x99, 0xd6, 0x5a, 0xf5, 0x90, 0x87, 0x5c, 0x3d, 0xba, 0xf2, 0x09, 0x56, 0x77, 0xa1, 0x08, 0x8c, - 0xd4, 0x22, 0xb9, 0x40, 0xbb, 0x6f, 0xa4, 0x49, 0xcf, 0x8f, 0x7c, 0x16, 0x50, 0x8f, 0x8e, 0x33, - 0x2a, 0x52, 0xfc, 0x0a, 0x55, 0xfd, 0xc1, 0x20, 0xa1, 0x42, 0x34, 0xcc, 0x96, 0xd9, 0xde, 0xe9, - 0x3d, 0xfd, 0x33, 0x6d, 0x1e, 0x85, 0xc3, 0xf4, 0x53, 0xd6, 0x77, 0x02, 0x3e, 0x72, 0x17, 0xbc, - 0x8e, 0xc4, 0xe0, 0xdc, 0x4d, 0x27, 0x31, 0x15, 0x4e, 0x37, 0x08, 0xba, 0xba, 0xd0, 0xcb, 0x1d, - 0x70, 0x1d, 0x6d, 0x0d, 0x28, 0xe3, 0xa3, 0xc6, 0x46, 0xcb, 0x6c, 0xdf, 0xf1, 0xf4, 0x0b, 0x79, - 0x8e, 0xea, 0x8b, 0x27, 0x8b, 0x98, 0x33, 0x41, 0xf1, 0x01, 0xaa, 0xf6, 0xf5, 0x92, 0x3a, 0xba, - 0xd6, 0xd9, 0x71, 0x80, 0xf8, 0x98, 0x0f, 0x99, 0x97, 0x6f, 0x92, 0x2f, 0x26, 0xda, 0x53, 0x06, - 0xdd, 0x28, 0x02, 0x0f, 0x71, 0x2b, 0xf8, 0x8f, 0xd1, 0x66, 0x42, 0xc7, 0x0a, 0xbe, 0xd6, 0xd9, - 0xcf, 0x61, 0x74, 0x36, 0x27, 0x7e, 0x98, 0xdf, 0x99, 0x27, 0x55, 0xe4, 0xab, 0x89, 0x1a, 0xab, - 0x54, 0xd0, 0xda, 0x19, 0xda, 0x06, 0x7a, 0xc9, 0xb5, 0xb9, 0xdc, 0x5b, 0xef, 0xc9, 0xe5, 0xb4, - 0x69, 0x7c, 0xfb, 0xd9, 0x6c, 0xdf, 0x80, 0x54, 0x16, 0x08, 0xef, 0xda, 0x0f, 0x1f, 0x4a, 0x4a, - 0x01, 0x94, 0x56, 0x19, 0xa5, 0x86, 0x90, 0x98, 0x82, 0xec, 0xc3, 0xdd, 0xbd, 0xe5, 0xa9, 0x1f, - 0x9d, 0x66, 0x71, 0x1c, 0x4d, 0xa0, 0x0d, 0x92, 0x40, 0x03, 0x0b, 0x5b, 0xd0, 0xc0, 0x3b, 0x54, - 0x11, 0x6a, 0xe5, 0x3f, 0xe1, 0x83, 0x1b, 0x39, 0x84, 0x59, 0xd0, 0xc7, 0xbd, 0xfe, 0x98, 0xe7, - 0x78, 0x3d, 0x39, 0x66, 0x71, 0x72, 0x3e, 0xa0, 0xbb, 0x4b, 0x6a, 0xc0, 0x7b, 0x81, 0x2a, 0xfe, - 0x88, 0x67, 0x2c, 0xd5, 0xfa, 0x9e, 0x23, 0x81, 0x7e, 0x4c, 0x9b, 0x07, 0x37, 0x00, 0x7a, 0xc9, - 0x52, 0x0f, 0xaa, 0x3b, 0xbf, 0x37, 0xd0, 0x96, 0x3a, 0x01, 0x9f, 0xa0, 0x2a, 0xa4, 0x88, 0x5b, - 0x4e, 0xe1, 0x0b, 0x74, 0x4a, 0x3e, 0x1a, 0xeb, 0xfe, 0x1a, 0x85, 0x26, 0x24, 0x06, 0x7e, 0x8f, - 0x6a, 0x85, 0xd1, 0xc0, 0x0f, 0x56, 0x6b, 0x56, 0xe7, 0xd9, 0x7a, 0xf8, 0x0f, 0x55, 0xd1, 0xbd, - 0x90, 0x5b, 0x99, 0xfb, 0x6a, 0xe2, 0x65, 0xee, 0x25, 0xe1, 0x13, 0x03, 0x9f, 0xa2, 0xed, 0xfc, - 0xce, 0x71, 0x49, 0xb3, 0x4b, 0xe9, 0x59, 0x64, 0x9d, 0x24, 0x37, 0xed, 0x1d, 0x5f, 0xce, 0x6c, - 0xf3, 0x6a, 0x66, 0x9b, 0xbf, 0x66, 0xb6, 0xf9, 0x79, 0x6e, 0x1b, 0x57, 0x73, 0xdb, 0xf8, 0x3e, - 0xb7, 0x8d, 0xb3, 0x47, 0x6b, 0x63, 0xbb, 0xd0, 0xff, 0x48, 0x95, 0x5e, 0xbf, 0xa2, 0xfe, 0x66, - 0xcf, 0xfe, 0x06, 0x00, 0x00, 0xff, 0xff, 0x6e, 0x62, 0xaf, 0x8a, 0x3f, 0x05, 0x00, 0x00, + // 525 bytes of a gzipped FileDescriptorProto + 0x1f, 0x8b, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x02, 0xff, 0xb4, 0x94, 0xcf, 0x6e, 0xd3, 0x4c, + 0x14, 0xc5, 0xed, 0x56, 0x4d, 0xfa, 0x4d, 0xba, 0x9a, 0xe6, 0x53, 0x53, 0x4b, 0x38, 0x61, 0xc4, + 0x9f, 0x20, 0x5a, 0x1b, 0xc2, 0x1e, 0x29, 0xee, 0x92, 0x05, 0xc5, 0x05, 0x16, 0x15, 0x1b, 0xc7, + 0x19, 0x4c, 0x54, 0x67, 0xc6, 0xf1, 0xd8, 0x52, 0xf3, 0x16, 0x48, 0xbc, 0x02, 0x2b, 0x9e, 0xa4, + 0xcb, 0x2e, 0x11, 0x8b, 0x80, 0x92, 0x1d, 0x8f, 0xc0, 0x0a, 0xcd, 0xcc, 0x75, 0xe5, 0x24, 0x56, + 0xe8, 0x02, 0x76, 0xf6, 0xcc, 0x9d, 0x73, 0x7f, 0xd7, 0xe7, 0x78, 0xd0, 0x41, 0xc8, 0xc5, 0x98, + 0x0b, 0x77, 0x10, 0xb0, 0x0b, 0x77, 0x92, 0xd3, 0x74, 0xea, 0x24, 0x29, 0xcf, 0x38, 0x6e, 0xe8, + 0x0d, 0x47, 0x6e, 0x58, 0x77, 0xa0, 0x4a, 0x15, 0xb8, 0x49, 0x10, 0x8d, 0x58, 0x90, 0x8d, 0x38, + 0xd3, 0xb5, 0x56, 0x33, 0xe2, 0x11, 0x57, 0x8f, 0xae, 0x7c, 0x82, 0xd5, 0x7d, 0x38, 0x04, 0x42, + 0x6a, 0x91, 0x5c, 0xa2, 0xfd, 0x57, 0x52, 0xc4, 0x0b, 0xe2, 0x80, 0x85, 0xd4, 0xa7, 0x93, 0x9c, + 0x8a, 0x0c, 0xbf, 0x40, 0xf5, 0x60, 0x38, 0x4c, 0xa9, 0x10, 0x2d, 0xb3, 0x63, 0x76, 0xf7, 0xbc, + 0xa7, 0xbf, 0x66, 0xed, 0xe3, 0x68, 0x94, 0x7d, 0xc8, 0x07, 0x4e, 0xc8, 0xc7, 0xee, 0x92, 0xd6, + 0xb1, 0x18, 0x5e, 0xb8, 0xd9, 0x34, 0xa1, 0xc2, 0xe9, 0x87, 0x61, 0x5f, 0x1f, 0xf4, 0x0b, 0x05, + 0xdc, 0x44, 0x3b, 0x43, 0xca, 0xf8, 0xb8, 0xb5, 0xd5, 0x31, 0xbb, 0xff, 0xf9, 0xfa, 0x85, 0x3c, + 0x47, 0xcd, 0xe5, 0xce, 0x22, 0xe1, 0x4c, 0x50, 0xfc, 0x00, 0xd5, 0x07, 0x7a, 0x49, 0xb5, 0x6e, + 0xf4, 0xf6, 0x1c, 0x20, 0x3e, 0xe1, 0x23, 0xe6, 0x17, 0x9b, 0xe4, 0x93, 0x89, 0x0e, 0x94, 0x40, + 0x3f, 0x8e, 0x41, 0x43, 0xfc, 0x13, 0xfc, 0xc7, 0x68, 0x3b, 0xa5, 0x13, 0x05, 0xdf, 0xe8, 0x1d, + 0x16, 0x30, 0xda, 0x9b, 0xd3, 0x20, 0x2a, 0xbe, 0x99, 0x2f, 0xab, 0xc8, 0x67, 0x13, 0xb5, 0xd6, + 0xa9, 0x60, 0xb4, 0x73, 0xb4, 0x0b, 0xf4, 0x92, 0x6b, 0x7b, 0x75, 0x36, 0xef, 0xc9, 0xd5, 0xac, + 0x6d, 0x7c, 0xf9, 0xde, 0xee, 0xde, 0x82, 0x54, 0x1e, 0x10, 0xfe, 0x8d, 0x1e, 0x3e, 0x92, 0x94, + 0x02, 0x28, 0xad, 0x2a, 0x4a, 0x0d, 0x21, 0x31, 0x05, 0x39, 0x84, 0x6f, 0xf7, 0x9a, 0x67, 0x41, + 0x7c, 0x96, 0x27, 0x49, 0x3c, 0x85, 0x31, 0x48, 0x0a, 0x03, 0x2c, 0x6d, 0xc1, 0x00, 0x6f, 0x51, + 0x4d, 0xa8, 0x95, 0xbf, 0x84, 0x0f, 0x6a, 0xe4, 0x08, 0xb2, 0xa0, 0xdb, 0xbd, 0x7c, 0x5f, 0xf8, + 0x78, 0x93, 0x1c, 0xb3, 0x9c, 0x1c, 0x86, 0xfe, 0x5f, 0xa9, 0x06, 0xbc, 0x37, 0xa8, 0x16, 0x8c, + 0x79, 0xce, 0xb2, 0xaa, 0xe4, 0x78, 0xae, 0xc4, 0xfb, 0x36, 0x6b, 0x3f, 0xbc, 0x25, 0x9e, 0x0f, + 0x62, 0xbd, 0x9f, 0x5b, 0x68, 0x47, 0x35, 0xc4, 0xa7, 0xa8, 0x0e, 0xa6, 0xe2, 0x8e, 0x53, 0xfa, + 0x21, 0x9d, 0x8a, 0x7f, 0xc8, 0xba, 0xbb, 0xa1, 0x42, 0x03, 0x13, 0x03, 0xbf, 0x43, 0x8d, 0x52, + 0x52, 0xf0, 0xbd, 0xf5, 0x33, 0xeb, 0xf1, 0xb6, 0xee, 0xff, 0xa1, 0xaa, 0xac, 0x5e, 0xb2, 0xb1, + 0x4a, 0x7d, 0x3d, 0x00, 0x55, 0xea, 0x15, 0x59, 0x20, 0x06, 0x3e, 0x43, 0xbb, 0x85, 0x05, 0xb8, + 0x62, 0xd8, 0x15, 0x33, 0x2d, 0xb2, 0xa9, 0xa4, 0x10, 0xf5, 0x4e, 0xae, 0xe6, 0xb6, 0x79, 0x3d, + 0xb7, 0xcd, 0x1f, 0x73, 0xdb, 0xfc, 0xb8, 0xb0, 0x8d, 0xeb, 0x85, 0x6d, 0x7c, 0x5d, 0xd8, 0xc6, + 0xf9, 0xa3, 0x8d, 0xbe, 0x5d, 0xea, 0x2b, 0x53, 0xd9, 0x37, 0xa8, 0xa9, 0xcb, 0xed, 0xd9, 0xef, + 0x00, 0x00, 0x00, 0xff, 0xff, 0x06, 0xd8, 0xbc, 0xab, 0x4e, 0x05, 0x00, 0x00, } // Reference imports to suppress errors if they are not otherwise used. @@ -1782,7 +1782,7 @@ func (m *QuerySupplyOfResponse) Unmarshal(dAtA []byte) error { if wireType != 2 { return fmt.Errorf("proto: wrong wireType = %d for field Amount", wireType) } - var stringLen uint64 + var msglen int for shift := uint(0); ; shift += 7 { if shift >= 64 { return ErrIntOverflowQuery @@ -1792,16 +1792,15 @@ func (m *QuerySupplyOfResponse) Unmarshal(dAtA []byte) error { } b := dAtA[iNdEx] iNdEx++ - stringLen |= uint64(b&0x7F) << shift + msglen |= int(b&0x7F) << shift if b < 0x80 { break } } - intStringLen := int(stringLen) - if intStringLen < 0 { + if msglen < 0 { return ErrInvalidLengthQuery } - postIndex := iNdEx + intStringLen + postIndex := iNdEx + msglen if postIndex < 0 { return ErrInvalidLengthQuery } From a0e5ecd075d35e9c768cf423e85f5e1b4f8a911b Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Sat, 27 Jun 2020 16:27:56 -0400 Subject: [PATCH 06/20] cli: remove indent and use ReadGetCommandFlags --- client/cmd.go | 59 +++++++++++++++++++++++++++++++ client/context.go | 32 ++++++----------- client/context_test.go | 45 ----------------------- client/flags/flags.go | 6 +--- client/keys/add.go | 10 ++---- client/keys/list.go | 2 +- client/keys/parse.go | 8 +---- client/keys/show.go | 1 - client/keys/utils.go | 20 ++--------- client/rpc/block.go | 4 --- client/rpc/status.go | 8 +---- client/rpc/validators.go | 7 ++-- types/rest/rest.go | 14 -------- types/rest/rest_test.go | 21 ++++------- x/auth/client/cli/query.go | 8 +---- x/auth/client/cli/tx_multisign.go | 13 +++---- x/auth/client/cli/tx_sign.go | 27 ++++---------- x/auth/client/tx.go | 18 ++-------- x/bank/client/cli/query.go | 6 ++-- x/gov/client/utils/query.go | 17 --------- 20 files changed, 107 insertions(+), 219 deletions(-) diff --git a/client/cmd.go b/client/cmd.go index df9c5be62f21..138672bf85df 100644 --- a/client/cmd.go +++ b/client/cmd.go @@ -6,6 +6,9 @@ import ( "github.com/pkg/errors" "github.com/spf13/cobra" + "github.com/spf13/pflag" + + "github.com/cosmos/cosmos-sdk/client/flags" ) // ValidateCmd returns unknown command error or Help display if help flag set @@ -55,3 +58,59 @@ func ValidateCmd(cmd *cobra.Command, args []string) error { return cmd.Help() } + +// ReadGetCommandFlags returns an updated Context with fields set based on flags +// defined in GetCommands. An error is returned if any flag query fails. +func ReadGetCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { + if flagSet.Changed(flags.FlagHeight) { + height, err := flagSet.GetInt64(flags.FlagHeight) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithHeight(height) + } + + if flagSet.Changed(flags.FlagTrustNode) { + trustNode, err := flagSet.GetBool(flags.FlagTrustNode) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithTrustNode(trustNode) + } + + if flagSet.Changed(flags.FlagUseLedger) { + useLedger, err := flagSet.GetBool(flags.FlagUseLedger) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithUseLedger(useLedger) + } + + if clientCtx.Keyring == nil && flagSet.Changed(flags.FlagKeyringBackend) { + keyringBackend, err := flagSet.GetString(flags.FlagKeyringBackend) + if err != nil { + return clientCtx, err + } + + kr, err := newKeyringFromFlags(clientCtx, keyringBackend) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithKeyring(kr) + } + + if clientCtx.Client == nil && flagSet.Changed(flags.FlagNode) { + rpcURI, err := flagSet.GetString(flags.FlagNode) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithNodeURI(rpcURI) + } + + return clientCtx, nil +} diff --git a/client/context.go b/client/context.go index 6b4282d7931d..b992c3460c9f 100644 --- a/client/context.go +++ b/client/context.go @@ -43,7 +43,6 @@ type Context struct { Simulate bool GenerateOnly bool Offline bool - Indent bool SkipConfirm bool TxGenerator TxGenerator AccountRetriever AccountRetriever @@ -127,33 +126,29 @@ func (ctx Context) InitWithInputAndFrom(input io.Reader, from string) Context { ctx.BroadcastMode = viper.GetString(flags.FlagBroadcastMode) ctx.Simulate = viper.GetBool(flags.FlagDryRun) ctx.Offline = offline - ctx.Indent = viper.GetBool(flags.FlagIndentResponse) ctx.SkipConfirm = viper.GetBool(flags.FlagSkipConfirmation) + ctx.HomeDir = viper.GetString(flags.FlagHome) + ctx.GenerateOnly = viper.GetBool(flags.FlagGenerateOnly) - homedir := viper.GetString(flags.FlagHome) - genOnly := viper.GetBool(flags.FlagGenerateOnly) backend := viper.GetString(flags.FlagKeyringBackend) if len(backend) == 0 { backend = keyring.BackendMemory } - kr, err := newKeyringFromFlags(backend, homedir, input, genOnly) + kr, err := newKeyringFromFlags(ctx, backend) if err != nil { panic(fmt.Errorf("couldn't acquire keyring: %v", err)) } - fromAddress, fromName, err := GetFromFields(kr, from, genOnly) + fromAddress, fromName, err := GetFromFields(kr, from, ctx.GenerateOnly) if err != nil { fmt.Printf("failed to get from fields: %v\n", err) os.Exit(1) } - ctx.HomeDir = homedir - ctx.Keyring = kr ctx.FromAddress = fromAddress ctx.FromName = fromName - ctx.GenerateOnly = genOnly if offline { return ctx @@ -335,6 +330,7 @@ func (ctx Context) PrintOutput(toPrint interface{}) error { if ctx.OutputFormat == "text" { // handle text format by decoding and re-encoding JSON as YAML var j interface{} + err = json.Unmarshal(out, &j) if err != nil { return err @@ -344,18 +340,9 @@ func (ctx Context) PrintOutput(toPrint interface{}) error { if err != nil { return err } - } else if ctx.Indent { - // To JSON indent, we re-encode the already encoded JSON given there is no - // error. The re-encoded JSON uses the standard library as the initial encoded - // JSON should have the correct output produced by ctx.JSONMarshaler. - out, err = codec.MarshalIndentFromJSON(out) - if err != nil { - return err - } } writer := ctx.Output - // default to stdout if writer == nil { writer = os.Stdout } @@ -409,9 +396,10 @@ func GetFromFields(kr keyring.Keyring, from string, genOnly bool) (sdk.AccAddres return info.GetAddress(), info.GetName(), nil } -func newKeyringFromFlags(backend, homedir string, input io.Reader, genOnly bool) (keyring.Keyring, error) { - if genOnly { - return keyring.New(sdk.KeyringServiceName(), keyring.BackendMemory, homedir, input) +func newKeyringFromFlags(ctx Context, backend string) (keyring.Keyring, error) { + if ctx.GenerateOnly { + return keyring.New(sdk.KeyringServiceName(), keyring.BackendMemory, ctx.HomeDir, ctx.Input) } - return keyring.New(sdk.KeyringServiceName(), backend, homedir, input) + + return keyring.New(sdk.KeyringServiceName(), backend, ctx.HomeDir, ctx.Input) } diff --git a/client/context_test.go b/client/context_test.go index e5598cbcd80e..d6b22e80fc67 100644 --- a/client/context_test.go +++ b/client/context_test.go @@ -106,36 +106,16 @@ func TestContext_PrintOutput(t *testing.T) { buf := &bytes.Buffer{} ctx = ctx.WithOutput(buf) ctx.OutputFormat = "json" - ctx.Indent = false err = ctx.PrintOutput(hasAnimal) require.NoError(t, err) require.Equal(t, `{"animal":{"@type":"/cosmos_sdk.codec.v1.Dog","size":"big","name":"Spot"},"x":"10"} `, string(buf.Bytes())) - // json indent - buf = &bytes.Buffer{} - ctx = ctx.WithOutput(buf) - ctx.OutputFormat = "json" - ctx.Indent = true - err = ctx.PrintOutput(hasAnimal) - require.NoError(t, err) - require.Equal(t, - `{ - "animal": { - "@type": "/cosmos_sdk.codec.v1.Dog", - "name": "Spot", - "size": "big" - }, - "x": "10" -} -`, string(buf.Bytes())) - // yaml buf = &bytes.Buffer{} ctx = ctx.WithOutput(buf) ctx.OutputFormat = "text" - ctx.Indent = false err = ctx.PrintOutput(hasAnimal) require.NoError(t, err) require.Equal(t, @@ -156,41 +136,16 @@ x: "10" buf = &bytes.Buffer{} ctx = ctx.WithOutput(buf) ctx.OutputFormat = "json" - ctx.Indent = false err = ctx.PrintOutput(hasAnimal) require.NoError(t, err) require.Equal(t, `{"type":"testdata/HasAnimal","value":{"animal":{"type":"testdata/Dog","value":{"size":"big","name":"Spot"}},"x":"10"}} `, string(buf.Bytes())) - // json indent - buf = &bytes.Buffer{} - ctx = ctx.WithOutput(buf) - ctx.OutputFormat = "json" - ctx.Indent = true - err = ctx.PrintOutput(hasAnimal) - require.NoError(t, err) - require.Equal(t, - `{ - "type": "testdata/HasAnimal", - "value": { - "animal": { - "type": "testdata/Dog", - "value": { - "name": "Spot", - "size": "big" - } - }, - "x": "10" - } -} -`, string(buf.Bytes())) - // yaml buf = &bytes.Buffer{} ctx = ctx.WithOutput(buf) ctx.OutputFormat = "text" - ctx.Indent = false err = ctx.PrintOutput(hasAnimal) require.NoError(t, err) require.Equal(t, diff --git a/client/flags/flags.go b/client/flags/flags.go index f5c4e9d0c56a..9029cf26e5f8 100644 --- a/client/flags/flags.go +++ b/client/flags/flags.go @@ -57,7 +57,6 @@ const ( FlagDryRun = "dry-run" FlagGenerateOnly = "generate-only" FlagOffline = "offline" - FlagIndentResponse = "indent" FlagOutputDocument = "output-document" // inspired by wget -O FlagSkipConfirmation = "yes" FlagProve = "prove" @@ -77,13 +76,13 @@ var ( // GetCommands adds common flags to query commands func GetCommands(cmds ...*cobra.Command) []*cobra.Command { for _, c := range cmds { - c.Flags().Bool(FlagIndentResponse, false, "Add indent to JSON response") c.Flags().Bool(FlagTrustNode, false, "Trust connected full node (don't verify proofs for responses)") c.Flags().Bool(FlagUseLedger, false, "Use a connected Ledger device") c.Flags().String(FlagNode, "tcp://localhost:26657", ": to Tendermint RPC interface for this chain") c.Flags().Int64(FlagHeight, 0, "Use a specific height to query state at (this can error if the node is pruning state)") c.Flags().String(FlagKeyringBackend, DefaultKeyringBackend, "Select keyring's backend (os|file|kwallet|pass|test)") + // TODO: REMOVE VIPER CALLS! viper.BindPFlag(FlagTrustNode, c.Flags().Lookup(FlagTrustNode)) viper.BindPFlag(FlagUseLedger, c.Flags().Lookup(FlagUseLedger)) viper.BindPFlag(FlagNode, c.Flags().Lookup(FlagNode)) @@ -100,7 +99,6 @@ func GetCommands(cmds ...*cobra.Command) []*cobra.Command { // PostCommands adds common flags for commands to post tx func PostCommands(cmds ...*cobra.Command) []*cobra.Command { for _, c := range cmds { - c.Flags().Bool(FlagIndentResponse, false, "Add indent to JSON response") c.Flags().String(FlagFrom, "", "Name or address of private key with which to sign") c.Flags().Uint64P(FlagAccountNumber, "a", 0, "The account number of the signing account (offline mode only)") c.Flags().Uint64P(FlagSequence, "s", 0, "The sequence number of the signing account (offline mode only)") @@ -137,8 +135,6 @@ func PostCommands(cmds ...*cobra.Command) []*cobra.Command { return cmds } -// Gas flag parsing functions - // GasSetting encapsulates the possible values passed through the --gas flag. type GasSetting struct { Simulate bool diff --git a/client/keys/add.go b/client/keys/add.go index 529fcf4102fb..90946ab98ade 100644 --- a/client/keys/add.go +++ b/client/keys/add.go @@ -78,7 +78,6 @@ the flag --nosort is set. cmd.Flags().Uint32(flagCoinType, sdk.GetConfig().GetCoinType(), "coin type number for HD derivation") cmd.Flags().Uint32(flagAccount, 0, "Account number for HD derivation") cmd.Flags().Uint32(flagIndex, 0, "Address index number for HD derivation") - cmd.Flags().Bool(flags.FlagIndentResponse, false, "Add indent to JSON response") cmd.Flags().String(flagKeyAlgo, string(hd.Secp256k1Type), "Key signing algorithm to generate keys for") return cmd @@ -311,18 +310,13 @@ func printCreate(cmd *cobra.Command, info keyring.Info, showMnemonic bool, mnemo out.Mnemonic = mnemonic } - var jsonString []byte - if viper.GetBool(flags.FlagIndentResponse) { - jsonString, err = KeysCdc.MarshalJSONIndent(out, "", " ") - } else { - jsonString, err = KeysCdc.MarshalJSON(out) - } - + jsonString, err := KeysCdc.MarshalJSON(out) if err != nil { return err } cmd.PrintErrln(string(jsonString)) + default: return fmt.Errorf("invalid output format %s", output) } diff --git a/client/keys/list.go b/client/keys/list.go index 9ec4df43bf4a..4862fccf87fb 100644 --- a/client/keys/list.go +++ b/client/keys/list.go @@ -20,7 +20,7 @@ func ListKeysCmd() *cobra.Command { along with their associated name and address.`, RunE: runListCmd, } - cmd.Flags().Bool(flags.FlagIndentResponse, false, "Add indent to JSON response") + cmd.Flags().BoolP(flagListNames, "n", false, "List names only") return cmd } diff --git a/client/keys/parse.go b/client/keys/parse.go index 220517913708..47424e58e51a 100644 --- a/client/keys/parse.go +++ b/client/keys/parse.go @@ -16,7 +16,6 @@ import ( "github.com/cosmos/cosmos-sdk/types/bech32" - "github.com/cosmos/cosmos-sdk/client/flags" sdk "github.com/cosmos/cosmos-sdk/types" ) @@ -85,7 +84,6 @@ hexadecimal into bech32 cosmos prefixed format and vice versa. Args: cobra.ExactArgs(1), RunE: parseKey, } - cmd.Flags().Bool(flags.FlagIndentResponse, false, "Indent JSON output") return cmd } @@ -145,11 +143,7 @@ func displayParseKeyInfo(w io.Writer, stringer fmt.Stringer) { out, err = yaml.Marshal(&stringer) case OutputFormatJSON: - if viper.GetBool(flags.FlagIndentResponse) { - out, err = KeysCdc.MarshalJSONIndent(stringer, "", " ") - } else { - out = KeysCdc.MustMarshalJSON(stringer) - } + out, err = KeysCdc.MarshalJSON(stringer) } if err != nil { diff --git a/client/keys/show.go b/client/keys/show.go index 465aa0007a89..1d38fe4232ed 100644 --- a/client/keys/show.go +++ b/client/keys/show.go @@ -49,7 +49,6 @@ consisting of all the keys provided by name and multisig threshold.`, cmd.Flags().BoolP(FlagPublicKey, "p", false, "Output the public key only (overrides --output)") cmd.Flags().BoolP(FlagDevice, "d", false, "Output the address in a ledger device") cmd.Flags().Uint(flagMultiSigThreshold, 1, "K out of N required signatures") - cmd.Flags().Bool(flags.FlagIndentResponse, false, "Add indent to JSON response") return cmd } diff --git a/client/keys/utils.go b/client/keys/utils.go index 1a6f1d019207..69f3de80dd6b 100644 --- a/client/keys/utils.go +++ b/client/keys/utils.go @@ -9,7 +9,6 @@ import ( "github.com/tendermint/tendermint/libs/cli" "gopkg.in/yaml.v2" - "github.com/cosmos/cosmos-sdk/client/flags" cryptokeyring "github.com/cosmos/cosmos-sdk/crypto/keyring" ) @@ -45,13 +44,7 @@ func printKeyInfo(w io.Writer, keyInfo cryptokeyring.Info, bechKeyOut bechKeyOut printTextInfos(w, []cryptokeyring.KeyOutput{ko}) case OutputFormatJSON: - var out []byte - var err error - if viper.GetBool(flags.FlagIndentResponse) { - out, err = KeysCdc.MarshalJSONIndent(ko, "", " ") - } else { - out, err = KeysCdc.MarshalJSON(ko) - } + out, err := KeysCdc.MarshalJSON(ko) if err != nil { panic(err) } @@ -71,18 +64,11 @@ func printInfos(w io.Writer, infos []cryptokeyring.Info) { printTextInfos(w, kos) case OutputFormatJSON: - var out []byte - var err error - - if viper.GetBool(flags.FlagIndentResponse) { - out, err = KeysCdc.MarshalJSONIndent(kos, "", " ") - } else { - out, err = KeysCdc.MarshalJSON(kos) - } - + out, err := KeysCdc.MarshalJSON(kos) if err != nil { panic(err) } + fmt.Fprintf(w, "%s", out) } } diff --git a/client/rpc/block.go b/client/rpc/block.go index 4fabdf3ab7b8..68fae1d8f554 100644 --- a/client/rpc/block.go +++ b/client/rpc/block.go @@ -64,10 +64,6 @@ func getBlock(clientCtx client.Context, height *int64) ([]byte, error) { } } - if clientCtx.Indent { - return legacy.Cdc.MarshalJSONIndent(res, "", " ") - } - return legacy.Cdc.MarshalJSON(res) } diff --git a/client/rpc/status.go b/client/rpc/status.go index b85a67c1302a..918c49068c66 100644 --- a/client/rpc/status.go +++ b/client/rpc/status.go @@ -28,7 +28,6 @@ func StatusCommand() *cobra.Command { cmd.Flags().StringP(flags.FlagNode, "n", "tcp://localhost:26657", "Node to connect to") viper.BindPFlag(flags.FlagNode, cmd.Flags().Lookup(flags.FlagNode)) - cmd.Flags().Bool(flags.FlagIndentResponse, false, "Add indent to JSON response") return cmd } @@ -53,12 +52,7 @@ func printNodeStatus(_ *cobra.Command, _ []string) error { return err } - var output []byte - if clientCtx.Indent { - output, err = legacy.Cdc.MarshalJSONIndent(status, "", " ") - } else { - output, err = legacy.Cdc.MarshalJSON(status) - } + output, err := legacy.Cdc.MarshalJSON(status) if err != nil { return err } diff --git a/client/rpc/validators.go b/client/rpc/validators.go index 4e7fc8af12a5..77bc4dafdcd1 100644 --- a/client/rpc/validators.go +++ b/client/rpc/validators.go @@ -56,15 +56,18 @@ func ValidatorCommand(cdc *codec.Codec) *cobra.Command { cmd.Flags().StringP(flags.FlagNode, "n", "tcp://localhost:26657", "Node to connect to") viper.BindPFlag(flags.FlagNode, cmd.Flags().Lookup(flags.FlagNode)) + cmd.Flags().Bool(flags.FlagTrustNode, false, "Trust connected full node (don't verify proofs for responses)") viper.BindPFlag(flags.FlagTrustNode, cmd.Flags().Lookup(flags.FlagTrustNode)) + cmd.Flags().String(flags.FlagKeyringBackend, flags.DefaultKeyringBackend, "Select keyring's backend (os|file|kwallet|pass|test)") viper.BindPFlag(flags.FlagKeyringBackend, cmd.Flags().Lookup(flags.FlagKeyringBackend)) - cmd.Flags().Bool(flags.FlagIndentResponse, false, "indent JSON response") - viper.BindPFlag(flags.FlagIndentResponse, cmd.Flags().Lookup(flags.FlagIndentResponse)) + cmd.Flags().Int(flags.FlagPage, 0, "Query a specific page of paginated results") viper.BindPFlag(flags.FlagPage, cmd.Flags().Lookup(flags.FlagPage)) + cmd.Flags().Int(flags.FlagLimit, 100, "Query number of results returned per page") + viper.BindPFlag(flags.FlagLimit, cmd.Flags().Lookup(flags.FlagLimit)) return cmd } diff --git a/types/rest/rest.go b/types/rest/rest.go index 3825c95049e2..24b6ad9dd50c 100644 --- a/types/rest/rest.go +++ b/types/rest/rest.go @@ -288,11 +288,6 @@ func PostProcessResponseBare(w http.ResponseWriter, ctx client.Context, body int default: resp, err = marshaler.MarshalJSON(body) - - if ctx.Indent && err == nil { - resp, err = codec.MarshalIndentFromJSON(resp) - } - if CheckInternalServerError(w, err) { return } @@ -332,11 +327,6 @@ func PostProcessResponse(w http.ResponseWriter, ctx client.Context, resp interfa default: result, err = marshaler.MarshalJSON(resp) - - if ctx.Indent && err == nil { - result, err = codec.MarshalIndentFromJSON(result) - } - if CheckInternalServerError(w, err) { return } @@ -345,10 +335,6 @@ func PostProcessResponse(w http.ResponseWriter, ctx client.Context, resp interfa wrappedResp := NewResponseWithHeight(ctx.Height, result) output, err := marshaler.MarshalJSON(wrappedResp) - if ctx.Indent && err == nil { - output, err = codec.MarshalIndentFromJSON(output) - } - if CheckInternalServerError(w, err) { return } diff --git a/types/rest/rest_test.go b/types/rest/rest_test.go index e428d8e49a61..533ba664b120 100644 --- a/types/rest/rest_test.go +++ b/types/rest/rest_test.go @@ -223,10 +223,10 @@ func TestProcessPostResponse(t *testing.T) { // check that height returns expected response ctx = ctx.WithHeight(height) - runPostProcessResponse(t, ctx, acc, expectedNoIndent, false) + runPostProcessResponse(t, ctx, acc, expectedNoIndent) // check height with indent - runPostProcessResponse(t, ctx, acc, expectedWithIndent, true) + runPostProcessResponse(t, ctx, acc, expectedWithIndent) } func TestReadRESTReq(t *testing.T) { @@ -329,7 +329,7 @@ func TestPostProcessResponseBare(t *testing.T) { require.Equal(t, "text string", string(got)) // write struct and indent response - clientCtx = client.Context{Indent: true}.WithCodec(codec.New()) + clientCtx = client.Context{}.WithCodec(codec.New()) w = httptest.NewRecorder() data := struct { X int `json:"x"` @@ -351,7 +351,7 @@ func TestPostProcessResponseBare(t *testing.T) { }`, string(got)) // write struct, don't indent response - clientCtx = client.Context{Indent: false}.WithCodec(codec.New()) + clientCtx = client.Context{}.WithCodec(codec.New()) w = httptest.NewRecorder() data = struct { X int `json:"x"` @@ -370,7 +370,7 @@ func TestPostProcessResponseBare(t *testing.T) { require.Equal(t, `{"x":"10","s":"test"}`, string(got)) // test marshalling failure - clientCtx = client.Context{Indent: false}.WithCodec(codec.New()) + clientCtx = client.Context{}.WithCodec(codec.New()) w = httptest.NewRecorder() data2 := badJSONMarshaller{} @@ -396,11 +396,7 @@ func (badJSONMarshaller) MarshalJSON() ([]byte, error) { // asserts that ResponseRecorder returns the expected code and body // runs PostProcessResponse on the objects regular interface and on // the marshalled struct. -func runPostProcessResponse(t *testing.T, ctx client.Context, obj interface{}, expectedBody []byte, indent bool) { - if indent { - ctx.Indent = indent - } - +func runPostProcessResponse(t *testing.T, ctx client.Context, obj interface{}, expectedBody []byte) { // test using regular struct w := httptest.NewRecorder() @@ -417,11 +413,6 @@ func runPostProcessResponse(t *testing.T, ctx client.Context, obj interface{}, e marshalled, err := ctx.Codec.MarshalJSON(obj) require.NoError(t, err) - if indent { - marshalled, err = codec.MarshalIndentFromJSON(marshalled) - require.NoError(t, err) - } - // test using marshalled struct w = httptest.NewRecorder() rest.PostProcessResponse(w, ctx, marshalled) diff --git a/x/auth/client/cli/query.go b/x/auth/client/cli/query.go index 581a00cfe2ce..f0d121d94b7a 100644 --- a/x/auth/client/cli/query.go +++ b/x/auth/client/cli/query.go @@ -155,13 +155,7 @@ $ %s query txs --%s 'message.sender=cosmos1...&message.action=withdraw_delegator return err } - var output []byte - if clientCtx.Indent { - output, err = cdc.MarshalJSONIndent(txs, "", " ") - } else { - output, err = cdc.MarshalJSON(txs) - } - + output, err := cdc.MarshalJSON(txs) if err != nil { return err } diff --git a/x/auth/client/cli/tx_multisign.go b/x/auth/client/cli/tx_multisign.go index dd707f4468d4..5da0b4f2f5f0 100644 --- a/x/auth/client/cli/tx_multisign.go +++ b/x/auth/client/cli/tx_multisign.go @@ -128,18 +128,15 @@ func makeMultiSignCmd(clientCtx client.Context) func(cmd *cobra.Command, args [] newStdSig := types.StdSignature{Signature: sigBz, PubKey: multisigPub.Bytes()} //nolint:staticcheck newTx := types.NewStdTx(stdTx.GetMsgs(), stdTx.Fee, []types.StdSignature{newStdSig}, stdTx.GetMemo()) //nolint:staticcheck - sigOnly := viper.GetBool(flagSigOnly) var json []byte - switch { - case sigOnly && clientCtx.Indent: - json, err = cdc.MarshalJSONIndent(newTx.Signatures[0], "", " ") - case sigOnly && !clientCtx.Indent: + + sigOnly := viper.GetBool(flagSigOnly) + if sigOnly { json, err = cdc.MarshalJSON(newTx.Signatures[0]) - case !sigOnly && clientCtx.Indent: - json, err = cdc.MarshalJSONIndent(newTx, "", " ") - default: + } else { json, err = cdc.MarshalJSON(newTx) } + if err != nil { return err } diff --git a/x/auth/client/cli/tx_sign.go b/x/auth/client/cli/tx_sign.go index 43341469e2ef..4a83b103f589 100644 --- a/x/auth/client/cli/tx_sign.go +++ b/x/auth/client/cli/tx_sign.go @@ -116,7 +116,7 @@ func makeSignBatchCmd(cdc *codec.Codec) func(cmd *cobra.Command, args []string) return err } - json, err := getSignatureJSON(cdc, stdTx, clientCtx.Indent, generateSignatureOnly) + json, err := getSignatureJSON(cdc, stdTx, generateSignatureOnly) if err != nil { return err } @@ -232,7 +232,7 @@ func makeSignCmd(clientCtx client.Context) func(cmd *cobra.Command, args []strin return err } - json, err := getSignatureJSON(clientCtx.Codec, newTx, clientCtx.Indent, generateSignatureOnly) + json, err := getSignatureJSON(clientCtx.Codec, newTx, generateSignatureOnly) if err != nil { return err } @@ -256,23 +256,10 @@ func makeSignCmd(clientCtx client.Context) func(cmd *cobra.Command, args []strin } } -func getSignatureJSON(cdc *codec.Codec, newTx types.StdTx, indent, generateSignatureOnly bool) ([]byte, error) { - switch generateSignatureOnly { - case true: - switch indent { - case true: - return cdc.MarshalJSONIndent(newTx.Signatures[0], "", " ") - - default: - return cdc.MarshalJSON(newTx.Signatures[0]) - } - default: - switch indent { - case true: - return cdc.MarshalJSONIndent(newTx, "", " ") - - default: - return cdc.MarshalJSON(newTx) - } +func getSignatureJSON(cdc *codec.Codec, newTx types.StdTx, generateSignatureOnly bool) ([]byte, error) { + if generateSignatureOnly { + return cdc.MarshalJSON(newTx.Signatures[0]) } + + return cdc.MarshalJSON(newTx) } diff --git a/x/auth/client/tx.go b/x/auth/client/tx.go index a2bad734a4d2..bafdf3b74daf 100644 --- a/x/auth/client/tx.go +++ b/x/auth/client/tx.go @@ -11,10 +11,8 @@ import ( "github.com/gogo/protobuf/jsonpb" "github.com/pkg/errors" - "github.com/spf13/viper" "github.com/cosmos/cosmos-sdk/client" - "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/client/input" "github.com/cosmos/cosmos-sdk/codec" sdk "github.com/cosmos/cosmos-sdk/types" @@ -85,12 +83,9 @@ func CompleteAndBroadcastTxCLI(txBldr authtypes.TxBuilder, clientCtx client.Cont return err } - json := clientCtx.JSONMarshaler.MustMarshalJSON(stdSignMsg) - if viper.GetBool(flags.FlagIndentResponse) { - json, err = codec.MarshalIndentFromJSON(json) - if err != nil { - panic(err) - } + json, err := clientCtx.JSONMarshaler.MarshalJSON(stdSignMsg) + if err != nil { + return err } _, _ = fmt.Fprintf(os.Stderr, "%s\n\n", json) @@ -164,13 +159,6 @@ func PrintUnsignedStdTx(txBldr authtypes.TxBuilder, clientCtx client.Context, ms return err } - if viper.GetBool(flags.FlagIndentResponse) { - json, err = codec.MarshalIndentFromJSON(json) - if err != nil { - return err - } - } - _, _ = fmt.Fprintf(clientCtx.Output, "%s\n", json) return nil } diff --git a/x/bank/client/cli/query.go b/x/bank/client/cli/query.go index bd1c4cc95c4f..f87ed0c99b11 100644 --- a/x/bank/client/cli/query.go +++ b/x/bank/client/cli/query.go @@ -55,7 +55,7 @@ Example: ), Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - height, err := cmd.Flags().GetInt64(flags.FlagHeight) + clientCtx, err := client.ReadGetCommandFlags(clientCtx, cmd.Flags()) if err != nil { return err } @@ -65,7 +65,6 @@ Example: return err } - clientCtx = clientCtx.WithHeight(height) queryClient := types.NewQueryClient(clientCtx) addr, err := sdk.AccAddressFromBech32(args[0]) @@ -116,7 +115,7 @@ To query for the total supply of a specific coin denomination use: ), ), RunE: func(cmd *cobra.Command, args []string) error { - height, err := cmd.Flags().GetInt64(flags.FlagHeight) + clientCtx, err := client.ReadGetCommandFlags(clientCtx, cmd.Flags()) if err != nil { return err } @@ -126,7 +125,6 @@ To query for the total supply of a specific coin denomination use: return err } - clientCtx = clientCtx.WithHeight(height) queryClient := types.NewQueryClient(clientCtx) if denom == "" { diff --git a/x/gov/client/utils/query.go b/x/gov/client/utils/query.go index b4ff81902f5e..1780b2c2aff8 100644 --- a/x/gov/client/utils/query.go +++ b/x/gov/client/utils/query.go @@ -4,7 +4,6 @@ import ( "fmt" "github.com/cosmos/cosmos-sdk/client" - "github.com/cosmos/cosmos-sdk/codec" sdk "github.com/cosmos/cosmos-sdk/types" authclient "github.com/cosmos/cosmos-sdk/x/auth/client" "github.com/cosmos/cosmos-sdk/x/gov/types" @@ -71,10 +70,6 @@ func QueryDepositsByTxQuery(clientCtx client.Context, params types.QueryProposal return nil, err } - if clientCtx.Indent { - return codec.MarshalIndentFromJSON(bz) - } - return bz, nil } @@ -127,10 +122,6 @@ func QueryVotesByTxQuery(clientCtx client.Context, params types.QueryProposalVot return nil, err } - if clientCtx.Indent { - return codec.MarshalIndentFromJSON(bz) - } - return bz, nil } @@ -165,10 +156,6 @@ func QueryVoteByTxQuery(clientCtx client.Context, params types.QueryVoteParams) return nil, err } - if clientCtx.Indent { - return codec.MarshalIndentFromJSON(bz) - } - return bz, nil } } @@ -210,10 +197,6 @@ func QueryDepositByTxQuery(clientCtx client.Context, params types.QueryDepositPa return nil, err } - if clientCtx.Indent { - return codec.MarshalIndentFromJSON(bz) - } - return bz, nil } } From 2f9ae757e572ea095bb0256c3d0501ed34fa660c Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Mon, 29 Jun 2020 15:04:50 -0400 Subject: [PATCH 07/20] Updates --- client/cmd.go | 88 ++++++++++++++----- client/context.go | 23 +++-- client/flags/flags.go | 2 + simapp/cmd/simcli/main.go | 1 + testutil/network.go | 82 ++++++++++------- testutil/util.go | 18 ++-- .../client/cli/{query_test.go => cli_test.go} | 54 ++++++++++++ x/bank/client/cli/query.go | 4 +- x/bank/client/cli/tx.go | 7 +- 9 files changed, 202 insertions(+), 77 deletions(-) rename x/bank/client/cli/{query_test.go => cli_test.go} (77%) diff --git a/client/cmd.go b/client/cmd.go index 138672bf85df..36576c93305d 100644 --- a/client/cmd.go +++ b/client/cmd.go @@ -59,18 +59,10 @@ func ValidateCmd(cmd *cobra.Command, args []string) error { return cmd.Help() } -// ReadGetCommandFlags returns an updated Context with fields set based on flags -// defined in GetCommands. An error is returned if any flag query fails. -func ReadGetCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { - if flagSet.Changed(flags.FlagHeight) { - height, err := flagSet.GetInt64(flags.FlagHeight) - if err != nil { - return clientCtx, err - } - - clientCtx = clientCtx.WithHeight(height) - } - +// ReadPersistentCommandFlags returns a Context with fields set for "persistent" +// flags that do not necessarily change with context. These must be checked if +// the caller explicitly changed the values. +func ReadPersistentCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { if flagSet.Changed(flags.FlagTrustNode) { trustNode, err := flagSet.GetBool(flags.FlagTrustNode) if err != nil { @@ -80,16 +72,7 @@ func ReadGetCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, er clientCtx = clientCtx.WithTrustNode(trustNode) } - if flagSet.Changed(flags.FlagUseLedger) { - useLedger, err := flagSet.GetBool(flags.FlagUseLedger) - if err != nil { - return clientCtx, err - } - - clientCtx = clientCtx.WithUseLedger(useLedger) - } - - if clientCtx.Keyring == nil && flagSet.Changed(flags.FlagKeyringBackend) { + if flagSet.Changed(flags.FlagKeyringBackend) { keyringBackend, err := flagSet.GetString(flags.FlagKeyringBackend) if err != nil { return clientCtx, err @@ -103,7 +86,7 @@ func ReadGetCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, er clientCtx = clientCtx.WithKeyring(kr) } - if clientCtx.Client == nil && flagSet.Changed(flags.FlagNode) { + if flagSet.Changed(flags.FlagNode) { rpcURI, err := flagSet.GetString(flags.FlagNode) if err != nil { return clientCtx, err @@ -114,3 +97,62 @@ func ReadGetCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, er return clientCtx, nil } + +// ReadQueryCommandFlags returns an updated Context with fields set based on flags +// defined in GetCommands. An error is returned if any flag query fails. +// +// Certain flags are naturally command and context dependent, so for these flags +// we do not check if they've been explicitly set by the caller. Other flags can +// be considered "persistent" (e.g. KeyBase or Client) and these should be checked +// if the caller explicitly set those. +func ReadQueryCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { + height, _ := flagSet.GetInt64(flags.FlagHeight) + clientCtx = clientCtx.WithHeight(height) + + useLedger, _ := flagSet.GetBool(flags.FlagUseLedger) + clientCtx = clientCtx.WithUseLedger(useLedger) + + return ReadPersistentCommandFlags(clientCtx, flagSet) +} + +// ReadTxCommandFlags returns an updated Context with fields set based on flags +// defined in PostCommands. An error is returned if any flag query fails. +// +// Certain flags are naturally command and context dependent, so for these flags +// we do not check if they've been explicitly set by the caller. Other flags can +// be considered "persistent" (e.g. KeyBase or Client) and these should be checked +// if the caller explicitly set those. +func ReadTxCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { + clientCtx, err := ReadPersistentCommandFlags(clientCtx, flagSet) + if err != nil { + return clientCtx, err + } + + genOnly, _ := flagSet.GetBool(flags.FlagGenerateOnly) + clientCtx = clientCtx.WithGenerateOnly(genOnly) + + dryRun, _ := flagSet.GetBool(flags.FlagDryRun) + clientCtx = clientCtx.WithSimulation(dryRun) + + offline, _ := flagSet.GetBool(flags.FlagOffline) + clientCtx = clientCtx.WithOffline(offline) + + useLedger, _ := flagSet.GetBool(flags.FlagUseLedger) + clientCtx = clientCtx.WithUseLedger(useLedger) + + bMode, _ := flagSet.GetString(flags.FlagBroadcastMode) + clientCtx = clientCtx.WithBroadcastMode(bMode) + + skipConfirm, _ := flagSet.GetBool(flags.FlagSkipConfirmation) + clientCtx = clientCtx.WithSkipConfirmation(skipConfirm) + + from, _ := flagSet.GetString(flags.FlagFrom) + fromAddr, fromName, err := GetFromFields(clientCtx.Keyring, from, clientCtx.GenerateOnly) + if err != nil { + return clientCtx, err + } + + clientCtx = clientCtx.WithFrom(from).WithFromAddress(fromAddr).WithFromName(fromName) + + return clientCtx, nil +} diff --git a/client/context.go b/client/context.go index b992c3460c9f..60f150200a35 100644 --- a/client/context.go +++ b/client/context.go @@ -46,17 +46,15 @@ type Context struct { SkipConfirm bool TxGenerator TxGenerator AccountRetriever AccountRetriever - - // TODO: API and CLI interfaces are migrating to a single binary (i.e be part of - // the same process of the application). We need to groom through these fields - // and remove any that no longer make sense. - NodeURI string - Verifier tmlite.Verifier + NodeURI string + Verifier tmlite.Verifier // TODO: Deprecated (remove). Codec *codec.Codec } +// TODO: Remove all New* and Init* methods. + // NewContextWithInputAndFrom returns a new initialized Context with parameters from the // command line using Viper. It takes a io.Reader and and key name or address and populates // the FromName and FromAddress field accordingly. It will also create Tendermint verifier @@ -285,6 +283,12 @@ func (ctx Context) WithSimulation(simulate bool) Context { return ctx } +// WithOffline returns a copy of the context with updated Offline value. +func (ctx Context) WithOffline(offline bool) Context { + ctx.Offline = offline + return ctx +} + // WithFromName returns a copy of the context with an updated from account name. func (ctx Context) WithFromName(name string) Context { ctx.FromName = name @@ -305,6 +309,13 @@ func (ctx Context) WithBroadcastMode(mode string) Context { return ctx } +// WithSkipConfirmation returns a copy of the context with an updated SkipConfirm +// value. +func (ctx Context) WithSkipConfirmation(skip bool) Context { + ctx.SkipConfirm = skip + return ctx +} + // WithTxGenerator returns the context with an updated TxGenerator func (ctx Context) WithTxGenerator(generator TxGenerator) Context { ctx.TxGenerator = generator diff --git a/client/flags/flags.go b/client/flags/flags.go index 9029cf26e5f8..06025209989a 100644 --- a/client/flags/flags.go +++ b/client/flags/flags.go @@ -122,6 +122,8 @@ func PostCommands(cmds ...*cobra.Command) []*cobra.Command { "gas limit to set per-transaction; set to %q to calculate required gas automatically (default %d)", GasFlagAuto, DefaultGasLimit, )) + + // TODO: REMOVE VIPER CALLS! viper.BindPFlag(FlagTrustNode, c.Flags().Lookup(FlagTrustNode)) viper.BindPFlag(FlagUseLedger, c.Flags().Lookup(FlagUseLedger)) viper.BindPFlag(FlagNode, c.Flags().Lookup(FlagNode)) diff --git a/simapp/cmd/simcli/main.go b/simapp/cmd/simcli/main.go index 1b3eae7194c9..cfcdbbc1c617 100644 --- a/simapp/cmd/simcli/main.go +++ b/simapp/cmd/simcli/main.go @@ -107,6 +107,7 @@ func queryCmd(config simappparams.EncodingConfig) *cobra.Command { clientCtx = clientCtx. WithJSONMarshaler(config.Marshaler). WithCodec(cdc) + simapp.ModuleBasics.AddQueryCommands(queryCmd, clientCtx) return queryCmd diff --git a/testutil/network.go b/testutil/network.go index b4f3c46a2a5b..d2e820257278 100644 --- a/testutil/network.go +++ b/testutil/network.go @@ -26,6 +26,7 @@ import ( "github.com/cosmos/cosmos-sdk/baseapp" "github.com/cosmos/cosmos-sdk/client" clientkeys "github.com/cosmos/cosmos-sdk/client/keys" + "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/crypto/keyring" "github.com/cosmos/cosmos-sdk/server" "github.com/cosmos/cosmos-sdk/server/api" @@ -39,12 +40,8 @@ import ( stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types" ) -var ( - _, cdc = simapp.MakeCodecs() - - // package-wide network lock to only allow one test network at a time - lock = new(sync.Mutex) -) +// package-wide network lock to only allow one test network at a time +var lock = new(sync.Mutex) // AppConstructor defines a function which accepts a network configuration and // creates an ABCI Application to provide to Tendermint. @@ -61,39 +58,47 @@ func NewSimApp(val Validator) server.Application { // Config defines the necessary configuration used to bootstrap and start an // in-process local testing network. type Config struct { - AppConstructor AppConstructor // the ABCI application constructor - GenesisState map[string]json.RawMessage // custom gensis state to provide - TimeoutCommit time.Duration // the consensus commitment timeout - ChainID string // the network chain-id - NumValidators int // the total number of validators to create and bond - BondDenom string // the staking bond denomination - MinGasPrices string // the minimum gas prices each validator will accept - Passphrase string // the passphrase provided to the test keyring - AccountTokens sdk.Int // the amount of unique validator tokens (e.g. 1000node0) - StakingTokens sdk.Int // the amount of tokens each validator has available to stake - BondedTokens sdk.Int // the amount of tokens each validator stakes - PruningStrategy string // the pruning strategy each validator will have - EnableLogging bool // enable Tendermint logging to STDOUT - CleanupDir bool // remove base temporary directory during cleanup + Codec codec.Marshaler + TxGenerator client.TxGenerator + AccountRetriever client.AccountRetriever + AppConstructor AppConstructor // the ABCI application constructor + GenesisState map[string]json.RawMessage // custom gensis state to provide + TimeoutCommit time.Duration // the consensus commitment timeout + ChainID string // the network chain-id + NumValidators int // the total number of validators to create and bond + BondDenom string // the staking bond denomination + MinGasPrices string // the minimum gas prices each validator will accept + Passphrase string // the passphrase provided to the test keyring + AccountTokens sdk.Int // the amount of unique validator tokens (e.g. 1000node0) + StakingTokens sdk.Int // the amount of tokens each validator has available to stake + BondedTokens sdk.Int // the amount of tokens each validator stakes + PruningStrategy string // the pruning strategy each validator will have + EnableLogging bool // enable Tendermint logging to STDOUT + CleanupDir bool // remove base temporary directory during cleanup } // DefaultConfig returns a sane default configuration suitable for nearly all // testing requirements. func DefaultConfig() Config { + encCfg := simapp.MakeEncodingConfig() + return Config{ - AppConstructor: NewSimApp, - GenesisState: simapp.ModuleBasics.DefaultGenesis(cdc), - TimeoutCommit: 2 * time.Second, - ChainID: "chain-" + tmrand.NewRand().Str(6), - NumValidators: 4, - BondDenom: sdk.DefaultBondDenom, - MinGasPrices: fmt.Sprintf("0.000006%s", sdk.DefaultBondDenom), - Passphrase: clientkeys.DefaultKeyPass, - AccountTokens: sdk.TokensFromConsensusPower(1000), - StakingTokens: sdk.TokensFromConsensusPower(500), - BondedTokens: sdk.TokensFromConsensusPower(100), - PruningStrategy: storetypes.PruningOptionNothing, - CleanupDir: true, + Codec: encCfg.Marshaler, + TxGenerator: encCfg.TxGenerator, + AccountRetriever: authtypes.NewAccountRetriever(encCfg.Marshaler), + AppConstructor: NewSimApp, + GenesisState: simapp.ModuleBasics.DefaultGenesis(encCfg.Marshaler), + TimeoutCommit: 2 * time.Second, + ChainID: "chain-" + tmrand.NewRand().Str(6), + NumValidators: 4, + BondDenom: sdk.DefaultBondDenom, + MinGasPrices: fmt.Sprintf("0.000006%s", sdk.DefaultBondDenom), + Passphrase: clientkeys.DefaultKeyPass, + AccountTokens: sdk.TokensFromConsensusPower(1000), + StakingTokens: sdk.TokensFromConsensusPower(500), + BondedTokens: sdk.TokensFromConsensusPower(100), + PruningStrategy: storetypes.PruningOptionNothing, + CleanupDir: true, } } @@ -279,14 +284,23 @@ func NewTestNetwork(t *testing.T, cfg Config) *Network { signedTx, err := txBldr.SignStdTx(nodeDirName, tx, false) require.NoError(t, err) - txBz, err := cdc.MarshalJSON(signedTx) + txBz, err := cfg.Codec.MarshalJSON(signedTx) require.NoError(t, err) require.NoError(t, writeFile(fmt.Sprintf("%v.json", nodeDirName), gentxsDir, txBz)) srvconfig.WriteConfigFile(filepath.Join(nodeDir, "config/app.toml"), appCfg) + clientCtx := client.Context{}. + WithKeyring(kb). + WithHomeDir(tmCfg.RootDir). + WithChainID(cfg.ChainID). + WithJSONMarshaler(cfg.Codec). + WithTxGenerator(cfg.TxGenerator). + WithAccountRetriever(cfg.AccountRetriever) + network.Validators[i] = &Validator{ AppConfig: appCfg, + ClientCtx: clientCtx, Ctx: ctx, Dir: filepath.Join(network.BaseDir, nodeDirName), NodeID: nodeID, diff --git a/testutil/util.go b/testutil/util.go index eb89e2272b92..8e8a8896feb6 100644 --- a/testutil/util.go +++ b/testutil/util.go @@ -13,7 +13,6 @@ import ( "github.com/tendermint/tendermint/types" tmtime "github.com/tendermint/tendermint/types/time" - "github.com/cosmos/cosmos-sdk/client" "github.com/cosmos/cosmos-sdk/codec" "github.com/cosmos/cosmos-sdk/server/api" authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" @@ -60,10 +59,7 @@ func startInProcess(cfg Config, val *Validator) error { } if val.APIAddress != "" { - val.ClientCtx = client.Context{}. - WithHomeDir(tmCfg.RootDir). - WithChainID(cfg.ChainID). - WithJSONMarshaler(cdc). + val.ClientCtx = val.ClientCtx. WithClient(val.RPCClient). WithTrustNode(true) @@ -110,7 +106,7 @@ func collectGenFiles(cfg Config, vals []*Validator, outputDir string) error { return err } - appState, err := genutil.GenAppStateFromConfig(cdc, tmCfg, initCfg, *genDoc, banktypes.GenesisBalancesIterator{}) + appState, err := genutil.GenAppStateFromConfig(cfg.Codec, tmCfg, initCfg, *genDoc, banktypes.GenesisBalancesIterator{}) if err != nil { return err } @@ -128,19 +124,19 @@ func initGenFiles(cfg Config, genAccounts []authtypes.GenesisAccount, genBalance // set the accounts in the genesis state var authGenState authtypes.GenesisState - cdc.MustUnmarshalJSON(cfg.GenesisState[authtypes.ModuleName], &authGenState) + cfg.Codec.MustUnmarshalJSON(cfg.GenesisState[authtypes.ModuleName], &authGenState) authGenState.Accounts = genAccounts - cfg.GenesisState[authtypes.ModuleName] = cdc.MustMarshalJSON(authGenState) + cfg.GenesisState[authtypes.ModuleName] = cfg.Codec.MustMarshalJSON(authGenState) // set the balances in the genesis state var bankGenState banktypes.GenesisState - cdc.MustUnmarshalJSON(cfg.GenesisState[banktypes.ModuleName], &bankGenState) + cfg.Codec.MustUnmarshalJSON(cfg.GenesisState[banktypes.ModuleName], &bankGenState) bankGenState.Balances = genBalances - cfg.GenesisState[banktypes.ModuleName] = cdc.MustMarshalJSON(bankGenState) + cfg.GenesisState[banktypes.ModuleName] = cfg.Codec.MustMarshalJSON(bankGenState) - appGenStateJSON, err := codec.MarshalJSONIndent(cdc, cfg.GenesisState) + appGenStateJSON, err := codec.MarshalJSONIndent(cfg.Codec, cfg.GenesisState) if err != nil { return err } diff --git a/x/bank/client/cli/query_test.go b/x/bank/client/cli/cli_test.go similarity index 77% rename from x/bank/client/cli/query_test.go rename to x/bank/client/cli/cli_test.go index 4f9574cd7e29..8fab1bf77460 100644 --- a/x/bank/client/cli/query_test.go +++ b/x/bank/client/cli/cli_test.go @@ -174,6 +174,60 @@ func (s *IntegrationTestSuite) TestGetCmdQueryTotalSupply() { } } +func (s *IntegrationTestSuite) TestNewSendTxCmd() { + buf := new(bytes.Buffer) + val := s.network.Validators[0] + clientCtx := val.ClientCtx.WithOutput(buf) + + cmd := cli.NewSendTxCmd(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) + + testCases := []struct { + name string + args []string + expectErr bool + respType fmt.Stringer + }{ + // TODO: Self send gen only + // TODO: Self send invalid fees + // TODO: send invalid gas + { + "valid transaction", + []string{ + val.Address.String(), + val.Address.String(), + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), + sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), + ).String(), + }, + false, + &sdk.TxResponse{}, + }, + } + + for _, tc := range testCases { + tc := tc + + s.Run(tc.name, func() { + buf.Reset() + cmd.SetArgs(tc.args) + + err := cmd.Execute() + if tc.expectErr { + s.Require().Error(err) + } else { + s.Require().NoError(err) + s.Require().NoError(clientCtx.JSONMarshaler.UnmarshalJSON(buf.Bytes(), tc.respType), buf.String()) + + fmt.Println(tc.respType) + // s.Require().Equal(tc.expected.String(), tc.respType.String()) + } + }) + } +} + func TestIntegrationTestSuite(t *testing.T) { suite.Run(t, new(IntegrationTestSuite)) } diff --git a/x/bank/client/cli/query.go b/x/bank/client/cli/query.go index f87ed0c99b11..27fa0f6057dc 100644 --- a/x/bank/client/cli/query.go +++ b/x/bank/client/cli/query.go @@ -55,7 +55,7 @@ Example: ), Args: cobra.ExactArgs(1), RunE: func(cmd *cobra.Command, args []string) error { - clientCtx, err := client.ReadGetCommandFlags(clientCtx, cmd.Flags()) + clientCtx, err := client.ReadQueryCommandFlags(clientCtx, cmd.Flags()) if err != nil { return err } @@ -115,7 +115,7 @@ To query for the total supply of a specific coin denomination use: ), ), RunE: func(cmd *cobra.Command, args []string) error { - clientCtx, err := client.ReadGetCommandFlags(clientCtx, cmd.Flags()) + clientCtx, err := client.ReadQueryCommandFlags(clientCtx, cmd.Flags()) if err != nil { return err } diff --git a/x/bank/client/cli/tx.go b/x/bank/client/cli/tx.go index 8ad3b8057343..675150e284fb 100644 --- a/x/bank/client/cli/tx.go +++ b/x/bank/client/cli/tx.go @@ -32,7 +32,11 @@ func NewSendTxCmd(clientCtx client.Context) *cobra.Command { Short: "Create and/or sign and broadcast a MsgSend transaction", Args: cobra.ExactArgs(3), RunE: func(cmd *cobra.Command, args []string) error { - clientCtx = clientCtx.InitWithInputAndFrom(cmd.InOrStdin(), args[0]) + cmd.Flags().Set(flags.FlagFrom, args[0]) + clientCtx, err := client.ReadTxCommandFlags(clientCtx, cmd.Flags()) + if err != nil { + return err + } toAddr, err := sdk.AccAddressFromBech32(args[1]) if err != nil { @@ -49,6 +53,7 @@ func NewSendTxCmd(clientCtx client.Context) *cobra.Command { return err } + // TODO: Fix stupid GenerateOrBroadcastTx return tx.GenerateOrBroadcastTx(clientCtx, msg) }, } From ec870e029bfd2e8291cf60e623b6f58bbd87086d Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Mon, 29 Jun 2020 15:59:53 -0400 Subject: [PATCH 08/20] test updates --- client/tx/factory.go | 42 ++++++++++++++++++++++++++++++++++- client/tx/tx.go | 8 +++++++ x/bank/client/cli/cli_test.go | 25 ++++++++++++--------- x/bank/client/cli/tx.go | 3 +-- 4 files changed, 65 insertions(+), 13 deletions(-) diff --git a/client/tx/factory.go b/client/tx/factory.go index 9d9490eb6263..aa2457f42605 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -3,6 +3,7 @@ package tx import ( "io" + "github.com/spf13/pflag" "github.com/spf13/viper" "github.com/cosmos/cosmos-sdk/client" @@ -35,6 +36,46 @@ const ( signModeAminoJSON = "amino-json" ) +func NewFactoryFromFlags(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { + signModeStr, _ := flagSet.GetString(flags.FlagSignMode) + + signMode := signing.SignMode_SIGN_MODE_UNSPECIFIED + switch signModeStr { + case signModeDirect: + signMode = signing.SignMode_SIGN_MODE_DIRECT + case signModeAminoJSON: + signMode = signing.SignMode_SIGN_MODE_LEGACY_AMINO_JSON + } + + accNum, _ := flagSet.GetUint64(flags.FlagAccountNumber) + accSeq, _ := flagSet.GetUint64(flags.FlagSequence) + gasAdj, _ := flagSet.GetFloat64(flags.FlagGasAdjustment) + memo, _ := flagSet.GetString(flags.FlagMemo) + + f := Factory{ + txGenerator: clientCtx.TxGenerator, + accountRetriever: clientCtx.AccountRetriever, + keybase: clientCtx.Keyring, + chainID: clientCtx.ChainID, + gas: flags.GasFlagVar.Gas, + simulateAndExecute: flags.GasFlagVar.Simulate, + accountNumber: accNum, + sequence: accSeq, + gasAdjustment: gasAdj, + memo: memo, + signMode: signMode, + } + + feesStr, _ := flagSet.GetString(flags.FlagFees) + f = f.WithFees(feesStr) + + gasPricesStr, _ := flagSet.GetString(flags.FlagGasPrices) + f = f.WithGasPrices(gasPricesStr) + + return f +} + +// TODO: Remove in favor of NewFactoryFromFlags func NewFactoryFromCLI(input io.Reader) Factory { kb, err := keyring.New( sdk.KeyringServiceName(), @@ -62,7 +103,6 @@ func NewFactoryFromCLI(input io.Reader) Factory { gas: flags.GasFlagVar.Gas, gasAdjustment: viper.GetFloat64(flags.FlagGasAdjustment), simulateAndExecute: flags.GasFlagVar.Simulate, - chainID: viper.GetString(flags.FlagChainID), memo: viper.GetString(flags.FlagMemo), signMode: signMode, } diff --git a/client/tx/tx.go b/client/tx/tx.go index 384093852a9b..452e22b8da07 100644 --- a/client/tx/tx.go +++ b/client/tx/tx.go @@ -9,6 +9,7 @@ import ( "strings" "github.com/gogo/protobuf/jsonpb" + "github.com/spf13/pflag" "github.com/cosmos/cosmos-sdk/client" "github.com/cosmos/cosmos-sdk/client/flags" @@ -20,8 +21,15 @@ import ( authsigning "github.com/cosmos/cosmos-sdk/x/auth/signing" ) +func GenerateOrBroadcastTxCLI(clientCtx client.Context, flagSet *pflag.FlagSet, msgs ...sdk.Msg) error { + txf := NewFactoryFromFlags(clientCtx, flagSet) + return GenerateOrBroadcastTxWithFactory(clientCtx, txf, msgs...) +} + // GenerateOrBroadcastTx will either generate and print and unsigned transaction // or sign it and broadcast it returning an error upon failure. +// +// TODO: Remove in favor of GenerateOrBroadcastTxCLI func GenerateOrBroadcastTx(clientCtx client.Context, msgs ...sdk.Msg) error { txf := NewFactoryFromCLI(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) return GenerateOrBroadcastTxWithFactory(clientCtx, txf, msgs...) diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go index 8fab1bf77460..fca682da921d 100644 --- a/x/bank/client/cli/cli_test.go +++ b/x/bank/client/cli/cli_test.go @@ -24,7 +24,7 @@ func (s *IntegrationTestSuite) SetupSuite() { s.T().Log("setting up integration test suite") cfg := testutil.DefaultConfig() - cfg.NumValidators = 1 + cfg.NumValidators = 2 s.cfg = cfg s.network = testutil.NewTestNetwork(s.T(), cfg) @@ -184,26 +184,31 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { cmd.SetOut(buf) testCases := []struct { - name string - args []string - expectErr bool - respType fmt.Stringer + name string + args []string + expectErr bool + respType fmt.Stringer + expectedCode uint32 }{ - // TODO: Self send gen only - // TODO: Self send invalid fees + // TODO: send gen only + // TODO: send invalid fees // TODO: send invalid gas { "valid transaction", []string{ val.Address.String(), - val.Address.String(), + s.network.Validators[1].Address.String(), sdk.NewCoins( sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), ).String(), + fmt.Sprintf("--%s=true", flags.FlagSkipConfirmation), + fmt.Sprintf("--%s=%s", flags.FlagBroadcastMode, flags.BroadcastBlock), + fmt.Sprintf("--%s=%s", flags.FlagFees, sdk.NewCoins(sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10))).String()), }, false, &sdk.TxResponse{}, + 0, }, } @@ -221,8 +226,8 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { s.Require().NoError(err) s.Require().NoError(clientCtx.JSONMarshaler.UnmarshalJSON(buf.Bytes(), tc.respType), buf.String()) - fmt.Println(tc.respType) - // s.Require().Equal(tc.expected.String(), tc.respType.String()) + txResp := tc.respType.(*sdk.TxResponse) + s.Require().Equal(tc.expectedCode, txResp.Code) } }) } diff --git a/x/bank/client/cli/tx.go b/x/bank/client/cli/tx.go index 675150e284fb..853a79856b20 100644 --- a/x/bank/client/cli/tx.go +++ b/x/bank/client/cli/tx.go @@ -53,8 +53,7 @@ func NewSendTxCmd(clientCtx client.Context) *cobra.Command { return err } - // TODO: Fix stupid GenerateOrBroadcastTx - return tx.GenerateOrBroadcastTx(clientCtx, msg) + return tx.GenerateOrBroadcastTxCLI(clientCtx, cmd.Flags(), msg) }, } From 8b7a62443afc9e38c51b477b79b74505a110214b Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Mon, 29 Jun 2020 16:02:44 -0400 Subject: [PATCH 09/20] Updates --- client/tx/factory.go | 6 +++--- client/tx/tx.go | 6 ++++-- x/staking/client/cli/tx.go | 2 +- 3 files changed, 8 insertions(+), 6 deletions(-) diff --git a/client/tx/factory.go b/client/tx/factory.go index aa2457f42605..0c410875c2c0 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -36,7 +36,7 @@ const ( signModeAminoJSON = "amino-json" ) -func NewFactoryFromFlags(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { +func NewFactoryCLI(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { signModeStr, _ := flagSet.GetString(flags.FlagSignMode) signMode := signing.SignMode_SIGN_MODE_UNSPECIFIED @@ -75,8 +75,8 @@ func NewFactoryFromFlags(clientCtx client.Context, flagSet *pflag.FlagSet) Facto return f } -// TODO: Remove in favor of NewFactoryFromFlags -func NewFactoryFromCLI(input io.Reader) Factory { +// TODO: Remove in favor of NewFactoryCLI +func NewFactoryFrom_Deprecated(input io.Reader) Factory { kb, err := keyring.New( sdk.KeyringServiceName(), viper.GetString(flags.FlagKeyringBackend), diff --git a/client/tx/tx.go b/client/tx/tx.go index 452e22b8da07..27ac4a907e36 100644 --- a/client/tx/tx.go +++ b/client/tx/tx.go @@ -21,8 +21,10 @@ import ( authsigning "github.com/cosmos/cosmos-sdk/x/auth/signing" ) +// GenerateOrBroadcastTxCLI will either generate and print and unsigned transaction +// or sign it and broadcast it returning an error upon failure. func GenerateOrBroadcastTxCLI(clientCtx client.Context, flagSet *pflag.FlagSet, msgs ...sdk.Msg) error { - txf := NewFactoryFromFlags(clientCtx, flagSet) + txf := NewFactoryCLI(clientCtx, flagSet) return GenerateOrBroadcastTxWithFactory(clientCtx, txf, msgs...) } @@ -31,7 +33,7 @@ func GenerateOrBroadcastTxCLI(clientCtx client.Context, flagSet *pflag.FlagSet, // // TODO: Remove in favor of GenerateOrBroadcastTxCLI func GenerateOrBroadcastTx(clientCtx client.Context, msgs ...sdk.Msg) error { - txf := NewFactoryFromCLI(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) + txf := NewFactoryFrom_Deprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) return GenerateOrBroadcastTxWithFactory(clientCtx, txf, msgs...) } diff --git a/x/staking/client/cli/tx.go b/x/staking/client/cli/tx.go index 324230c02d16..5d6a66e9acad 100644 --- a/x/staking/client/cli/tx.go +++ b/x/staking/client/cli/tx.go @@ -60,7 +60,7 @@ func NewCreateValidatorCmd(clientCtx client.Context) *cobra.Command { Short: "create new validator initialized with a self-delegation to it", RunE: func(cmd *cobra.Command, args []string) error { clientCtx := clientCtx.InitWithInput(cmd.InOrStdin()) - txf := tx.NewFactoryFromCLI(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) + txf := tx.NewFactoryFrom_Deprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) txf, msg, err := NewBuildCreateValidatorMsg(clientCtx, txf) if err != nil { From cfeaf9468097322e868f12d597724566a75807a1 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Mon, 29 Jun 2020 16:05:41 -0400 Subject: [PATCH 10/20] Add back missing line --- client/tx/factory.go | 1 + 1 file changed, 1 insertion(+) diff --git a/client/tx/factory.go b/client/tx/factory.go index 0c410875c2c0..5a46514ae186 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -98,6 +98,7 @@ func NewFactoryFrom_Deprecated(input io.Reader) Factory { f := Factory{ keybase: kb, + chainID: viper.GetString(flags.FlagChainID), accountNumber: viper.GetUint64(flags.FlagAccountNumber), sequence: viper.GetUint64(flags.FlagSequence), gas: flags.GasFlagVar.Gas, From 079019d27023a49b96e6f37ecca417c37f08f3e3 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Mon, 29 Jun 2020 16:31:26 -0400 Subject: [PATCH 11/20] more test cases --- client/flags/flags.go | 3 ++ x/bank/client/cli/cli_test.go | 85 ++++++++++++++++++++++++++++------- 2 files changed, 71 insertions(+), 17 deletions(-) diff --git a/client/flags/flags.go b/client/flags/flags.go index 06025209989a..ad2562bff89a 100644 --- a/client/flags/flags.go +++ b/client/flags/flags.go @@ -118,6 +118,9 @@ func PostCommands(cmds ...*cobra.Command) []*cobra.Command { c.Flags().String(FlagSignMode, "", "Choose sign mode (direct|amino-json), this is an advanced feature") // --gas can accept integers and "simulate" + // + // TODO: Remove usage of var in favor of string as this is technical creating + // a singleton usage pattern and can cause issues in parallel tests. c.Flags().Var(&GasFlagVar, "gas", fmt.Sprintf( "gas limit to set per-transaction; set to %q to calculate required gas automatically (default %d)", GasFlagAuto, DefaultGasLimit, diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go index fca682da921d..8a28e947ef74 100644 --- a/x/bank/client/cli/cli_test.go +++ b/x/bank/client/cli/cli_test.go @@ -10,6 +10,7 @@ import ( "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/testutil" sdk "github.com/cosmos/cosmos-sdk/types" + sdkerrors "github.com/cosmos/cosmos-sdk/types/errors" "github.com/cosmos/cosmos-sdk/x/bank/client/cli" ) @@ -24,7 +25,7 @@ func (s *IntegrationTestSuite) SetupSuite() { s.T().Log("setting up integration test suite") cfg := testutil.DefaultConfig() - cfg.NumValidators = 2 + cfg.NumValidators = 1 s.cfg = cfg s.network = testutil.NewTestNetwork(s.T(), cfg) @@ -43,10 +44,6 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { val := s.network.Validators[0] clientCtx := val.ClientCtx.WithOutput(buf) - cmd := cli.GetBalancesCmd(clientCtx) - cmd.SetErr(buf) - cmd.SetOut(buf) - testCases := []struct { name string args []string @@ -93,6 +90,10 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { s.Run(tc.name, func() { buf.Reset() + + cmd := cli.GetBalancesCmd(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) cmd.SetArgs(tc.args) err := cmd.Execute() @@ -112,10 +113,6 @@ func (s *IntegrationTestSuite) TestGetCmdQueryTotalSupply() { val := s.network.Validators[0] clientCtx := val.ClientCtx.WithOutput(buf) - cmd := cli.GetCmdQueryTotalSupply(clientCtx) - cmd.SetErr(buf) - cmd.SetOut(buf) - testCases := []struct { name string args []string @@ -160,6 +157,10 @@ func (s *IntegrationTestSuite) TestGetCmdQueryTotalSupply() { s.Run(tc.name, func() { buf.Reset() + + cmd := cli.GetCmdQueryTotalSupply(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) cmd.SetArgs(tc.args) err := cmd.Execute() @@ -179,10 +180,6 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { val := s.network.Validators[0] clientCtx := val.ClientCtx.WithOutput(buf) - cmd := cli.NewSendTxCmd(clientCtx) - cmd.SetErr(buf) - cmd.SetOut(buf) - testCases := []struct { name string args []string @@ -190,14 +187,29 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { respType fmt.Stringer expectedCode uint32 }{ - // TODO: send gen only - // TODO: send invalid fees - // TODO: send invalid gas + { + "valid transaction (gen-only)", + []string{ + val.Address.String(), + val.Address.String(), + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), + sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), + ).String(), + fmt.Sprintf("--%s=true", flags.FlagSkipConfirmation), + fmt.Sprintf("--%s=%s", flags.FlagBroadcastMode, flags.BroadcastBlock), + fmt.Sprintf("--%s=%s", flags.FlagFees, sdk.NewCoins(sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10))).String()), + fmt.Sprintf("--%s=true", flags.FlagGenerateOnly), + }, + false, + &sdk.TxResponse{}, + 0, + }, { "valid transaction", []string{ val.Address.String(), - s.network.Validators[1].Address.String(), + val.Address.String(), sdk.NewCoins( sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), @@ -210,6 +222,41 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { &sdk.TxResponse{}, 0, }, + { + "not enough fees", + []string{ + val.Address.String(), + val.Address.String(), + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), + sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), + ).String(), + fmt.Sprintf("--%s=true", flags.FlagSkipConfirmation), + fmt.Sprintf("--%s=%s", flags.FlagBroadcastMode, flags.BroadcastBlock), + fmt.Sprintf("--%s=%s", flags.FlagFees, sdk.NewCoins(sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(1))).String()), + }, + false, + &sdk.TxResponse{}, + sdkerrors.ErrInsufficientFee.ABCICode(), + }, + { + "not enough gas", + []string{ + val.Address.String(), + val.Address.String(), + sdk.NewCoins( + sdk.NewCoin(fmt.Sprintf("%stoken", val.Moniker), sdk.NewInt(10)), + sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10)), + ).String(), + fmt.Sprintf("--%s=true", flags.FlagSkipConfirmation), + fmt.Sprintf("--%s=%s", flags.FlagBroadcastMode, flags.BroadcastBlock), + fmt.Sprintf("--%s=%s", flags.FlagFees, sdk.NewCoins(sdk.NewCoin(s.cfg.BondDenom, sdk.NewInt(10))).String()), + "--gas=10", + }, + false, + &sdk.TxResponse{}, + sdkerrors.ErrOutOfGas.ABCICode(), + }, } for _, tc := range testCases { @@ -217,6 +264,10 @@ func (s *IntegrationTestSuite) TestNewSendTxCmd() { s.Run(tc.name, func() { buf.Reset() + + cmd := cli.NewSendTxCmd(clientCtx) + cmd.SetErr(buf) + cmd.SetOut(buf) cmd.SetArgs(tc.args) err := cmd.Execute() From ba9832104187d02b07c9ab8b730f646b313d53ff Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:04:15 -0400 Subject: [PATCH 12/20] tests: attempt fix --- types/rest/rest_test.go | 5 +---- 1 file changed, 1 insertion(+), 4 deletions(-) diff --git a/types/rest/rest_test.go b/types/rest/rest_test.go index 533ba664b120..786547d8256c 100644 --- a/types/rest/rest_test.go +++ b/types/rest/rest_test.go @@ -345,10 +345,7 @@ func TestPostProcessResponseBare(t *testing.T) { require.NoError(t, err) t.Cleanup(func() { res.Body.Close() }) - require.Equal(t, `{ - "s": "test", - "x": "10" -}`, string(got)) + require.Equal(t, "{\"x\":\"10\",\"s\":\"test\"}", string(got)) // write struct, don't indent response clientCtx = client.Context{}.WithCodec(codec.New()) From dcc5fa7f097c7f0c073290bd6e665198d0442698 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:06:56 -0400 Subject: [PATCH 13/20] lint++ --- client/tx/factory.go | 2 +- client/tx/tx.go | 2 +- x/staking/client/cli/tx.go | 2 +- 3 files changed, 3 insertions(+), 3 deletions(-) diff --git a/client/tx/factory.go b/client/tx/factory.go index 5a46514ae186..767119f00138 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -76,7 +76,7 @@ func NewFactoryCLI(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { } // TODO: Remove in favor of NewFactoryCLI -func NewFactoryFrom_Deprecated(input io.Reader) Factory { +func NewFactoryFromDeprecated(input io.Reader) Factory { kb, err := keyring.New( sdk.KeyringServiceName(), viper.GetString(flags.FlagKeyringBackend), diff --git a/client/tx/tx.go b/client/tx/tx.go index 27ac4a907e36..69b6bc380964 100644 --- a/client/tx/tx.go +++ b/client/tx/tx.go @@ -33,7 +33,7 @@ func GenerateOrBroadcastTxCLI(clientCtx client.Context, flagSet *pflag.FlagSet, // // TODO: Remove in favor of GenerateOrBroadcastTxCLI func GenerateOrBroadcastTx(clientCtx client.Context, msgs ...sdk.Msg) error { - txf := NewFactoryFrom_Deprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) + txf := NewFactoryFromDeprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) return GenerateOrBroadcastTxWithFactory(clientCtx, txf, msgs...) } diff --git a/x/staking/client/cli/tx.go b/x/staking/client/cli/tx.go index 5d6a66e9acad..3c904aae0f5d 100644 --- a/x/staking/client/cli/tx.go +++ b/x/staking/client/cli/tx.go @@ -60,7 +60,7 @@ func NewCreateValidatorCmd(clientCtx client.Context) *cobra.Command { Short: "create new validator initialized with a self-delegation to it", RunE: func(cmd *cobra.Command, args []string) error { clientCtx := clientCtx.InitWithInput(cmd.InOrStdin()) - txf := tx.NewFactoryFrom_Deprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) + txf := tx.NewFactoryFromDeprecated(clientCtx.Input).WithTxGenerator(clientCtx.TxGenerator).WithAccountRetriever(clientCtx.AccountRetriever) txf, msg, err := NewBuildCreateValidatorMsg(clientCtx, txf) if err != nil { From c25fed38b273f445b217f2700ff0529ff24d5927 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:12:54 -0400 Subject: [PATCH 14/20] tests: attempt fix --- types/rest/rest_test.go | 6 ------ 1 file changed, 6 deletions(-) diff --git a/types/rest/rest_test.go b/types/rest/rest_test.go index 786547d8256c..505c51f8176b 100644 --- a/types/rest/rest_test.go +++ b/types/rest/rest_test.go @@ -212,9 +212,6 @@ func TestProcessPostResponse(t *testing.T) { expectedNoIndent, err := ctx.Codec.MarshalJSON(respNoIndent) require.Nil(t, err) - expectedWithIndent, err := codec.MarshalIndentFromJSON(expectedNoIndent) - require.Nil(t, err) - // check that negative height writes an error w := httptest.NewRecorder() ctx = ctx.WithHeight(-1) @@ -224,9 +221,6 @@ func TestProcessPostResponse(t *testing.T) { // check that height returns expected response ctx = ctx.WithHeight(height) runPostProcessResponse(t, ctx, acc, expectedNoIndent) - - // check height with indent - runPostProcessResponse(t, ctx, acc, expectedWithIndent) } func TestReadRESTReq(t *testing.T) { From a73f357fb95063173b815a40a20d5c97ec13ef5d Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:16:32 -0400 Subject: [PATCH 15/20] cl++ --- CHANGELOG.md | 1 + 1 file changed, 1 insertion(+) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6c22ad3160ab..ec6657942a1d 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -63,6 +63,7 @@ older clients. ### API Breaking Changes +* (client) [\#6525](https://github.com/cosmos/cosmos-sdk/pull/6525) Removed support for `indent` in JSON responses. Clients should consider piping to an external tool such as `jq`. * (x/staking) [\#6451](https://github.com/cosmos/cosmos-sdk/pull/6451) `DefaultParamspace` and `ParamKeyTable` in staking module are moved from keeper to types to enforce consistency. * [\#6409](https://github.com/cosmos/cosmos-sdk/pull/6409) Rename all IsEmpty methods to Empty across the codebase and enforce consistency. * [\#6231](https://github.com/cosmos/cosmos-sdk/pull/6231) Simplify `AppModule` interface, `Route` and `NewHandler` methods become only `Route` From 7dbac20858da80b740b16ce6180b1c2ba77fa9db Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:21:27 -0400 Subject: [PATCH 16/20] cl++ --- x/bank/keeper/grpc_query_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/x/bank/keeper/grpc_query_test.go b/x/bank/keeper/grpc_query_test.go index 3902ed4ad9f1..bdd15535bfbb 100644 --- a/x/bank/keeper/grpc_query_test.go +++ b/x/bank/keeper/grpc_query_test.go @@ -127,5 +127,5 @@ func (suite *IntegrationTestSuite) TestQueryTotalSupplyOf() { suite.Require().NoError(err) suite.Require().NotNil(res) - suite.Require().Equal(test1Supply.Amount, res.Amount) + suite.Require().Equal(test1Supply, res.Amount) } From d26123712d4956d921def875dc157520f6794390 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:41:53 -0400 Subject: [PATCH 17/20] tests: attempt fix --- client/tx/factory.go | 15 ++++++++++++++- x/bank/client/testutil/helpers.go | 4 +++- 2 files changed, 17 insertions(+), 2 deletions(-) diff --git a/client/tx/factory.go b/client/tx/factory.go index 767119f00138..9a15486e6102 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -52,10 +52,23 @@ func NewFactoryCLI(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { gasAdj, _ := flagSet.GetFloat64(flags.FlagGasAdjustment) memo, _ := flagSet.GetString(flags.FlagMemo) + kr := clientCtx.Keyring + if kr == nil { + var err error + + krBackend, _ := flagSet.GetString(flags.FlagKeyringBackend) + home, _ := flagSet.GetString(flags.FlagHome) + + kr, err = keyring.New(sdk.KeyringServiceName(), krBackend, home, clientCtx.Input) + if err != nil { + panic(err) + } + } + f := Factory{ txGenerator: clientCtx.TxGenerator, accountRetriever: clientCtx.AccountRetriever, - keybase: clientCtx.Keyring, + keybase: kr, chainID: clientCtx.ChainID, gas: flags.GasFlagVar.Gas, simulateAndExecute: flags.GasFlagVar.Simulate, diff --git a/x/bank/client/testutil/helpers.go b/x/bank/client/testutil/helpers.go index 4c2d1eca1475..dd813affaa67 100644 --- a/x/bank/client/testutil/helpers.go +++ b/x/bank/client/testutil/helpers.go @@ -13,9 +13,11 @@ import ( authtypes "github.com/cosmos/cosmos-sdk/x/auth/types" ) +// TODO: REMOVE OR COMPLETELY REFACTOR THIS FILE. + // TxSend is simcli tx send func TxSend(f *cli.Fixtures, from string, to sdk.AccAddress, amount sdk.Coin, flags ...string) (bool, string, string) { - cmd := fmt.Sprintf("%s tx send --keyring-backend=test %s %s %s %v", f.SimcliBinary, from, + cmd := fmt.Sprintf("%s tx send --chain-id=%s --keyring-backend=test %s %s %s %v", f.SimcliBinary, f.ChainID, from, to, amount, f.Flags()) return cli.ExecuteWriteRetStdStreams(f.T, cli.AddFlags(cmd, flags), clientkeys.DefaultKeyPass) } From 8c81821df8f1227b0a21478d088118a298ea4023 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 09:47:49 -0400 Subject: [PATCH 18/20] tests: attempt fix --- client/cmd.go | 22 ++++++++-------------- 1 file changed, 8 insertions(+), 14 deletions(-) diff --git a/client/cmd.go b/client/cmd.go index 36576c93305d..84ca3926d761 100644 --- a/client/cmd.go +++ b/client/cmd.go @@ -63,20 +63,18 @@ func ValidateCmd(cmd *cobra.Command, args []string) error { // flags that do not necessarily change with context. These must be checked if // the caller explicitly changed the values. func ReadPersistentCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Context, error) { - if flagSet.Changed(flags.FlagTrustNode) { - trustNode, err := flagSet.GetBool(flags.FlagTrustNode) - if err != nil { - return clientCtx, err - } + if flagSet.Changed(flags.FlagChainID) { + chainID, _ := flagSet.GetString(flags.FlagChainID) + clientCtx = clientCtx.WithChainID(chainID) + } + if flagSet.Changed(flags.FlagTrustNode) { + trustNode, _ := flagSet.GetBool(flags.FlagTrustNode) clientCtx = clientCtx.WithTrustNode(trustNode) } if flagSet.Changed(flags.FlagKeyringBackend) { - keyringBackend, err := flagSet.GetString(flags.FlagKeyringBackend) - if err != nil { - return clientCtx, err - } + keyringBackend, _ := flagSet.GetString(flags.FlagKeyringBackend) kr, err := newKeyringFromFlags(clientCtx, keyringBackend) if err != nil { @@ -87,11 +85,7 @@ func ReadPersistentCommandFlags(clientCtx Context, flagSet *pflag.FlagSet) (Cont } if flagSet.Changed(flags.FlagNode) { - rpcURI, err := flagSet.GetString(flags.FlagNode) - if err != nil { - return clientCtx, err - } - + rpcURI, _ := flagSet.GetString(flags.FlagNode) clientCtx = clientCtx.WithNodeURI(rpcURI) } From be638d3144cb774a0eecc0aa01682d4a10d86c43 Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 14:21:59 -0400 Subject: [PATCH 19/20] undo changes --- client/tx/factory.go | 15 +-------------- x/bank/client/testutil/helpers.go | 3 +-- 2 files changed, 2 insertions(+), 16 deletions(-) diff --git a/client/tx/factory.go b/client/tx/factory.go index 9a15486e6102..767119f00138 100644 --- a/client/tx/factory.go +++ b/client/tx/factory.go @@ -52,23 +52,10 @@ func NewFactoryCLI(clientCtx client.Context, flagSet *pflag.FlagSet) Factory { gasAdj, _ := flagSet.GetFloat64(flags.FlagGasAdjustment) memo, _ := flagSet.GetString(flags.FlagMemo) - kr := clientCtx.Keyring - if kr == nil { - var err error - - krBackend, _ := flagSet.GetString(flags.FlagKeyringBackend) - home, _ := flagSet.GetString(flags.FlagHome) - - kr, err = keyring.New(sdk.KeyringServiceName(), krBackend, home, clientCtx.Input) - if err != nil { - panic(err) - } - } - f := Factory{ txGenerator: clientCtx.TxGenerator, accountRetriever: clientCtx.AccountRetriever, - keybase: kr, + keybase: clientCtx.Keyring, chainID: clientCtx.ChainID, gas: flags.GasFlagVar.Gas, simulateAndExecute: flags.GasFlagVar.Simulate, diff --git a/x/bank/client/testutil/helpers.go b/x/bank/client/testutil/helpers.go index dd813affaa67..1a440ce3df5e 100644 --- a/x/bank/client/testutil/helpers.go +++ b/x/bank/client/testutil/helpers.go @@ -17,8 +17,7 @@ import ( // TxSend is simcli tx send func TxSend(f *cli.Fixtures, from string, to sdk.AccAddress, amount sdk.Coin, flags ...string) (bool, string, string) { - cmd := fmt.Sprintf("%s tx send --chain-id=%s --keyring-backend=test %s %s %s %v", f.SimcliBinary, f.ChainID, from, - to, amount, f.Flags()) + cmd := fmt.Sprintf("%s tx send --keyring-backend=test %s %s %s %v", f.SimcliBinary, from, to, amount, f.Flags()) return cli.ExecuteWriteRetStdStreams(f.T, cli.AddFlags(cmd, flags), clientkeys.DefaultKeyPass) } From 66cb9614dd63076a2119370af31b57f52b86fd3a Mon Sep 17 00:00:00 2001 From: Aleksandr Bezobchuk Date: Tue, 30 Jun 2020 14:53:11 -0400 Subject: [PATCH 20/20] fix test --- x/bank/client/cli/cli_test.go | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/x/bank/client/cli/cli_test.go b/x/bank/client/cli/cli_test.go index 8a28e947ef74..baeba0605bcf 100644 --- a/x/bank/client/cli/cli_test.go +++ b/x/bank/client/cli/cli_test.go @@ -51,7 +51,7 @@ func (s *IntegrationTestSuite) TestGetBalancesCmd() { respType fmt.Stringer expected fmt.Stringer }{ - {"no address provided", nil, true, nil, nil}, + {"no address provided", []string{}, true, nil, nil}, { "total account balance", []string{