Last active
March 2, 2022 14:58
-
-
Save sainoe/cf0ebdf6358c0ebb25ab1263c759ee77 to your computer and use it in GitHub Desktop.
TestChain validator set update issue
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
package ibc_testing_test | |
import ( | |
"bytes" | |
"testing" | |
sdk "github.com/cosmos/cosmos-sdk/types" | |
stakingtypes "github.com/cosmos/cosmos-sdk/x/staking/types" | |
abci "github.com/tendermint/tendermint/abci/types" | |
ibctesting "github.com/cosmos/ibc-go/v3/testing" | |
"github.com/stretchr/testify/suite" | |
) | |
// KeeperTestSuite is a testing suite to test keeper functions. | |
type KeeperTestSuite struct { | |
suite.Suite | |
coordinator *ibctesting.Coordinator | |
// testing chains used for convenience and readability | |
chainA *ibctesting.TestChain | |
chainB *ibctesting.TestChain | |
ctx sdk.Context | |
} | |
// TestKeeperTestSuite runs all the tests within this package. | |
func TestKeeperTestSuite(t *testing.T) { | |
suite.Run(t, new(KeeperTestSuite)) | |
} | |
// SetupTest creates a coordinator with 2 test chains. | |
func (s *KeeperTestSuite) SetupTest() { | |
s.coordinator = ibctesting.NewCoordinator(s.T(), 2) // initializes 2 test chains | |
s.chainA = s.coordinator.GetChain(ibctesting.GetChainID(1)) // convenience and readability | |
s.chainB = s.coordinator.GetChain(ibctesting.GetChainID(2)) // convenience and readability | |
s.ctx = s.chainA.GetContext() | |
} | |
func (s *KeeperTestSuite) TestUpdateValset() { | |
path := ibctesting.NewPath(s.chainA, s.chainB) // clientID, connectionID, channelID empty | |
s.coordinator.Setup(path) // clientID, connectionID, channelID filled | |
s.Require().Equal("07-tendermint-0", path.EndpointA.ClientID) | |
s.Require().Equal("connection-0", path.EndpointA.ConnectionID) | |
s.Require().Equal("channel-0", path.EndpointA.ChannelID) | |
chainAStakingKeeper := s.chainA.App.GetStakingKeeper() | |
// Choose a validator, and get its address and data structure into the correct types | |
tmValidator := s.chainA.Vals.Validators[0] | |
valAddr, err := sdk.ValAddressFromHex(tmValidator.Address.String()) | |
s.Require().NoError(err) | |
// jail validator to zero its power in the validator set | |
chainAStakingKeeper.Jail(s.ctx, sdk.ConsAddress(tmValidator.Address)) | |
// check that validator was jailed | |
val, ok := chainAStakingKeeper.GetValidatorByConsAddr(s.ctx, sdk.ConsAddress(valAddr)) | |
s.Require().True(ok) | |
s.Require().True(val.Jailed) | |
// check that validator updates are seen by the staking module endblock callback | |
valUpdates := chainAStakingKeeper.BlockValidatorUpdates(s.ctx) | |
s.Require().Len(valUpdates, 1) | |
// check that chain endblock callback returns validator updates | |
valUpdatesEnblock := s.chainA.App.EndBlock(abci.RequestEndBlock{}) | |
s.T().Log(len(valUpdatesEnblock.ValidatorUpdates) == 1) | |
// Update the second client chain - | |
// chainA block is ended and committed | |
err = path.EndpointB.UpdateClient() | |
s.Require().NoError(err) | |
// Check the validator states are updated | |
vals, ok := s.chainA.GetValsAtHeight(s.chainA.CurrentHeader.Height) | |
s.Require().True(ok) | |
s.T().Log(vals.Validators[0].VotingPower == int64(2)) | |
// Check the chain validator hash is updated | |
s.T().Log(!bytes.Equal(s.chainA.CurrentHeader.GetNextValidatorsHash(), s.chainA.CurrentHeader.GetValidatorsHash())) | |
// Check the validator set is updated in chain A | |
s.T().Log(s.chainA.Vals.Validators[0].VotingPower == int64(2)) | |
// Update the second client chain; | |
err = path.EndpointB.UpdateClient() | |
s.Require().NoError(err) | |
} | |
func (s *KeeperTestSuite) TestUpdateValset2() { | |
path := ibctesting.NewPath(s.chainA, s.chainB) // clientID, connectionID, channelID empty | |
s.coordinator.Setup(path) // clientID, connectionID, channelID filled | |
chainAStakingKeeper := s.chainA.App.GetStakingKeeper() | |
bondAmt := sdk.NewInt(1000000) | |
delAddr := s.chainA.SenderAccount.GetAddress() | |
tmValidator := s.chainA.Vals.Validators[0] | |
valAddr, err := sdk.ValAddressFromHex(tmValidator.Address.String()) | |
s.Require().NoError(err) | |
validator, found := chainAStakingKeeper.GetValidator(s.ctx, valAddr) | |
s.Require().True(found) | |
_, err = chainAStakingKeeper.Delegate(s.ctx, delAddr, bondAmt, stakingtypes.Unbonded, stakingtypes.Validator(validator), true) | |
s.Require().NoError(err) | |
// check that validator updates are seen by the staking module endblock callback | |
valUpdates := chainAStakingKeeper.BlockValidatorUpdates(s.ctx) | |
s.Require().Len(valUpdates, 1) | |
err = path.EndpointB.UpdateClient() | |
s.Require().NoError(err) | |
// Check the chain validator hash is updated | |
s.T().Log(!bytes.Equal(s.chainA.CurrentHeader.GetNextValidatorsHash(), s.chainA.CurrentHeader.GetValidatorsHash())) | |
// Check the validator power was updated | |
s.T().Log(s.chainA.Vals.Validators[0].VotingPower == int64(2)) | |
// Undelegate both shares | |
_, err = chainAStakingKeeper.Undelegate(s.ctx, delAddr, valAddr, sdk.NewDec(2)) | |
s.Require().NoError(err) | |
// check that validator updates are seen by the staking module endblock callback | |
valUpdates = chainAStakingKeeper.BlockValidatorUpdates(s.ctx) | |
s.Require().Len(valUpdates, 1) | |
err = path.EndpointB.UpdateClient() | |
s.Require().NoError(err) | |
ubd, found := chainAStakingKeeper.GetUnbondingDelegation(s.ctx, delAddr, valAddr) | |
s.Require().True(found) | |
s.Require().Len(ubd.Entries, 1) | |
vals, ok := s.chainA.GetValsAtHeight(s.chainA.CurrentHeader.Height) | |
s.Require().True(ok) | |
// Check the validator set is updated in chain A | |
s.T().Log(vals.Validators[0].VotingPower == int64(0)) | |
// Check the chain validator hash is updated | |
s.T().Log(!bytes.Equal(s.chainA.CurrentHeader.GetNextValidatorsHash(), s.chainA.CurrentHeader.GetValidatorsHash())) | |
// Check the validator set is updated in chain A | |
s.T().Log(s.chainA.Vals.Validators[0].VotingPower == int64(0)) | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment