From 0484a055d3db69d3f81693a7667396b9b18e8a64 Mon Sep 17 00:00:00 2001 From: jongwhan Date: Fri, 18 Sep 2020 20:20:24 +0800 Subject: [PATCH] Problem: no decimal CRO display for account balance (fix #29) move prefix to module add 1_cro_in_carson unit tidy up error names fix unit test --- app/prefix.go | 33 ++++--------- app/prefix_test.go | 17 ++++--- cmd/chain-maind/cmd/root.go | 12 +++-- cmd/chain-maind/cmd/testnet.go | 10 ++-- x/chainmain/module.go | 89 ++++++++++++++++++++++++++++++++-- x/chainmain/prefix.go | 19 ++++++++ 6 files changed, 135 insertions(+), 45 deletions(-) create mode 100644 x/chainmain/prefix.go diff --git a/app/prefix.go b/app/prefix.go index 0515026f3..7cc64eb94 100644 --- a/app/prefix.go +++ b/app/prefix.go @@ -4,41 +4,26 @@ import ( "log" sdk "github.com/cosmos/cosmos-sdk/types" -) - -const ( - CoinType = 394 - FundraiserPath = "44'/394'/0'/0/1" -) - -var ( - AccountAddressPrefix = "cro" - AccountPubKeyPrefix = "cropub" - ValidatorAddressPrefix = "crocncl" - ValidatorPubKeyPrefix = "crocnclpub" - ConsNodeAddressPrefix = "crocnclcons" - ConsNodePubKeyPrefix = "crocnclconspub" - HumanCoinUnit = "cro" - BaseCoinUnit = "basecro" // 10^-8 AKA "carson" + chain "github.com/crypto-com/chain-main/x/chainmain" ) func SetConfig() { config := sdk.GetConfig() - config.SetBech32PrefixForAccount(AccountAddressPrefix, AccountPubKeyPrefix) - config.SetBech32PrefixForValidator(ValidatorAddressPrefix, ValidatorPubKeyPrefix) - config.SetBech32PrefixForConsensusNode(ConsNodeAddressPrefix, ConsNodePubKeyPrefix) + config.SetBech32PrefixForAccount(chain.AccountAddressPrefix, chain.AccountPubKeyPrefix) + config.SetBech32PrefixForValidator(chain.ValidatorAddressPrefix, chain.ValidatorPubKeyPrefix) + config.SetBech32PrefixForConsensusNode(chain.ConsNodeAddressPrefix, chain.ConsNodePubKeyPrefix) - config.SetCoinType(CoinType) - config.SetFullFundraiserPath(FundraiserPath) + config.SetCoinType(chain.CoinType) + config.SetFullFundraiserPath(chain.FundraiserPath) croUnit := sdk.OneDec() - err := sdk.RegisterDenom(HumanCoinUnit, croUnit) + err := sdk.RegisterDenom(chain.HumanCoinUnit, croUnit) if err != nil { log.Fatal(err) } - carsonUnit := sdk.NewDecWithPrec(1, 8) // 10^-8 (carson) - err = sdk.RegisterDenom(BaseCoinUnit, carsonUnit) + carsonUnit := sdk.NewDecWithPrec(1, int64(chain.CroExponential)) // 10^-8 (carson) + err = sdk.RegisterDenom(chain.BaseCoinUnit, carsonUnit) if err != nil { log.Fatal(err) diff --git a/app/prefix_test.go b/app/prefix_test.go index a0d84435e..0997b86f4 100644 --- a/app/prefix_test.go +++ b/app/prefix_test.go @@ -9,6 +9,7 @@ import ( keys "github.com/cosmos/cosmos-sdk/crypto/keyring" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/crypto-com/chain-main/app" + chain "github.com/crypto-com/chain-main/x/chainmain" "github.com/stretchr/testify/require" ) @@ -19,7 +20,7 @@ func TestMnemonic(t *testing.T) { //nolint:lll "point shiver hurt flight fun online hub antenna engine pave chef fantasy front interest poem accident catch load frequent praise elite pet remove used", "", - app.FundraiserPath, + chain.FundraiserPath, hd.Secp256k1, ) require.NoError(t, err) @@ -45,15 +46,15 @@ func TestConversion(t *testing.T) { result sdk.Coin expErr bool }{ - {sdk.NewCoin("foo", sdk.ZeroInt()), app.HumanCoinUnit, sdk.Coin{}, true}, - {sdk.NewCoin(app.HumanCoinUnit, sdk.ZeroInt()), "foo", sdk.Coin{}, true}, - {sdk.NewCoin(app.HumanCoinUnit, sdk.ZeroInt()), "FOO", sdk.Coin{}, true}, + {sdk.NewCoin("foo", sdk.ZeroInt()), chain.HumanCoinUnit, sdk.Coin{}, true}, + {sdk.NewCoin(chain.HumanCoinUnit, sdk.ZeroInt()), "foo", sdk.Coin{}, true}, + {sdk.NewCoin(chain.HumanCoinUnit, sdk.ZeroInt()), "FOO", sdk.Coin{}, true}, - {sdk.NewCoin(app.HumanCoinUnit, sdk.NewInt(5)), - app.BaseCoinUnit, sdk.NewCoin(app.BaseCoinUnit, sdk.NewInt(500000000)), false}, // cro => carson + {sdk.NewCoin(chain.HumanCoinUnit, sdk.NewInt(5)), + chain.BaseCoinUnit, sdk.NewCoin(chain.BaseCoinUnit, sdk.NewInt(500000000)), false}, // cro => carson - {sdk.NewCoin(app.BaseCoinUnit, sdk.NewInt(500000000)), - app.HumanCoinUnit, sdk.NewCoin(app.HumanCoinUnit, sdk.NewInt(5)), false}, // carson => cro + {sdk.NewCoin(chain.BaseCoinUnit, sdk.NewInt(500000000)), + chain.HumanCoinUnit, sdk.NewCoin(chain.HumanCoinUnit, sdk.NewInt(5)), false}, // carson => cro } diff --git a/cmd/chain-maind/cmd/root.go b/cmd/chain-maind/cmd/root.go index 8bc936c65..c565d8b58 100644 --- a/cmd/chain-maind/cmd/root.go +++ b/cmd/chain-maind/cmd/root.go @@ -33,6 +33,8 @@ import ( genutilcli "github.com/cosmos/cosmos-sdk/x/genutil/client/cli" govtypes "github.com/cosmos/cosmos-sdk/x/gov/types" "github.com/crypto-com/chain-main/app" + + chain "github.com/crypto-com/chain-main/x/chainmain" ) // NewRootCmd creates a new root command for chain-maind. It is called once in the @@ -72,7 +74,7 @@ func convertCoin(s string) string { if err != nil { panic(err) } - coin, err = sdk.ConvertCoin(coin, app.BaseCoinUnit) + coin, err = sdk.ConvertCoin(coin, chain.BaseCoinUnit) if err != nil { panic(err) } @@ -85,7 +87,7 @@ func convertCoins(s string) string { panic(err) } for i, coin := range coins { - coins[i], err = sdk.ConvertCoin(coin, app.BaseCoinUnit) + coins[i], err = sdk.ConvertCoin(coin, chain.BaseCoinUnit) if err != nil { panic(err) } @@ -175,17 +177,17 @@ func initRootCmd(rootCmd *cobra.Command, encodingConfig params.EncodingConfig) { "app_state": map[string]interface{}{ "staking": map[string]interface{}{ "params": map[string]string{ - "bond_denom": app.BaseCoinUnit, + "bond_denom": chain.BaseCoinUnit, }, }, "gov": map[string]interface{}{ "deposit_params": map[string]interface{}{ - "min_deposit": sdk.NewCoins(sdk.NewCoin(app.BaseCoinUnit, govtypes.DefaultMinDepositTokens)), + "min_deposit": sdk.NewCoins(sdk.NewCoin(chain.BaseCoinUnit, govtypes.DefaultMinDepositTokens)), }, }, "mint": map[string]interface{}{ "params": map[string]string{ - "mint_denom": app.BaseCoinUnit, + "mint_denom": chain.BaseCoinUnit, }, }, "bank": map[string]interface{}{ diff --git a/cmd/chain-maind/cmd/testnet.go b/cmd/chain-maind/cmd/testnet.go index 73c51b387..3653004fc 100644 --- a/cmd/chain-maind/cmd/testnet.go +++ b/cmd/chain-maind/cmd/testnet.go @@ -12,7 +12,6 @@ import ( "path/filepath" "time" - "github.com/crypto-com/chain-main/app" "github.com/spf13/cobra" tmconfig "github.com/tendermint/tendermint/config" "github.com/tendermint/tendermint/crypto" @@ -37,6 +36,7 @@ import ( govtypes "github.com/cosmos/cosmos-sdk/x/gov/types" minttypes "github.com/cosmos/cosmos-sdk/x/mint/types" stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types" + chain "github.com/crypto-com/chain-main/x/chainmain" ) var ( @@ -383,7 +383,7 @@ func initGenFiles( var stakingGenState stakingtypes.GenesisState clientCtx.JSONMarshaler.MustUnmarshalJSON(appGenState[stakingtypes.ModuleName], &stakingGenState) - stakingGenState.Params.BondDenom = app.BaseCoinUnit + stakingGenState.Params.BondDenom = chain.BaseCoinUnit stakingGenState.Params.UnbondingTime = unbondingTime appGenState[stakingtypes.ModuleName] = clientCtx.JSONMarshaler.MustMarshalJSON(&stakingGenState) @@ -391,14 +391,14 @@ func initGenFiles( // set gov min_deposit in the genesis state var govGenState govtypes.GenesisState clientCtx.JSONMarshaler.MustUnmarshalJSON(appGenState[govtypes.ModuleName], &govGenState) - govGenState.DepositParams.MinDeposit[0].Denom = app.BaseCoinUnit + govGenState.DepositParams.MinDeposit[0].Denom = chain.BaseCoinUnit govGenState.DepositParams.MinDeposit[0].Amount = govtypes.DefaultMinDepositTokens appGenState[govtypes.ModuleName] = clientCtx.JSONMarshaler.MustMarshalJSON(&govGenState) // set mint in the genesis state var mintGenState minttypes.GenesisState clientCtx.JSONMarshaler.MustUnmarshalJSON(appGenState[minttypes.ModuleName], &mintGenState) - mintGenState.Params.MintDenom = app.BaseCoinUnit + mintGenState.Params.MintDenom = chain.BaseCoinUnit appGenState[minttypes.ModuleName] = clientCtx.JSONMarshaler.MustMarshalJSON(&mintGenState) // set the accounts in the genesis state @@ -531,7 +531,7 @@ func writeFile(name string, dir string, contents []byte) error { func parseStakingCoin(coins sdk.Coins, stakingAmount string) (sdk.Coin, error) { stakingCoin := sdk.Coin{ - Denom: app.BaseCoinUnit, + Denom: chain.BaseCoinUnit, Amount: sdk.ZeroInt(), } if stakingAmount == "" { diff --git a/x/chainmain/module.go b/x/chainmain/module.go index 2b32932d7..3049b9c50 100644 --- a/x/chainmain/module.go +++ b/x/chainmain/module.go @@ -1,8 +1,10 @@ package chainmain import ( + "context" "encoding/json" "fmt" + "strings" "github.com/gogo/protobuf/grpc" "github.com/gorilla/mux" @@ -12,10 +14,13 @@ import ( abci "github.com/tendermint/tendermint/abci/types" "github.com/cosmos/cosmos-sdk/client" + "github.com/cosmos/cosmos-sdk/client/flags" "github.com/cosmos/cosmos-sdk/codec" cdctypes "github.com/cosmos/cosmos-sdk/codec/types" sdk "github.com/cosmos/cosmos-sdk/types" "github.com/cosmos/cosmos-sdk/types/module" + "github.com/cosmos/cosmos-sdk/version" + banktypes "github.com/cosmos/cosmos-sdk/x/bank/types" "github.com/crypto-com/chain-main/x/chainmain/keeper" "github.com/crypto-com/chain-main/x/chainmain/types" ) @@ -67,17 +72,95 @@ func (AppModuleBasic) ValidateGenesis(cdc codec.JSONMarshaler, } // RegisterRESTRoutes registers the capability module's REST service handlers. -func (a AppModuleBasic) RegisterRESTRoutes(_ client.Context, _ *mux.Router) {} +func (a AppModuleBasic) RegisterRESTRoutes(clientCtx client.Context, rtr *mux.Router) { + +} // RegisterGRPCRoutes registers the gRPC Gateway routes for the capability module. -func (a AppModuleBasic) RegisterGRPCRoutes(_ client.Context, _ *runtime.ServeMux) { +func (a AppModuleBasic) RegisterGRPCRoutes(clientCtx client.Context, mux *runtime.ServeMux) { + } // GetTxCmd returns the capability module's root tx command. func (a AppModuleBasic) GetTxCmd() *cobra.Command { return nil } +func GetBalancesCmd() *cobra.Command { + cmd := &cobra.Command{ + Use: "balances [address]", + Short: "Query for account balances by address", + 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.AppName, types.ModuleName, version.AppName, types.ModuleName, + ), + ), + Args: cobra.ExactArgs(1), + RunE: func(cmd *cobra.Command, args []string) error { + clientCtx := client.GetClientContextFromCmd(cmd) + clientCtx, queryErr := client.ReadQueryCommandFlags(clientCtx, cmd.Flags()) + clientCtx = clientCtx.WithNodeURI("http://localhost:26657") + if queryErr != nil { + return queryErr + } + + denom := "" + queryClient := banktypes.NewQueryClient(clientCtx) + + addr, addressErr := sdk.AccAddressFromBech32(args[0]) + if addressErr != nil { + return addressErr + } + + pageReq, clientErr := client.ReadPageRequest(cmd.Flags()) + if clientErr != nil { + return clientErr + } + if denom == "" { + params := banktypes.NewQueryAllBalancesRequest(addr, pageReq) + res, allBalancesErr := queryClient.AllBalances(context.Background(), params) + basecro := res.Balances.AmountOf(BaseCoinUnit).Uint64() + carson := uint64(OneCroInCarson) + fmt.Printf("%d.%08d CRO (%d BASECRO)\n", basecro/carson, basecro%carson, basecro) + if allBalancesErr != nil { + return allBalancesErr + } + return nil + } + + params := banktypes.NewQueryBalanceRequest(addr, denom) + res, balancesErr := queryClient.Balance(context.Background(), params) + if balancesErr != nil { + return balancesErr + } + + return clientCtx.PrintOutput(res.Balance) + }, + } + + flags.AddPaginationFlagsToCmd(cmd, "all balances") + + return cmd +} + // GetQueryCmd returns the capability module's root query command. -func (AppModuleBasic) GetQueryCmd() *cobra.Command { return nil } +func (AppModuleBasic) GetQueryCmd() *cobra.Command { + cmd := &cobra.Command{ + Use: types.ModuleName, + Short: "Querying commands for the chain module", + DisableFlagParsing: true, + SuggestionsMinimumDistance: 2, + RunE: client.ValidateCmd, + } + + cmd.AddCommand( + GetBalancesCmd(), + ) + return cmd +} // ---------------------------------------------------------------------------- // AppModule diff --git a/x/chainmain/prefix.go b/x/chainmain/prefix.go new file mode 100644 index 000000000..09d680939 --- /dev/null +++ b/x/chainmain/prefix.go @@ -0,0 +1,19 @@ +package chainmain + +const ( + CoinType = 394 + FundraiserPath = "44'/394'/0'/0/1" +) + +var ( + AccountAddressPrefix = "cro" + AccountPubKeyPrefix = "cropub" + ValidatorAddressPrefix = "crocncl" + ValidatorPubKeyPrefix = "crocnclpub" + ConsNodeAddressPrefix = "crocnclcons" + ConsNodePubKeyPrefix = "crocnclconspub" + HumanCoinUnit = "cro" + BaseCoinUnit = "basecro" // 10^-8 AKA "carson" + CroExponential = 8 // 10^8 + OneCroInCarson = 1_0000_0000 +)