diff --git a/.github/CODEOWNERS b/.github/CODEOWNERS index dcdf7080b8..11f9e598b4 100644 --- a/.github/CODEOWNERS +++ b/.github/CODEOWNERS @@ -4,4 +4,6 @@ * @ebuchman @rigelrozanski @cwgoes # Precious documentation -/docs/ @zramsay @jolesbi +/docs/README.md @zramsay +/docs/DOCS_README.md @zramsay +/docs/.vuepress/ @zramsay diff --git a/PENDING.md b/PENDING.md index bcb7fcd152..a684ea8820 100644 --- a/PENDING.md +++ b/PENDING.md @@ -5,6 +5,7 @@ BREAKING CHANGES * Gaia REST API (`gaiacli advanced rest-server`) * Gaia CLI (`gaiacli`) + - [#3399](https://github.com/cosmos/cosmos-sdk/pull/3399) Add `gaiad validate-genesis` command to facilitate checking of genesis files * Gaia diff --git a/cmd/gaia/cli_test/cli_test.go b/cmd/gaia/cli_test/cli_test.go index 092e09ec52..845f4c95df 100644 --- a/cmd/gaia/cli_test/cli_test.go +++ b/cmd/gaia/cli_test/cli_test.go @@ -982,3 +982,14 @@ func TestSlashingGetParams(t *testing.T) { require.Equal(t, int64(0), sinfo.StartHeight) require.False(t, sinfo.Tombstoned) } + +func TestValidateGenesis(t *testing.T) { + t.Parallel() + f := InitFixtures(t) + + // start gaiad server + proc := f.GDStart() + defer proc.Stop(false) + + f.ValidateGenesis() +} diff --git a/cmd/gaia/cli_test/test_helpers.go b/cmd/gaia/cli_test/test_helpers.go index 2d60ff292d..9b42e592b8 100644 --- a/cmd/gaia/cli_test/test_helpers.go +++ b/cmd/gaia/cli_test/test_helpers.go @@ -205,6 +205,12 @@ func (f *Fixtures) GDTendermint(query string) string { return strings.TrimSpace(stdout) } +// ValidateGenesis runs gaiad validate-genesis +func (f *Fixtures) ValidateGenesis() { + cmd := fmt.Sprintf("gaiad validate-genesis --home=%s", f.GDHome) + executeWriteCheckErr(f.T, cmd) +} + //___________________________________________________________________________________ // gaiacli keys diff --git a/cmd/gaia/cmd/gaiad/main.go b/cmd/gaia/cmd/gaiad/main.go index 4014bef733..0d6e8a92fd 100644 --- a/cmd/gaia/cmd/gaiad/main.go +++ b/cmd/gaia/cmd/gaiad/main.go @@ -43,6 +43,7 @@ func main() { rootCmd.AddCommand(gaiaInit.TestnetFilesCmd(ctx, cdc)) rootCmd.AddCommand(gaiaInit.GenTxCmd(ctx, cdc)) rootCmd.AddCommand(gaiaInit.AddGenesisAccountCmd(ctx, cdc)) + rootCmd.AddCommand(gaiaInit.ValidateGenesisCmd(ctx, cdc)) rootCmd.AddCommand(client.NewCompletionCmd(rootCmd, true)) server.AddCommands(ctx, cdc, rootCmd, newApp, exportAppStateAndTMValidators) diff --git a/cmd/gaia/init/validate_genesis.go b/cmd/gaia/init/validate_genesis.go new file mode 100644 index 0000000000..ed0f6e0a05 --- /dev/null +++ b/cmd/gaia/init/validate_genesis.go @@ -0,0 +1,52 @@ +package init + +import ( + "fmt" + "os" + + "github.com/cosmos/cosmos-sdk/cmd/gaia/app" + "github.com/cosmos/cosmos-sdk/codec" + "github.com/cosmos/cosmos-sdk/server" + "github.com/pkg/errors" + "github.com/spf13/cobra" + "github.com/tendermint/tendermint/types" +) + +// Validate genesis command takes +func ValidateGenesisCmd(ctx *server.Context, cdc *codec.Codec) *cobra.Command { + return &cobra.Command{ + Use: "validate-genesis [file]", + Args: cobra.RangeArgs(0, 1), + Short: "validates the genesis file at the default location or at the location passed as an arg", + RunE: func(cmd *cobra.Command, args []string) (err error) { + + // Load default if passed no args, otherwise load passed file + var genesis string + if len(args) == 0 { + genesis = ctx.Config.GenesisFile() + } else { + genesis = args[0] + } + + //nolint + fmt.Fprintf(os.Stderr, "validating genesis file at %s\n", genesis) + + var genDoc types.GenesisDoc + if genDoc, err = loadGenesisDoc(cdc, genesis); err != nil { + return errors.Errorf("Error loading genesis doc from %s: %s", genesis, err.Error()) + } + + var genstate app.GenesisState + if err = cdc.UnmarshalJSON(genDoc.AppState, &genstate); err != nil { + return errors.Errorf("Error unmarshaling genesis doc %s: %s", genesis, err.Error()) + } + + if err = app.GaiaValidateGenesisState(genstate); err != nil { + return errors.Errorf("Error validating genesis file %s: %s", genesis, err.Error()) + } + + fmt.Printf("File at %s is a valid genesis file for gaiad\n", genesis) + return nil + }, + } +} diff --git a/docs/.vuepress/config.js b/docs/.vuepress/config.js index a007b9fe98..cb5f8cd43c 100644 --- a/docs/.vuepress/config.js +++ b/docs/.vuepress/config.js @@ -21,7 +21,7 @@ module.exports = { }, nav: [ { text: "Back to Cosmos", link: "https://cosmos.network" }, - { text: "RPC", link: "../rpc/" } + { text: "RPC", link: "https://cosmos.network/rpc/" } ], sidebar: [ { diff --git a/x/auth/account.go b/x/auth/account.go index e67e081aea..2bf2fce0c1 100644 --- a/x/auth/account.go +++ b/x/auth/account.go @@ -83,12 +83,20 @@ type BaseAccount struct { // String implements fmt.Stringer func (acc BaseAccount) String() string { - return fmt.Sprintf(`Account %s: + var pubkey string + + if acc.PubKey != nil { + pubkey = sdk.MustBech32ifyAccPub(acc.PubKey) + } + + return fmt.Sprintf(`Account: + Address: %s + Pubkey: %s Coins: %s - PubKey: %s AccountNumber: %d - Sequence: %d`, acc.Address, acc.Coins, - acc.PubKey.Address(), acc.AccountNumber, acc.Sequence) + Sequence: %d`, + acc.Address, pubkey, acc.Coins, acc.AccountNumber, acc.Sequence, + ) } // Prototype function for BaseAccount @@ -183,8 +191,15 @@ type BaseVestingAccount struct { // String implements fmt.Stringer func (bva BaseVestingAccount) String() string { + var pubkey string + + if bva.PubKey != nil { + pubkey = sdk.MustBech32ifyAccPub(bva.PubKey) + } + return fmt.Sprintf(`Vesting Account: - Address: %s + Address: %s + Pubkey: %s Coins: %s AccountNumber: %d Sequence: %d @@ -192,10 +207,8 @@ func (bva BaseVestingAccount) String() string { DelegatedFree: %s DelegatedVesting: %s EndTime: %d `, - bva.Address, bva.Coins, - bva.AccountNumber, bva.Sequence, - bva.OriginalVesting, bva.DelegatedFree, - bva.DelegatedVesting, bva.EndTime, + bva.Address, pubkey, bva.Coins, bva.AccountNumber, bva.Sequence, + bva.OriginalVesting, bva.DelegatedFree, bva.DelegatedVesting, bva.EndTime, ) } @@ -395,8 +408,15 @@ func NewContinuousVestingAccount( } func (cva ContinuousVestingAccount) String() string { + var pubkey string + + if cva.PubKey != nil { + pubkey = sdk.MustBech32ifyAccPub(cva.PubKey) + } + return fmt.Sprintf(`Continuous Vesting Account: - Address: %s + Address: %s + Pubkey: %s Coins: %s AccountNumber: %d Sequence: %d @@ -405,10 +425,9 @@ func (cva ContinuousVestingAccount) String() string { DelegatedVesting: %s StartTime: %d EndTime: %d `, - cva.Address, cva.Coins, - cva.AccountNumber, cva.Sequence, - cva.OriginalVesting, cva.DelegatedFree, - cva.DelegatedVesting, cva.StartTime, cva.EndTime, + cva.Address, pubkey, cva.Coins, cva.AccountNumber, cva.Sequence, + cva.OriginalVesting, cva.DelegatedFree, cva.DelegatedVesting, + cva.StartTime, cva.EndTime, ) }