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

E2E: Add ICA MsgSubmitTx tests (success + failure) #2021

Merged
merged 35 commits into from
Aug 17, 2022
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
35 commits
Select commit Hold shift + click to select a range
8f44301
feat(test): adding support for backwards compatibility testing
chatton Aug 8, 2022
f470bcf
Merge branch 'main' into cian/issue#1911-support-backwards-compatibil…
chatton Aug 8, 2022
2297280
chore: made names of variables more descriptive
chatton Aug 8, 2022
4c30485
Merge branch 'cian/issue#1911-support-backwards-compatibility-tests' …
chatton Aug 8, 2022
cd6363c
wip: adding demo interchain accounts test
chatton Aug 9, 2022
d87a711
wip
chatton Aug 9, 2022
a9ceda1
merge main
chatton Aug 10, 2022
2ec4c73
wip
chatton Aug 10, 2022
39eff2f
chore: merge main
chatton Aug 12, 2022
17d5840
chore: pass -p events to relayer
chatton Aug 12, 2022
1c79319
wip: temporarily setting env vars in the test
chatton Aug 12, 2022
1db8103
chore: adding Make command to run test
chatton Aug 12, 2022
57067fb
work in progress ICA test using s.BroadcastMessages
charleenfei Aug 15, 2022
6890de3
chore: refactoring register ica account to broadcast message
chatton Aug 15, 2022
d147af9
wip update to test host account
charleenfei Aug 15, 2022
917a6a5
chore: converting query interchain account to grpc query call
chatton Aug 15, 2022
27cd4f8
chore: specify empty version string explicitly
chatton Aug 15, 2022
4afd01e
merge sample-test branch
chatton Aug 15, 2022
f452e8b
wip
charleenfei Aug 15, 2022
e0e33f1
Merge branch 'cian/refactor-register-ica' into cian/issue#1941-add-in…
charleenfei Aug 15, 2022
eb4bcb5
wip bank transfer
charleenfei Aug 15, 2022
85370a8
wip
charleenfei Aug 15, 2022
d96c0d5
cleanup tests
charleenfei Aug 16, 2022
83eaa6f
rm init env versions, handle unhappy path
charleenfei Aug 16, 2022
5328362
setup env
charleenfei Aug 16, 2022
289af25
chore: adding comment to outline temprorary usage of setting env vars
chatton Aug 16, 2022
0094b36
chore: merge main
chatton Aug 16, 2022
bd9ebc4
chore: removing unused code
chatton Aug 16, 2022
61a444e
chore: exporting GetRelayerExecReporter method
chatton Aug 16, 2022
50c9375
chore: adding wait for blocks
chatton Aug 16, 2022
bb08d13
chore: updating names of test functions
chatton Aug 16, 2022
f9de6e6
chore: updating test name
chatton Aug 16, 2022
e688082
chore: corrected typo
chatton Aug 16, 2022
cf8a8bc
chrore: split test into two separate test cases
chatton Aug 16, 2022
609d93d
chore: addressing PR feedback
chatton Aug 17, 2022
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
1 change: 1 addition & 0 deletions e2e/go.mod
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,7 @@ replace github.com/gogo/protobuf => github.com/regen-network/protobuf v1.3.3-alp
require (
github.com/cosmos/cosmos-sdk v0.46.0
github.com/cosmos/ibc-go/v5 v5.0.0-beta1
github.com/cosmos/interchain-accounts v0.3.1-0.20220816085955-393d8444c111
github.com/docker/docker v20.10.17+incompatible
github.com/strangelove-ventures/ibctest v0.0.0-20220808203516-6cbd3743756d
github.com/stretchr/testify v1.8.0
Expand Down
4 changes: 4 additions & 0 deletions e2e/go.sum
Original file line number Diff line number Diff line change
Expand Up @@ -256,6 +256,10 @@ github.com/cosmos/iavl v0.19.0 h1:sgyrjqOkycXiN7Tuupuo4QAldKFg7Sipyfeg/IL7cps=
github.com/cosmos/iavl v0.19.0/go.mod h1:l5h9pAB3m5fihB3pXVgwYqdY8aBsMagqz7T0MUjxZeA=
github.com/cosmos/ibc-go/v5 v5.0.0-beta1 h1:YqC9giQlZId8Wui8xpaUFI+TpVmEupQZSoDlmxAu6yI=
github.com/cosmos/ibc-go/v5 v5.0.0-beta1/go.mod h1:9mmcbzuidgX7nhafIKng/XhXAHDEnRqDjGy/60W1cvg=
github.com/cosmos/interchain-accounts v0.3.0 h1:Zu9372ze/a6HhUy5Z4Mu+C+FcnNLGrQ15aPwr6lRTeI=
github.com/cosmos/interchain-accounts v0.3.0/go.mod h1:FYF1IiAz6M/LC1Gb3Jch042IaL0AXOfU+s1ZGvR4IqI=
github.com/cosmos/interchain-accounts v0.3.1-0.20220816085955-393d8444c111 h1:5Tm0jHmyh2XDc/XlIvaFJbIvVQyRMH4EtoLzSJM/MAY=
github.com/cosmos/interchain-accounts v0.3.1-0.20220816085955-393d8444c111/go.mod h1:vNWr9YxBrI5c74jBwk9ooiUCIDvdOJeF8MQEA/z0IEk=
github.com/cosmos/ledger-cosmos-go v0.11.1 h1:9JIYsGnXP613pb2vPjFeMMjBI5lEDsEaF6oYorTy6J4=
github.com/cosmos/ledger-cosmos-go v0.11.1/go.mod h1:J8//BsAGTo3OC/vDLjMRFLW6q0WAaXvHnVc7ZmE8iUY=
github.com/cosmos/ledger-go v0.9.2 h1:Nnao/dLwaVTk1Q5U9THldpUMMXU94BOTWPddSmVB6pI=
Expand Down
225 changes: 225 additions & 0 deletions e2e/interchain_accounts_test.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,225 @@
package e2e

import (
"context"
"testing"

ibctest "github.com/strangelove-ventures/ibctest"
"github.com/strangelove-ventures/ibctest/chain/cosmos"
"github.com/strangelove-ventures/ibctest/ibc"
"github.com/strangelove-ventures/ibctest/test"
"github.com/stretchr/testify/suite"

sdk "github.com/cosmos/cosmos-sdk/types"
banktypes "github.com/cosmos/cosmos-sdk/x/bank/types"
intertxtypes "github.com/cosmos/interchain-accounts/x/inter-tx/types"

"github.com/cosmos/ibc-go/e2e/testconfig"
"github.com/cosmos/ibc-go/e2e/testsuite"
"github.com/cosmos/ibc-go/e2e/testvalues"
ibctesting "github.com/cosmos/ibc-go/v5/testing"
)

func TestInterchainAccountsTestSuite(t *testing.T) {
// NOTE: this is a temporary mechanism to enable this test to run alongside the simd tests.
// This will be removed in a follow up PR and properly parameterized in a github workflow.
testconfig.SetChainBinaryVersions(
"ghcr.io/cosmos/ibc-go-icad", "master", "icad", "ghcr.io/cosmos/ibc-go-icad", "master",
)
suite.Run(t, new(InterchainAccountsTestSuite))
}

type InterchainAccountsTestSuite struct {
testsuite.E2ETestSuite
}

// RegisterInterchainAccount will attempt to register an interchain account on the counterparty chain.
func (s *InterchainAccountsTestSuite) RegisterInterchainAccount(ctx context.Context, chain *cosmos.CosmosChain, user *ibctest.User, msgRegisterAccount *intertxtypes.MsgRegisterAccount) error {
txResp, err := s.BroadcastMessages(ctx, chain, user, msgRegisterAccount)
s.AssertValidTxResponse(txResp)
return err
}

func (s *InterchainAccountsTestSuite) TestMsgSubmitTx_SuccessfulTransfer() {
Copy link
Contributor

Choose a reason for hiding this comment

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

ive got the fail case /unhappy case below as well, so maybe we can keep this naming but break out the unhappy case into a separate test function

Copy link
Contributor Author

Choose a reason for hiding this comment

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

separated out into 2 tests as you suggested!

t := s.T()
ctx := context.TODO()

// setup relayers and connection-0 between two chains
// channel-0 is a transfer channel but it will not be used in this test case
relayer, _ := s.SetupChainsRelayerAndChannel(ctx)
chainA, chainB := s.GetChains()

// setup 2 accounts: controller account on chain A, a second chain B account.
// host account will be created when the ICA is registered
controllerAccount := s.CreateUserOnChainA(ctx, testvalues.StartingTokenAmount)
Copy link
Contributor

@seantking seantking Aug 17, 2022

Choose a reason for hiding this comment

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

wdyt about renaming controllerAccount to ownerAccount and the hostAccount as interchainAccount?

cc: @damiannolan

Copy link
Contributor

@charleenfei charleenfei Aug 17, 2022

Choose a reason for hiding this comment

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

i personally think that this change would be more confusing -- but that's just my opinion because of the language from the spec.

Copy link
Contributor

Choose a reason for hiding this comment

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

I personally like host/controller terminology

chainBAccount := s.CreateUserOnChainB(ctx, testvalues.StartingTokenAmount)
var hostAccount string

t.Run("register interchain account", func(t *testing.T) {
version := "" // allow app to handle the version as appropriate.
msgRegisterAccount := intertxtypes.NewMsgRegisterAccount(controllerAccount.Bech32Address(chainA.Config().Bech32Prefix), ibctesting.FirstConnectionID, version)
err := s.RegisterInterchainAccount(ctx, chainA, controllerAccount, msgRegisterAccount)
s.Require().NoError(err)
})

t.Run("start relayer", func(t *testing.T) {
s.StartRelayer(relayer)
})

t.Run("verify interchain account", func(t *testing.T) {
var err error
hostAccount, err = s.QueryInterchainAccount(ctx, chainA, controllerAccount.Bech32Address(chainA.Config().Bech32Prefix), ibctesting.FirstConnectionID)
s.Require().NoError(err)
s.Require().NotZero(len(hostAccount))

channels, err := relayer.GetChannels(ctx, s.GetRelayerExecReporter(), chainA.Config().ChainID)
s.Require().NoError(err)
s.Require().Equal(len(channels), 2)
})

t.Run("interchain account executes a bank transfer on behalf of the corresponding owner account", func(t *testing.T) {

t.Run("fund interchain account wallet", func(t *testing.T) {
// fund the host account account so it has some $$ to send
err := chainB.SendFunds(ctx, ibctest.FaucetAccountKeyName, ibc.WalletAmount{
Address: hostAccount,
Amount: testvalues.StartingTokenAmount,
Denom: chainB.Config().Denom,
})
s.Require().NoError(err)
})

t.Run("broadcast MsgSubmitTx", func(t *testing.T) {
// assemble bank transfer message from host account to user account on host chain
msgSend := &banktypes.MsgSend{
FromAddress: hostAccount,
ToAddress: chainBAccount.Bech32Address(chainB.Config().Bech32Prefix),
Amount: sdk.NewCoins(testvalues.DefaultTransferAmount(chainB.Config().Denom)),
}

// assemble submitMessage tx for intertx
msgSubmitTx, err := intertxtypes.NewMsgSubmitTx(
msgSend,
ibctesting.FirstConnectionID,
controllerAccount.Bech32Address(chainA.Config().Bech32Prefix),
)
s.Require().NoError(err)

// broadcast submitMessage tx from controller account on chain A
// this message should trigger the sending of an ICA packet over channel-1 (channel created between controller and host)
// this ICA packet contains the assembled bank transfer message from above, which will be executed by the host account on the host chain.
resp, err := s.BroadcastMessages(
ctx,
chainA,
controllerAccount,
msgSubmitTx,
)

s.AssertValidTxResponse(resp)
s.Require().NoError(err)

s.Require().NoError(test.WaitForBlocks(ctx, 10, chainA, chainB))
})

t.Run("verify tokens transferred", func(t *testing.T) {
balance, err := chainB.GetBalance(ctx, chainBAccount.Bech32Address(chainB.Config().Bech32Prefix), chainB.Config().Denom)
s.Require().NoError(err)

_, err = chainB.GetBalance(ctx, hostAccount, chainB.Config().Denom)
s.Require().NoError(err)

expected := testvalues.IBCTransferAmount + testvalues.StartingTokenAmount
Copy link
Contributor

Choose a reason for hiding this comment

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

I find it a little confusing that we use IBCTransferAmount in a bank send. Maybe we could add a short comment explaining we use that var in the bank send. I don't have a strong preference though

s.Require().Equal(expected, balance)
})
})
}

func (s *InterchainAccountsTestSuite) TestMsgSubmitTx_FailedTransfer_InsufficientFunds() {
t := s.T()
ctx := context.TODO()

// setup relayers and connection-0 between two chains
// channel-0 is a transfer channel but it will not be used in this test case
relayer, _ := s.SetupChainsRelayerAndChannel(ctx)
chainA, chainB := s.GetChains()

// setup 2 accounts: controller account on chain A, a second chain B account.
// host account will be created when the ICA is registered
controllerAccount := s.CreateUserOnChainA(ctx, testvalues.StartingTokenAmount)
chainBAccount := s.CreateUserOnChainB(ctx, testvalues.StartingTokenAmount)
var hostAccount string

t.Run("register interchain account", func(t *testing.T) {
version := "" // allow app to handle the version as appropriate.
msgRegisterAccount := intertxtypes.NewMsgRegisterAccount(controllerAccount.Bech32Address(chainA.Config().Bech32Prefix), ibctesting.FirstConnectionID, version)
err := s.RegisterInterchainAccount(ctx, chainA, controllerAccount, msgRegisterAccount)
s.Require().NoError(err)
})

t.Run("start relayer", func(t *testing.T) {
s.StartRelayer(relayer)
})

t.Run("verify interchain account", func(t *testing.T) {
var err error
hostAccount, err = s.QueryInterchainAccount(ctx, chainA, controllerAccount.Bech32Address(chainA.Config().Bech32Prefix), ibctesting.FirstConnectionID)
s.Require().NoError(err)
s.Require().NotZero(len(hostAccount))

channels, err := relayer.GetChannels(ctx, s.GetRelayerExecReporter(), chainA.Config().ChainID)
s.Require().NoError(err)
s.Require().Equal(len(channels), 2)
})

t.Run("fail to execute bank transfer over ICA", func(t *testing.T) {
t.Run("verify empty host wallet", func(t *testing.T) {
hostAccountBalance, err := chainB.GetBalance(ctx, hostAccount, chainB.Config().Denom)
s.Require().NoError(err)
s.Require().Zero(hostAccountBalance)
})

t.Run("broadcast MsgSubmitTx", func(t *testing.T) {
// assemble bank transfer message from host account to user account on host chain
transferMsg := &banktypes.MsgSend{
FromAddress: hostAccount,
ToAddress: chainBAccount.Bech32Address(chainB.Config().Bech32Prefix),
Amount: sdk.NewCoins(testvalues.DefaultTransferAmount(chainB.Config().Denom)),
}

// assemble submitMessage tx for intertx
submitMsg, err := intertxtypes.NewMsgSubmitTx(
transferMsg,
ibctesting.FirstConnectionID,
controllerAccount.Bech32Address(chainA.Config().Bech32Prefix),
)
s.Require().NoError(err)

// broadcast submitMessage tx from controller account on chain A
// this message should trigger the sending of an ICA packet over channel-1 (channel created between controller and host)
// this ICA packet contains the assembled bank transfer message from above, which will be executed by the host account on the host chain.
resp, err := s.BroadcastMessages(
ctx,
chainA,
controllerAccount,
submitMsg,
)

s.AssertValidTxResponse(resp)
s.Require().NoError(err)
})

t.Run("packets are relayed", func(t *testing.T) {
channels, err := relayer.GetChannels(ctx, s.GetRelayerExecReporter(), chainA.Config().ChainID)
s.Require().NoError(err)
s.AssertPacketRelayed(ctx, chainA, channels[1].PortID, channels[1].ChannelID, 1)
})

t.Run("verify balance is the same", func(t *testing.T) {
balance, err := chainB.GetBalance(ctx, chainBAccount.Bech32Address(chainB.Config().Bech32Prefix), chainB.Config().Denom)
s.Require().NoError(err)

expected := testvalues.StartingTokenAmount
s.Require().Equal(expected, balance)
})
})
}
42 changes: 32 additions & 10 deletions e2e/testconfig/testconfig.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,8 +18,13 @@ const (
// ChainBSimdTagEnv specifies the tag that Chain B will use. If unspecified
// the value will default to the same value as Chain A.
ChainBSimdTagEnv = "CHAIN_B_SIMD_TAG"
GoRelayerTagEnv = "RLY_TAG"

// GoRelayerTagEnv specifies the go relayer version. Defaults to "main"
GoRelayerTagEnv = "RLY_TAG"
// ChainBinary binary is the binary that will be used for the chains.
ChainBinary = "CHAIN_BINARY"
// defaultBinary is the default binary that will be used by the chains.
defaultBinary = "simd"
// defaultSimdImage is the default image that will be used for the chain if none are specified.
defaultSimdImage = "ghcr.io/cosmos/ibc-go-simd"
defaultRlyTag = "main"
)
Expand All @@ -32,20 +37,26 @@ type TestConfig struct {
}

type ChainConfig struct {
Image string
Tag string
Image string
Tag string
Binary string
}

// FromEnv returns a TestConfig constructed from environment variables.
func FromEnv() TestConfig {
chainBinary, ok := os.LookupEnv(ChainBinary)
if !ok {
chainBinary = defaultBinary
}

chainASimdImage, ok := os.LookupEnv(ChainASimdImageEnv)
if !ok {
chainASimdImage = defaultSimdImage
}

chainASimdTag, ok := os.LookupEnv(ChainASimdTagEnv)
if !ok {
panic(fmt.Sprintf("must specify simd version for test with environment variable [%s]", ChainASimdTagEnv))
panic(fmt.Sprintf("must specify %s version for test with environment variable [%s]", chainBinary, ChainASimdTagEnv))
}

chainBSimdImage, ok := os.LookupEnv(ChainBSimdImageEnv)
Expand All @@ -65,12 +76,14 @@ func FromEnv() TestConfig {

return TestConfig{
ChainAConfig: ChainConfig{
Image: chainASimdImage,
Tag: chainASimdTag,
Image: chainASimdImage,
Tag: chainASimdTag,
Binary: chainBinary,
},
ChainBConfig: ChainConfig{
Image: chainBSimdImage,
Tag: chainBSimdTag,
Image: chainBSimdImage,
Tag: chainBSimdTag,
Binary: chainBinary,
},
RlyTag: rlyTag,
}
Expand Down Expand Up @@ -111,7 +124,7 @@ func newDefaultSimappConfig(cc ChainConfig, name, chainID, denom string) ibc.Cha
Version: cc.Tag,
},
},
Bin: "simd",
Bin: cc.Binary,
Bech32Prefix: "cosmos",
Denom: denom,
GasPrices: fmt.Sprintf("0.00%s", denom),
Expand All @@ -120,3 +133,12 @@ func newDefaultSimappConfig(cc ChainConfig, name, chainID, denom string) ibc.Cha
NoHostMount: false,
}
}

// SetChainBinaryVersions is a helper function for local cross-version testing
func SetChainBinaryVersions(chainaSimdImg, chainaSimdTag, chainBinary, chainbSimdImg, chainbSimdTag string) {
os.Setenv("CHAIN_A_SIMD_IMAGE", chainaSimdImg)
os.Setenv("CHAIN_A_SIMD_TAG", chainaSimdTag)
os.Setenv("CHAIN_B_SIMD_IMAGE", chainbSimdImg)
os.Setenv("CHAIN_B_SIMD_TAG", chainbSimdTag)
os.Setenv("CHAIN_BINARY", chainBinary)
}
14 changes: 14 additions & 0 deletions e2e/testsuite/grpc_query.go
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,7 @@ package testsuite
import (
"context"

intertxtypes "github.com/cosmos/interchain-accounts/x/inter-tx/types"
"github.com/strangelove-ventures/ibctest/ibc"

clienttypes "github.com/cosmos/ibc-go/v5/modules/core/02-client/types"
Expand Down Expand Up @@ -41,3 +42,16 @@ func (s *E2ETestSuite) QueryPacketCommitment(ctx context.Context, chain ibc.Chai
}
return res.Commitment, nil
}

// QueryInterchainAccount queries the interchain account for the given owner and connectionId.
func (s *E2ETestSuite) QueryInterchainAccount(ctx context.Context, chain ibc.Chain, owner, connectionId string) (string, error) {
queryClient := s.GetChainGRCPClients(chain).ICAQueryClient
res, err := queryClient.InterchainAccount(ctx, &intertxtypes.QueryInterchainAccountRequest{
Owner: owner,
ConnectionId: connectionId,
})
if err != nil {
return "", err
}
return res.InterchainAccountAddress, nil
}
2 changes: 1 addition & 1 deletion e2e/testsuite/relayer.go
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ const (

// newCosmosRelayer returns an instance of the go relayer.
func newCosmosRelayer(t *testing.T, tc testconfig.TestConfig, logger *zap.Logger, dockerClient *dockerclient.Client, network string) ibc.Relayer {
return ibctest.NewBuiltinRelayerFactory(ibc.CosmosRly, logger, relayer.CustomDockerImage(cosmosRelayerRepository, tc.RlyTag)).Build(
return ibctest.NewBuiltinRelayerFactory(ibc.CosmosRly, logger, relayer.CustomDockerImage(cosmosRelayerRepository, tc.RlyTag), relayer.StartupFlags("-p", "events")).Build(
t, dockerClient, network,
)
}
Loading