Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

R4R: Additional gentx verfication #2971

Merged
merged 19 commits into from
Dec 4, 2018
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -152,7 +152,7 @@ godocs:
test: test_unit

test_cli:
@go test -count 1 `go list github.com/cosmos/cosmos-sdk/cmd/gaia/cli_test` -tags=cli_test
@go test -p 4 `go list github.com/cosmos/cosmos-sdk/cmd/gaia/cli_test` -tags=cli_test
alessio marked this conversation as resolved.
Show resolved Hide resolved

test_examples:
@go test -count 1 -p 1 `go list github.com/cosmos/cosmos-sdk/docs/examples/basecoin/cli_test` -tags=cli_test
Expand Down
9 changes: 7 additions & 2 deletions cmd/gaia/app/genesis.go
Original file line number Diff line number Diff line change
Expand Up @@ -209,6 +209,7 @@ func CollectStdTxs(cdc *codec.Codec, moniker string, genTxsDir string, genDoc tm
if err := cdc.UnmarshalJSON(genDoc.AppState, &appState); err != nil {
return appGenTxs, persistentPeers, err
}

addrMap := make(map[string]GenesisAccount, len(appState.Accounts))
for i := 0; i < len(appState.Accounts); i++ {
acc := appState.Accounts[i]
Expand Down Expand Up @@ -257,13 +258,17 @@ func CollectStdTxs(cdc *codec.Codec, moniker string, genTxsDir string, genDoc tm
msg := msgs[0].(stake.MsgCreateValidator)
addr := string(sdk.AccAddress(msg.ValidatorAddr))
acc, ok := addrMap[addr]

if !ok {
return appGenTxs, persistentPeers, fmt.Errorf(
"account %v not in genesis.json: %+v", addr, addrMap)
}

if acc.Coins.AmountOf(msg.Delegation.Denom).LT(msg.Delegation.Amount) {
err = fmt.Errorf("insufficient fund for the delegation: %v < %v",
acc.Coins.AmountOf(msg.Delegation.Denom), msg.Delegation.Amount)
return appGenTxs, persistentPeers, fmt.Errorf(
"insufficient fund for delegation %v: %v < %v",
acc.Address, acc.Coins.AmountOf(msg.Delegation.Denom), msg.Delegation.Amount,
)
}

// exclude itself from persistent peers
Expand Down
112 changes: 49 additions & 63 deletions cmd/gaia/cli_test/cli_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -33,12 +33,12 @@ import (
)

func TestGaiaCLIMinimumFees(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
alexanderbez marked this conversation as resolved.
Show resolved Hide resolved
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server with minimum fees
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --minimum_fees=2feeToken", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v --minimum_fees=2feeToken", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand All @@ -58,12 +58,12 @@ func TestGaiaCLIMinimumFees(t *testing.T) {
}

func TestGaiaCLIFeesDeduction(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server with minimum fees
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --minimum_fees=1fooToken", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v --minimum_fees=1fooToken", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand Down Expand Up @@ -101,13 +101,12 @@ func TestGaiaCLIFeesDeduction(t *testing.T) {
}

func TestGaiaCLISend(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v", gaiadHome, servAddr))

proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v", gaiadHome, servAddr, p2pAddr))
defer proc.Stop(false)
tests.WaitForTMStart(port)
tests.WaitForNextNBlocksTM(2, port)
Expand Down Expand Up @@ -153,12 +152,12 @@ func TestGaiaCLISend(t *testing.T) {
}

func TestGaiaCLIGasAuto(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand Down Expand Up @@ -205,12 +204,12 @@ func TestGaiaCLIGasAuto(t *testing.T) {
}

func TestGaiaCLICreateValidator(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --chain-id=%v --node=%s", gaiacliHome, chainID, servAddr)

// start gaiad server
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand Down Expand Up @@ -303,12 +302,12 @@ func TestGaiaCLICreateValidator(t *testing.T) {
}

func TestGaiaCLISubmitProposal(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand Down Expand Up @@ -357,22 +356,20 @@ func TestGaiaCLISubmitProposal(t *testing.T) {
fooAcc = executeGetAccount(t, fmt.Sprintf("gaiacli query account %s %v", fooAddr, flags))
require.Equal(t, int64(45), fooAcc.GetCoins().AmountOf(stakeTypes.DefaultBondDenom).Int64())

proposal1 := executeGetProposal(t, fmt.Sprintf("gaiacli query gov proposal --proposal-id=1 --output=json %v", flags))
proposal1 := executeGetProposal(t, fmt.Sprintf("gaiacli query gov proposal 1 --output=json %v", flags))
require.Equal(t, uint64(1), proposal1.GetProposalID())
require.Equal(t, gov.StatusDepositPeriod, proposal1.GetStatus())

proposalsQuery, _ = tests.ExecuteT(t, fmt.Sprintf("gaiacli query gov proposals %v", flags), "")
require.Equal(t, " 1 - Test", proposalsQuery)

deposit := executeGetDeposit(t,
fmt.Sprintf("gaiacli query gov deposit --proposal-id=1 --depositor=%s --output=json %v",
fmt.Sprintf("gaiacli query gov deposit 1 %s --output=json %v",
fooAddr, flags))
require.Equal(t, int64(5), deposit.Amount.AmountOf(stakeTypes.DefaultBondDenom).Int64())

depositStr := fmt.Sprintf("gaiacli tx gov deposit %v", flags)
depositStr := fmt.Sprintf("gaiacli tx gov deposit 1 %s %v", fmt.Sprintf("10%s", stakeTypes.DefaultBondDenom), flags)
depositStr += fmt.Sprintf(" --from=%s", "foo")
depositStr += fmt.Sprintf(" --deposit=%s", fmt.Sprintf("10%s", stakeTypes.DefaultBondDenom))
depositStr += fmt.Sprintf(" --proposal-id=%s", "1")

// Test generate only
success, stdout, stderr = executeWriteRetStdStreams(t, depositStr+" --generate-only", app.DefaultKeyPass)
Expand All @@ -389,12 +386,12 @@ func TestGaiaCLISubmitProposal(t *testing.T) {

// test query deposit
deposits := executeGetDeposits(t,
fmt.Sprintf("gaiacli query gov deposits --proposal-id=1 --output=json %v", flags))
fmt.Sprintf("gaiacli query gov deposits 1 --output=json %v", flags))
require.Len(t, deposits, 1)
require.Equal(t, int64(15), deposits[0].Amount.AmountOf(stakeTypes.DefaultBondDenom).Int64())

deposit = executeGetDeposit(t,
fmt.Sprintf("gaiacli query gov deposit --proposal-id=1 --depositor=%s --output=json %v",
fmt.Sprintf("gaiacli query gov deposit 1 %s --output=json %v",
fooAddr, flags))
require.Equal(t, int64(15), deposit.Amount.AmountOf(stakeTypes.DefaultBondDenom).Int64())

Expand All @@ -404,14 +401,12 @@ func TestGaiaCLISubmitProposal(t *testing.T) {
fooAcc = executeGetAccount(t, fmt.Sprintf("gaiacli query account %s %v", fooAddr, flags))

require.Equal(t, int64(35), fooAcc.GetCoins().AmountOf(stakeTypes.DefaultBondDenom).Int64())
proposal1 = executeGetProposal(t, fmt.Sprintf("gaiacli query gov proposal --proposal-id=1 --output=json %v", flags))
proposal1 = executeGetProposal(t, fmt.Sprintf("gaiacli query gov proposal 1 --output=json %v", flags))
require.Equal(t, uint64(1), proposal1.GetProposalID())
require.Equal(t, gov.StatusVotingPeriod, proposal1.GetStatus())

voteStr := fmt.Sprintf("gaiacli tx gov vote %v", flags)
voteStr := fmt.Sprintf("gaiacli tx gov vote 1 Yes %v", flags)
voteStr += fmt.Sprintf(" --from=%s", "foo")
voteStr += fmt.Sprintf(" --proposal-id=%s", "1")
voteStr += fmt.Sprintf(" --option=%s", "Yes")

// Test generate only
success, stdout, stderr = executeWriteRetStdStreams(t, voteStr+" --generate-only", app.DefaultKeyPass)
Expand All @@ -426,11 +421,11 @@ func TestGaiaCLISubmitProposal(t *testing.T) {
executeWrite(t, voteStr, app.DefaultKeyPass)
tests.WaitForNextNBlocksTM(2, port)

vote := executeGetVote(t, fmt.Sprintf("gaiacli query gov vote --proposal-id=1 --voter=%s --output=json %v", fooAddr, flags))
vote := executeGetVote(t, fmt.Sprintf("gaiacli query gov vote 1 %s --output=json %v", fooAddr, flags))
require.Equal(t, uint64(1), vote.ProposalID)
require.Equal(t, gov.OptionYes, vote.Option)

votes := executeGetVotes(t, fmt.Sprintf("gaiacli query gov votes --proposal-id=1 --output=json %v", flags))
votes := executeGetVotes(t, fmt.Sprintf("gaiacli query gov votes 1 --output=json %v", flags))
require.Len(t, votes, 1)
require.Equal(t, uint64(1), votes[0].ProposalID)
require.Equal(t, gov.OptionYes, votes[0].Option)
Expand Down Expand Up @@ -460,13 +455,12 @@ func TestGaiaCLISubmitProposal(t *testing.T) {
}

func TestGaiaCLISendGenerateSignAndBroadcast(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
chainID, servAddr, port := initializeFixtures(t, gaiadHome, gaiacliHome)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr := initializeFixtures(t)
flags := fmt.Sprintf("--home=%s --node=%v --chain-id=%v", gaiacliHome, servAddr, chainID)

// start gaiad server
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf(
"gaiad start --home=%s --rpc.laddr=%v", gaiadHome, servAddr))
proc := tests.GoExecuteTWithStdout(t, fmt.Sprintf("gaiad start --home=%s --rpc.laddr=%v --p2p.laddr=%v", gaiadHome, servAddr, p2pAddr))

defer proc.Stop(false)
tests.WaitForTMStart(port)
Expand Down Expand Up @@ -562,11 +556,9 @@ func TestGaiaCLISendGenerateSignAndBroadcast(t *testing.T) {
}

func TestGaiaCLIConfig(t *testing.T) {
gaiadHome, gaiacliHome := getTestingHomeDirs(t)
servAddr, port, err := server.FreeTCPAddr()
require.NoError(t, err)
t.Parallel()
chainID, servAddr, port, gaiadHome, gaiacliHome, _ := initializeFixtures(t)
node := fmt.Sprintf("%s:%s", servAddr, port)
chainID := executeInit(t, fmt.Sprintf("gaiad init -o --moniker=foo --home=%s", gaiadHome))
executeWrite(t, fmt.Sprintf("gaiacli --home=%s config", gaiadHome), gaiacliHome, node, "y")
config, err := ioutil.ReadFile(path.Join(gaiacliHome, "config", "config.toml"))
require.NoError(t, err)
Expand Down Expand Up @@ -603,40 +595,34 @@ trust_node = true
//___________________________________________________________________________________
// helper methods

func getTestingHomeDirs(t *testing.T) (string, string) {
tmpDir, err := ioutil.TempDir("", t.Name())
require.NoError(t, err)
gaiadHome := fmt.Sprintf("%s%s.test_gaiad", tmpDir, string(os.PathSeparator))
gaiacliHome := fmt.Sprintf("%s%s.test_gaiacli", tmpDir, string(os.PathSeparator))
func getTestingHomeDirs(name string) (string, string) {
tmpDir := os.TempDir()
gaiadHome := fmt.Sprintf("%s%s%s%s.test_gaiad", tmpDir, string(os.PathSeparator), name, string(os.PathSeparator))
gaiacliHome := fmt.Sprintf("%s%s%s%s.test_gaiacli", tmpDir, string(os.PathSeparator), name, string(os.PathSeparator))
return gaiadHome, gaiacliHome
}

func initializeFixtures(t *testing.T, gaiadHome, gaiacliHome string) (chainID, servAddr, port string) {
func initializeFixtures(t *testing.T) (chainID, servAddr, port, gaiadHome, gaiacliHome, p2pAddr string) {
gaiadHome, gaiacliHome = getTestingHomeDirs(t.Name())
tests.ExecuteT(t, fmt.Sprintf("gaiad --home=%s unsafe-reset-all", gaiadHome), "")
os.RemoveAll(filepath.Join(gaiadHome, "config", "gentx"))
executeWrite(t, fmt.Sprintf("gaiacli keys delete --home=%s --force foo", gaiacliHome))
executeWrite(t, fmt.Sprintf("gaiacli keys delete --home=%s --force bar", gaiacliHome))
executeWrite(t, fmt.Sprintf("gaiacli keys delete --home=%s foo", gaiacliHome), app.DefaultKeyPass)
executeWrite(t, fmt.Sprintf("gaiacli keys delete --home=%s bar", gaiacliHome), app.DefaultKeyPass)
executeWriteCheckErr(t, fmt.Sprintf("gaiacli keys add --home=%s foo", gaiacliHome), app.DefaultKeyPass)
executeWriteCheckErr(t, fmt.Sprintf("gaiacli keys add --home=%s bar", gaiacliHome), app.DefaultKeyPass)
fooAddr, _ := executeGetAddrPK(t, fmt.Sprintf(
"gaiacli keys show foo --output=json --home=%s", gaiacliHome))
fooAddr, _ := executeGetAddrPK(t, fmt.Sprintf("gaiacli keys show foo --output=json --home=%s", gaiacliHome))
chainID = executeInit(t, fmt.Sprintf("gaiad init -o --moniker=foo --home=%s", gaiadHome))
genFile := filepath.Join(gaiadHome, "config", "genesis.json")
genDoc := readGenesisFile(t, genFile)
var appState app.GenesisState
err := codec.Cdc.UnmarshalJSON(genDoc.AppState, &appState)
require.NoError(t, err)
appState.Accounts = []app.GenesisAccount{app.NewDefaultGenesisAccount(fooAddr)}
appStateJSON, err := codec.Cdc.MarshalJSON(appState)
require.NoError(t, err)
genDoc.AppState = appStateJSON
genDoc.SaveAs(genFile)

executeWriteCheckErr(t, fmt.Sprintf(
"gaiad add-genesis-account %s 150%s,1000fooToken --home=%s", fooAddr, stakeTypes.DefaultBondDenom, gaiadHome))
executeWrite(t, fmt.Sprintf("cat %s%sconfig%sgenesis.json", gaiadHome, string(os.PathSeparator), string(os.PathSeparator)))
executeWriteCheckErr(t, fmt.Sprintf(
"gaiad gentx --name=foo --home=%s --home-client=%s", gaiadHome, gaiacliHome),
app.DefaultKeyPass)
"gaiad gentx --name=foo --home=%s --home-client=%s", gaiadHome, gaiacliHome), app.DefaultKeyPass)
executeWriteCheckErr(t, fmt.Sprintf("gaiad collect-gentxs --home=%s", gaiadHome), app.DefaultKeyPass)
// get a free port, also setup some common flags
servAddr, port, err = server.FreeTCPAddr()
servAddr, port, err := server.FreeTCPAddr()
require.NoError(t, err)
p2pAddr, _, err = server.FreeTCPAddr()
require.NoError(t, err)
return
}
Expand Down
41 changes: 39 additions & 2 deletions cmd/gaia/init/gentx.go
Original file line number Diff line number Diff line change
Expand Up @@ -64,18 +64,26 @@ following delegation and commission default parameters:
if err != nil {
return err
}

genDoc, err := loadGenesisDoc(cdc, config.GenesisFile())
if err != nil {
return err
}

genesisState := app.GenesisState{}

jackzampolin marked this conversation as resolved.
Show resolved Hide resolved
if err = cdc.UnmarshalJSON(genDoc.AppState, &genesisState); err != nil {
return err
}

kb, err := keys.GetKeyBaseFromDir(viper.GetString(flagClientHome))
if err != nil {
return err
}

name := viper.GetString(client.FlagName)
if _, err := kb.Get(name); err != nil {
key, err := kb.Get(name)
if err != nil {
return err
}

Expand All @@ -86,8 +94,37 @@ following delegation and commission default parameters:
return err
}
}
// Run gaiad tx create-validator

// Set flags for creating gentx
prepareFlagsForTxCreateValidator(config, nodeID, ip, genDoc.ChainID, valPubKey)

// Fetch the amount of coins staked
amount := viper.GetString(cli.FlagAmount)
coins, err := sdk.ParseCoins(amount)
if err != nil {
return err
}

for _, acc := range genesisState.Accounts {
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

The contents of this for loop should probably be broken out into a seperate function, or this whole containing function restructured to reduce indentation

// Ensure that account is in genesis
if string(key.GetAddress()) == string(acc.Address) {
jackzampolin marked this conversation as resolved.
Show resolved Hide resolved
// Ensure account contains enough funds of default bond denom
if acc.Coins.AmountOf(stakeTypes.DefaultBondDenom).
alexanderbez marked this conversation as resolved.
Show resolved Hide resolved
LT(coins.AmountOf(stakeTypes.DefaultBondDenom)) {
alexanderbez marked this conversation as resolved.
Show resolved Hide resolved
return fmt.Errorf(
"Account %s is in genesis, but the only has %s available to stake, not %s",
key.GetAddress(), acc.Coins, amount,
)
}
}
// If the account is not in genesis return an error
return fmt.Errorf(
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

We can eliminate use of inGenesis by just moving this error into the above loop (which should also probably get moved to it's own funcion per my previous comment)

"Account %s in not in the app_state.accounts array of genesis.json",
key.GetAddress(),
)
}

// Run gaiad tx create-validator
txBldr := authtxb.NewTxBuilderFromCLI().WithCodec(cdc)
cliCtx := context.NewCLIContext().WithCodec(cdc)
cliCtx, txBldr, msg, err := cli.BuildCreateValidatorMsg(cliCtx, txBldr)
Expand Down
6 changes: 6 additions & 0 deletions tests/gobash.go
Original file line number Diff line number Diff line change
Expand Up @@ -92,12 +92,18 @@ func GoExecuteTWithStdout(t *testing.T, cmd string) (proc *Process) {
require.NoError(t, err)

// Without this, the test halts ?!
// (theory: because stdout and/or err aren't connected to anything the process halts)
go func() {
_, err := ioutil.ReadAll(proc.StdoutPipe)
if err != nil {
fmt.Println("-------------ERR-----------------------", err)
return
}
_, err = ioutil.ReadAll(proc.StderrPipe)
if err != nil {
fmt.Println("-------------ERR-----------------------", err)
return
}
}()

err = proc.Cmd.Start()
Expand Down
Loading