diff --git a/.github/workflows/integration.yml b/.github/workflows/integration.yml index 7ce288bc0..ac3dfd398 100644 --- a/.github/workflows/integration.yml +++ b/.github/workflows/integration.yml @@ -27,7 +27,7 @@ jobs: # used to debug workflow # - name: Setup tmate session # uses: mxschmitt/action-tmate@v3 - - run: make bep159_integration_test integration_test + - run: make bep159_integration_test recon_integration_test integration_test coverage-test: runs-on: ubuntu-latest steps: diff --git a/.gitignore b/.gitignore index 810ed2241..751c9f013 100644 --- a/.gitignore +++ b/.gitignore @@ -26,3 +26,6 @@ app/apptest/data app_test/data plugins/param/data plugins/tokens/data + +# e2e temp files +e2e/priv_validator_key.json \ No newline at end of file diff --git a/Makefile b/Makefile index 72e078acb..146a1d955 100644 --- a/Makefile +++ b/Makefile @@ -205,9 +205,14 @@ integration_test: build bep159_integration_test: build @echo "-->BEP159 Integration Test" @bash ./scripts/bep159_integration_test.sh + +recon_integration_test: build + @echo "-->Recon Integration Test" + @bash ./scripts/recon_integration_test.sh + ######################################## ### Pre Commit -pre_commit: build test_unit bep159_integration_test integration_test format lint multi-nodes-test +pre_commit: build test_unit recon_integration_test bep159_integration_test integration_test format lint multi-nodes-test ######################################## ### Local validator nodes using docker and docker-compose diff --git a/app/app.go b/app/app.go index 5004e4de9..02734e110 100644 --- a/app/app.go +++ b/app/app.go @@ -258,6 +258,7 @@ func NewBinanceChain(logger log.Logger, db dbm.DB, traceStore io.Writer, baseApp common.BridgeStoreKey, common.OracleStoreKey, common.IbcStoreKey, + common.ReconStoreKey, ) app.SetAnteHandler(tx.NewAnteHandler(app.AccountKeeper)) app.SetPreChecker(tx.NewTxPreChecker()) @@ -269,6 +270,18 @@ func NewBinanceChain(logger log.Logger, db dbm.DB, traceStore io.Writer, baseApp cmn.Exit(err.Error()) } + // enable diff for reconciliation + accountIavl, ok := app.GetCommitMultiStore().GetCommitStore(common.AccountStoreKey).(*store.IavlStore) + if !ok { + cmn.Exit("cannot convert account store to ival store") + } + accountIavl.EnableDiff() + tokenIavl, ok := app.GetCommitMultiStore().GetCommitStore(common.TokenStoreKey).(*store.IavlStore) + if !ok { + cmn.Exit("cannot convert token store to ival store") + } + tokenIavl.EnableDiff() + // init app cache accountStore := app.BaseApp.GetCommitMultiStore().GetKVStore(common.AccountStoreKey) app.SetAccountStoreCache(cdc, accountStore, app.baseConfig.AccountCacheSize) @@ -345,6 +358,7 @@ func SetUpgradeConfig(upgradeConfig *config.UpgradeConfig) { upgrade.Mgr.AddUpgradeHeight(upgrade.BEP173, upgradeConfig.BEP173Height) upgrade.Mgr.AddUpgradeHeight(upgrade.FixDoubleSignChainId, upgradeConfig.FixDoubleSignChainIdHeight) upgrade.Mgr.AddUpgradeHeight(upgrade.BEP126, upgradeConfig.BEP126Height) + upgrade.Mgr.AddUpgradeHeight(upgrade.BEP255, upgradeConfig.BEP255Height) // register store keys of upgrade upgrade.Mgr.RegisterStoreKeys(upgrade.BEP9, common.TimeLockStoreKey.Name()) @@ -352,6 +366,7 @@ func SetUpgradeConfig(upgradeConfig *config.UpgradeConfig) { upgrade.Mgr.RegisterStoreKeys(upgrade.LaunchBscUpgrade, common.IbcStoreKey.Name(), common.SideChainStoreKey.Name(), common.SlashingStoreKey.Name(), common.BridgeStoreKey.Name(), common.OracleStoreKey.Name()) upgrade.Mgr.RegisterStoreKeys(upgrade.BEP128, common.StakeRewardStoreKey.Name()) + upgrade.Mgr.RegisterStoreKeys(upgrade.BEP255, common.ReconStoreKey.Name()) // register msg types of upgrade upgrade.Mgr.RegisterMsgTypes(upgrade.BEP9, @@ -953,6 +968,15 @@ func (app *BinanceChain) EndBlocker(ctx sdk.Context, req abci.RequestEndBlock) a pub.Pool.Clean() // match may end with transaction failure, which is better to save into // the EndBlock response. However, current cosmos doesn't support this. + + accountIavl, _ := app.GetCommitMultiStore().GetCommitStore(common.AccountStoreKey).(*store.IavlStore) + tokenIavl, _ := app.GetCommitMultiStore().GetCommitStore(common.TokenStoreKey).(*store.IavlStore) + if sdk.IsUpgrade(upgrade.BEP255) { + app.reconBalance(ctx, accountIavl, tokenIavl) + } + accountIavl.ResetDiff() + tokenIavl.ResetDiff() + return abci.ResponseEndBlock{ ValidatorUpdates: validatorUpdates, Events: ctx.EventManager().ABCIEvents(), diff --git a/app/config/config.go b/app/config/config.go index 9c88683ea..6ed50d9f0 100644 --- a/app/config/config.go +++ b/app/config/config.go @@ -101,6 +101,8 @@ BEP173Height = {{ .UpgradeConfig.BEP173Height }} FixDoubleSignChainIdHeight = {{ .UpgradeConfig.FixDoubleSignChainIdHeight }} # Block height of BEP126 upgrade BEP126Height = {{ .UpgradeConfig.BEP126Height }} +# Block height of BEP255 upgrade +BEP255Height = {{ .UpgradeConfig.BEP255Height }} [query] # ABCI query interface black list, suggested value: ["custom/gov/proposals", "custom/timelock/timelocks", "custom/atomicSwap/swapcreator", "custom/atomicSwap/swaprecipient"] @@ -549,6 +551,7 @@ type UpgradeConfig struct { BEP173Height int64 `mapstructure:"BEP173Height"` FixDoubleSignChainIdHeight int64 `mapstructure:"FixDoubleSignChainIdHeight"` BEP126Height int64 `mapstructure:"BEP126Height"` + BEP255Height int64 `mapstructure:"BEP255Height"` } func defaultUpgradeConfig() *UpgradeConfig { @@ -569,7 +572,7 @@ func defaultUpgradeConfig() *UpgradeConfig { BEP70Height: 1, LaunchBscUpgradeHeight: 1, LimitConsAddrUpdateIntervalHeight: math.MaxInt64, - BEP126Height: math.MaxInt64, + BEP126Height: math.MaxInt64, BEP128Height: math.MaxInt64, BEP151Height: math.MaxInt64, BEP153Height: math.MaxInt64, @@ -583,6 +586,7 @@ func defaultUpgradeConfig() *UpgradeConfig { BEP171Height: math.MaxInt64, FixFailAckPackageHeight: math.MaxInt64, EnableAccountScriptsForCrossChainTransferHeight: math.MaxInt64, + BEP255Height: math.MaxInt64, } } diff --git a/app/reconciliation.go b/app/reconciliation.go new file mode 100644 index 000000000..cfd2ea86e --- /dev/null +++ b/app/reconciliation.go @@ -0,0 +1,143 @@ +package app + +import ( + "encoding/binary" + "fmt" + "strings" + + "github.com/cosmos/cosmos-sdk/store" + sdk "github.com/cosmos/cosmos-sdk/types" + + "github.com/bnb-chain/node/common" + "github.com/bnb-chain/node/common/types" +) + +const globalAccountNumber = "globalAccountNumber" + +// unbalancedBlockHeightKey for saving unbalanced block height for reconciliation +var unbalancedBlockHeightKey = []byte("0x01") + +// reconBalance will do reconciliation for accounts balances. +func (app *BinanceChain) reconBalance(ctx sdk.Context, accountIavl *store.IavlStore, tokenIavl *store.IavlStore) { + height, exists := app.getUnbalancedBlockHeight(ctx) + if exists { + panic(fmt.Sprintf("unbalanced state at block height %d, please use hardfork to bypass it", height)) + } + + accPre, accCurrent := app.getAccountChanges(ctx, accountIavl) + tokenPre, tokenCurrent := app.getTokenChanges(ctx, tokenIavl) + + // accPre and tokenPre are positive, there will be no overflow + accountDiff := accCurrent.Plus(accPre.Negative()) + tokenDiff := tokenCurrent.Plus(tokenPre.Negative()) + + if !accountDiff.IsEqual(tokenDiff) { + ctx.Logger().Error(fmt.Sprintf("unbalanced at block %d, account diff: %s, token diff: %s \n", + ctx.BlockHeight(), accountDiff.String(), tokenDiff.String())) + app.saveUnbalancedBlockHeight(ctx) + } +} + +func (app *BinanceChain) getAccountChanges(ctx sdk.Context, accountStore *store.IavlStore) (sdk.Coins, sdk.Coins) { + preCoins := sdk.Coins{} + currentCoins := sdk.Coins{} + + diff := accountStore.GetDiff() + version := accountStore.GetTree().Version() - 1 + for k := range diff { + if strings.Contains(k, globalAccountNumber) { + continue + } + v := accountStore.Get([]byte(k)) + if v != nil { + var acc1 sdk.Account + err := app.Codec.UnmarshalBinaryBare(v, &acc1) + if err != nil { + ctx.Logger().Error("failed to unmarshal current account value", "err", err.Error()) + } else { + nacc1 := acc1.(types.NamedAccount) + ctx.Logger().Debug("current account", "address", nacc1.GetAddress(), "coins", nacc1.GetCoins().String()) + currentCoins = currentCoins.Plus(nacc1.GetCoins()) + currentCoins = currentCoins.Plus(nacc1.GetFrozenCoins()) + currentCoins = currentCoins.Plus(nacc1.GetLockedCoins()) + } + } + + _, v = accountStore.GetTree().GetVersioned([]byte(k), version) + if v != nil { // it is not a new account + var acc2 sdk.Account + err := app.Codec.UnmarshalBinaryBare(v, &acc2) + if err != nil { + ctx.Logger().Error("failed to unmarshal previous account value", "err", err.Error()) + } else { + nacc2 := acc2.(types.NamedAccount) + ctx.Logger().Debug("previous account", "address", nacc2.GetAddress(), "coins", nacc2.GetCoins().String()) + preCoins = preCoins.Plus(nacc2.GetCoins()) + preCoins = preCoins.Plus(nacc2.GetFrozenCoins()) + preCoins = preCoins.Plus(nacc2.GetLockedCoins()) + } + } + } + ctx.Logger().Debug("account changes", "current", currentCoins.String(), "previous", preCoins.String(), + "version", version, "height", ctx.BlockHeight()) + + return preCoins, currentCoins +} + +func (app *BinanceChain) getTokenChanges(ctx sdk.Context, tokenStore *store.IavlStore) (sdk.Coins, sdk.Coins) { + preCoins := sdk.Coins{} + currentCoins := sdk.Coins{} + + diff := tokenStore.GetDiff() + version := tokenStore.GetTree().Version() - 1 + for k := range diff { + v := tokenStore.Get([]byte(k)) + if v != nil { + var token1 types.IToken + err := app.Codec.UnmarshalBinaryBare(v, &token1) + if err != nil { + ctx.Logger().Error("failed to unmarshal current token value", "err", err.Error()) + } else { + ctx.Logger().Debug("current token", "symbol", token1.GetSymbol(), "supply", token1.GetTotalSupply().ToInt64()) + currentCoins = currentCoins.Plus(sdk.Coins{ + sdk.NewCoin(token1.GetSymbol(), token1.GetTotalSupply().ToInt64()), + }) + } + } + + _, v = tokenStore.GetTree().GetVersioned([]byte(k), version) + if v != nil { // it is not a new token + var token2 types.IToken + err := app.Codec.UnmarshalBinaryBare(v, &token2) + if err != nil { + ctx.Logger().Error("failed to unmarshal previous token value", "err", err.Error()) + } else { + ctx.Logger().Debug("previous token", "symbol", token2.GetSymbol(), "supply", token2.GetTotalSupply().ToInt64()) + preCoins = preCoins.Plus(sdk.Coins{ + sdk.NewCoin(token2.GetSymbol(), token2.GetTotalSupply().ToInt64()), + }) + } + } + } + ctx.Logger().Debug("token changes", "current", currentCoins.String(), "previous", preCoins.String(), + "version", version, "height", ctx.BlockHeight()) + + return preCoins, currentCoins +} + +func (app *BinanceChain) saveUnbalancedBlockHeight(ctx sdk.Context) { + reconStore := app.GetCommitMultiStore().GetCommitStore(common.ReconStoreKey).(*store.IavlStore) + bz := make([]byte, 8) + binary.BigEndian.PutUint64(bz[:], uint64(ctx.BlockHeight())) + reconStore.Set(unbalancedBlockHeightKey, bz) +} + +func (app *BinanceChain) getUnbalancedBlockHeight(ctx sdk.Context) (uint64, bool) { + reconStore := app.GetCommitMultiStore().GetCommitStore(common.ReconStoreKey).(*store.IavlStore) + + bz := reconStore.Get(unbalancedBlockHeightKey) + if bz == nil { + return 0, false + } + return binary.BigEndian.Uint64(bz), true +} diff --git a/app/reconciliation_test.go b/app/reconciliation_test.go new file mode 100644 index 000000000..705dcdefe --- /dev/null +++ b/app/reconciliation_test.go @@ -0,0 +1,66 @@ +package app + +import ( + "math" + "testing" + + "github.com/cosmos/cosmos-sdk/types" + "github.com/stretchr/testify/require" +) + +func Test_Reconciliation_Overflow(t *testing.T) { + defer func() { + if r := recover(); r == nil { + t.Errorf("should panic for overflow") + } + }() + + accountPre := types.Coins{ + types.NewCoin("BNB", 10), + } + accountCurrent := types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + tokenPre := types.Coins{ + types.NewCoin("BNB", 10), + } + tokenCurrent := types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + + _ = accountPre.Plus(tokenCurrent).IsEqual(accountCurrent.Plus(tokenPre)) +} + +func Test_Reconciliation_NoOverflow(t *testing.T) { + accountPre := types.Coins{ + types.NewCoin("BNB", 10), + } + accountCurrent := types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + tokenPre := types.Coins{ + types.NewCoin("BNB", 10), + } + tokenCurrent := types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + + equal := accountCurrent.Plus(accountPre.Negative()).IsEqual(tokenCurrent.Plus(tokenPre.Negative())) + require.True(t, equal) + + accountPre = types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + accountCurrent = types.Coins{ + types.NewCoin("BNB", 10), + } + tokenPre = types.Coins{ + types.NewCoin("BNB", math.MaxInt64), + } + tokenCurrent = types.Coins{ + types.NewCoin("BNB", 10), + } + + equal = accountCurrent.Plus(accountPre.Negative()).IsEqual(tokenCurrent.Plus(tokenPre.Negative())) + require.True(t, equal) +} diff --git a/common/stores.go b/common/stores.go index 62e0df656..7cfba97b0 100644 --- a/common/stores.go +++ b/common/stores.go @@ -20,6 +20,7 @@ const ( OracleStoreName = "oracle" IbcStoreName = "ibc" SideChainStoreName = "sc" + ReconStoreName = "recon" StakeTransientStoreName = "transient_stake" ParamsTransientStoreName = "transient_params" @@ -44,6 +45,7 @@ var ( OracleStoreKey = sdk.NewKVStoreKey(OracleStoreName) IbcStoreKey = sdk.NewKVStoreKey(IbcStoreName) SideChainStoreKey = sdk.NewKVStoreKey(SideChainStoreName) + ReconStoreKey = sdk.NewKVStoreKey(ReconStoreName) TStakeStoreKey = sdk.NewTransientStoreKey(StakeTransientStoreName) TParamsStoreKey = sdk.NewTransientStoreKey(ParamsTransientStoreName) @@ -66,6 +68,7 @@ var ( SideChainStoreName: SideChainStoreKey, BridgeStoreName: BridgeStoreKey, OracleStoreName: OracleStoreKey, + ReconStoreName: ReconStoreKey, StakeTransientStoreName: TStakeStoreKey, ParamsTransientStoreName: TParamsStoreKey, } @@ -88,6 +91,7 @@ var ( SideChainStoreName, BridgeStoreName, OracleStoreName, + ReconStoreName, } ) diff --git a/common/upgrade/upgrade.go b/common/upgrade/upgrade.go index 4683a32e4..d304e4c32 100644 --- a/common/upgrade/upgrade.go +++ b/common/upgrade/upgrade.go @@ -49,6 +49,7 @@ const ( BEP171 = sdk.BEP171 // https://github.com/bnb-chain/BEPs/pull/171 Security Enhancement for Cross-Chain Module BEP173 = sdk.BEP173 // https://github.com/bnb-chain/BEPs/pull/173 Text Proposal FixDoubleSignChainId = sdk.FixDoubleSignChainId + BEP255 = sdk.BEP255 // https://github.com/bnb-chain/BEPs/pull/255 Asset Reconciliation for Security Enhancement ) func UpgradeBEP10(before func(), after func()) { diff --git a/go.mod b/go.mod index d31428b5f..5b12dda6f 100644 --- a/go.mod +++ b/go.mod @@ -74,10 +74,10 @@ require ( github.com/tidwall/pretty v1.2.0 // indirect github.com/zondax/hid v0.9.0 // indirect github.com/zondax/ledger-cosmos-go v0.9.9 // indirect - golang.org/x/crypto v0.5.0 // indirect - golang.org/x/net v0.7.0 // indirect - golang.org/x/sys v0.5.0 // indirect - golang.org/x/text v0.7.0 // indirect + golang.org/x/crypto v0.10.0 // indirect + golang.org/x/net v0.11.0 // indirect + golang.org/x/sys v0.9.0 // indirect + golang.org/x/text v0.10.0 // indirect google.golang.org/genproto v0.0.0-20200825200019-8632dd797987 // indirect google.golang.org/grpc v1.31.0 // indirect google.golang.org/protobuf v1.28.1 // indirect @@ -88,7 +88,7 @@ require ( ) replace ( - github.com/cosmos/cosmos-sdk => github.com/bnb-chain/bnc-cosmos-sdk v0.26.5 + github.com/cosmos/cosmos-sdk => github.com/forcodedancing/bnc-cosmos-sdk v0.25.8-0.20230705071422-875aa9cf6664 github.com/tendermint/go-amino => github.com/bnb-chain/bnc-go-amino v0.14.1-binance.2 github.com/tendermint/iavl => github.com/bnb-chain/bnc-tendermint-iavl v0.12.0-binance.5 github.com/tendermint/tendermint => github.com/bnb-chain/bnc-tendermint v0.32.3-bc.10 diff --git a/go.sum b/go.sum index f918d76ab..648a0fbc6 100644 --- a/go.sum +++ b/go.sum @@ -58,8 +58,6 @@ github.com/beorn7/perks v1.0.1 h1:VlbKKnNfV8bJzeqoa4cOKqO6bYr3WgKZxO8Z16+hsOM= github.com/beorn7/perks v1.0.1/go.mod h1:G2ZrVWU2WbWT9wwq4/hrbKbnv/1ERSJQ0ibhJ6rlkpw= github.com/bgentry/speakeasy v0.1.0 h1:ByYyxL9InA1OWqxJqqp2A5pYHUrCiAL6K3J+LKSsQkY= github.com/bgentry/speakeasy v0.1.0/go.mod h1:+zsyZBPWlz7T6j88CTgSN5bM796AkVf0kBD4zp0CCIs= -github.com/bnb-chain/bnc-cosmos-sdk v0.26.5 h1:6NFIkrAURJdXP1w+cdVnyIxrtuDev4sg3kM86kteVvA= -github.com/bnb-chain/bnc-cosmos-sdk v0.26.5/go.mod h1:XiDYVT+XqECR+AyCBO4KBsrbL/d1x2UTsVU36SvHxI8= github.com/bnb-chain/bnc-go-amino v0.14.1-binance.2 h1:iAlp9gqG0f2LGAauf3ZiijWlT6NI+W2r9y70HH9LI3k= github.com/bnb-chain/bnc-go-amino v0.14.1-binance.2/go.mod h1:LiCO7jev+3HwLGAiN9gpD0z+jTz95RqgSavbse55XOY= github.com/bnb-chain/bnc-tendermint v0.32.3-bc.10 h1:E4iSwEbJCLYchHiHE1gnOM3jjmJXLBxARhy/RCl8CpI= @@ -143,6 +141,8 @@ github.com/envoyproxy/go-control-plane v0.9.4/go.mod h1:6rpuAdCZL397s3pYoYcLgu1m github.com/envoyproxy/protoc-gen-validate v0.1.0/go.mod h1:iSmxcyjqTsJpI2R4NaDN7+kN2VEUnK/pcBlmesArF7c= github.com/etcd-io/bbolt v1.3.3 h1:gSJmxrs37LgTqR/oyJBWok6k6SvXEUerFTbltIhXkBM= github.com/etcd-io/bbolt v1.3.3/go.mod h1:ZF2nL25h33cCyBtcyWeZ2/I3HQOfTP+0PIEvHjkjCrw= +github.com/forcodedancing/bnc-cosmos-sdk v0.25.8-0.20230705071422-875aa9cf6664 h1:ZgRdXdvAMFVkGAMNiu+LDb2u9ID0Gq+DC4tqEBBiyxo= +github.com/forcodedancing/bnc-cosmos-sdk v0.25.8-0.20230705071422-875aa9cf6664/go.mod h1:XiDYVT+XqECR+AyCBO4KBsrbL/d1x2UTsVU36SvHxI8= github.com/fortytw2/leaktest v1.2.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= github.com/fortytw2/leaktest v1.3.0 h1:u8491cBMTQ8ft8aeV+adlcytMZylmA5nnwwkRZjI8vw= github.com/fortytw2/leaktest v1.3.0/go.mod h1:jDsjWgpAGjm2CA7WthBh/CdZYEPF31XHquHwclZch5g= @@ -480,6 +480,7 @@ golang.org/x/mod v0.1.1-0.20191107180719-034126e5016b/go.mod h1:QqPTAvyqsEbceGzB golang.org/x/mod v0.2.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.3.0/go.mod h1:s0Qsj1ACt9ePp/hMypM3fl4fZqREWJwdYDEqhRiZZUA= golang.org/x/mod v0.6.0-dev.0.20220419223038-86c51ed26bb4/go.mod h1:jJ57K6gSWd91VN4djpZkiMVwK6gcyfeH4XE8wZrZaV4= +golang.org/x/mod v0.8.0/go.mod h1:iBbtSCu2XBx23ZKBPSOrRkjjQPZFPuis4dIYUhu/chs= golang.org/x/net v0.0.0-20180719180050-a680a1efc54d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180724234803-3673e40ba225/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= golang.org/x/net v0.0.0-20180826012351-8a410e7b638d/go.mod h1:mL1N/T3taQHkDXs73rZJwtUhF3w3ftmwwsq0BUmARs4= @@ -519,8 +520,10 @@ golang.org/x/net v0.0.0-20220127200216-cd36cc0744dd/go.mod h1:CfG3xpIq0wQ8r1q4Su golang.org/x/net v0.0.0-20220225172249-27dd8689420f/go.mod h1:CfG3xpIq0wQ8r1q4Su4UZFWDARRcnwPjda9FqA0JpMk= golang.org/x/net v0.0.0-20220722155237-a158d28d115b/go.mod h1:XRhObCWvk6IyKnWLug+ECip1KBveYUHfp+8e9klMJ9c= golang.org/x/net v0.0.0-20220812174116-3211cb980234/go.mod h1:YDH+HFinaLZZlnHAfSS6ZXJJ9M9t4Dl22yv3iI2vPwk= -golang.org/x/net v0.7.0 h1:rJrUqqhjsgNp7KqAIc25s9pZnjU7TUcSY7HcVZjdn1g= +golang.org/x/net v0.6.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= golang.org/x/net v0.7.0/go.mod h1:2Tu9+aMcznHK/AK1HMvgo6xiTLG5rD5rZLDS+rp2Bjs= +golang.org/x/net v0.11.0 h1:Gi2tvZIJyBtO9SDr1q9h5hEQCp/4L2RQ+ar0qjx2oNU= +golang.org/x/net v0.11.0/go.mod h1:2L/ixqYpgIVXmeoSA/4Lu7BzTG4KIyPIryS4IsOd1oQ= golang.org/x/oauth2 v0.0.0-20180821212333-d2e6202438be/go.mod h1:N/0e6XlmueqKjAGxoOufVs8QHGRruUQn6yWY3a++T0U= golang.org/x/oauth2 v0.0.0-20190226205417-e64efc72b421/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= golang.org/x/oauth2 v0.0.0-20190604053449-0f29369cfe45/go.mod h1:gOpvHmFTYa4IltrdGE7lF6nIHvwfUNPOp7c8zoXwtLw= @@ -540,6 +543,7 @@ golang.org/x/sync v0.0.0-20201020160332-67f06af15bc9/go.mod h1:RxMgew5VJxzue5/jJ golang.org/x/sync v0.0.0-20201207232520-09787c993a3a/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20220601150217-0de741cfad7f/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sync v0.0.0-20220722155255-886fb9371eb4/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= +golang.org/x/sync v0.1.0/go.mod h1:RxMgew5VJxzue5/jJTE5uejpjVlOe/izrB70Jof72aM= golang.org/x/sys v0.0.0-20180830151530-49385e6e1522/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180905080454-ebe1bf3edb33/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= golang.org/x/sys v0.0.0-20180909124046-d0be0721c37e/go.mod h1:STP8DvDyc/dI5b8T5hshtkjS+E42TnysNCUPdjciGhY= @@ -593,11 +597,13 @@ golang.org/x/sys v0.0.0-20220520151302-bc2c85ada10a/go.mod h1:oPkhp1MJrh7nUepCBc golang.org/x/sys v0.0.0-20220722155257-8c9f86f7a55f/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.0.0-20220728004956-3c1f35247d10/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/sys v0.1.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= -golang.org/x/sys v0.5.0 h1:MUK/U/4lj1t1oPg0HfuXDN/Z1wv31ZJ/YcPiGccS4DU= golang.org/x/sys v0.5.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= +golang.org/x/sys v0.9.0 h1:KS/R3tvhPqvJvwcKfnBHJwwthS11LRhmM5D59eEXa0s= +golang.org/x/sys v0.9.0/go.mod h1:oPkhp1MJrh7nUepCBck5+mAzfO9JrbApNNgaTdGDITg= golang.org/x/term v0.0.0-20201126162022-7de9c90e9dd1/go.mod h1:bj7SfCRtBDWHUb9snDiAeCFNEtKQo2Wmx5Cou7ajbmo= golang.org/x/term v0.0.0-20210927222741-03fcf44c2211/go.mod h1:jbD1KX2456YbFQfuXm/mYQcufACuNUgVhRMnK/tPxf8= golang.org/x/term v0.5.0/go.mod h1:jMB1sMXY+tzblOD4FWmEbocvup2/aLOaQEp7JmGp78k= +golang.org/x/term v0.9.0/go.mod h1:M6DEAAIenWoTxdKrOltXcmDY3rSplQUkrvaDU5FcQyo= golang.org/x/text v0.0.0-20170915032832-14c0d48ead0c/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.0/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= golang.org/x/text v0.3.1-0.20180807135948-17ff2d5776d2/go.mod h1:NqM8EUOU14njkJ3fqMW+pc6Ldnwhi/IjpwHt7yyuwOQ= @@ -605,8 +611,9 @@ golang.org/x/text v0.3.2/go.mod h1:bEr9sfX3Q8Zfm5fL9x+3itogRgK3+ptLWKqgva+5dAk= golang.org/x/text v0.3.3/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.6/go.mod h1:5Zoc/QRtKVWzQhOtBMvqHzDpF6irO9z98xDceosuGiQ= golang.org/x/text v0.3.7/go.mod h1:u+2+/6zg+i71rQMx5EYifcz6MCKuco9NR6JIITiCfzQ= -golang.org/x/text v0.7.0 h1:4BRB4x83lYWy72KwLD/qYDuTu7q9PjSagHvijDw7cLo= golang.org/x/text v0.7.0/go.mod h1:mrYo+phRRbMaCq/xk9113O4dZlRixOauAjOtrjsXDZ8= +golang.org/x/text v0.10.0 h1:UpjohKhiEgNc0CSauXmwYftY1+LlaC75SJwh0SgCX58= +golang.org/x/text v0.10.0/go.mod h1:TvPlkZtksWOMsz7fbANvkp4WM8x/WCo/om8BMLbz+aE= golang.org/x/time v0.0.0-20181108054448-85acf8d2951c/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20190308202827-9d24e82272b4/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= golang.org/x/time v0.0.0-20191024005414-555d28b269f0/go.mod h1:tRJNPiyCQ0inRvYxbN9jk5I+vvW/OXSQhTDSoE431IQ= @@ -655,6 +662,7 @@ golang.org/x/tools v0.0.0-20200804011535-6c149bb5ef0d/go.mod h1:njjCfa9FT2d7l9Bc golang.org/x/tools v0.0.0-20200825202427-b303f430e36d/go.mod h1:njjCfa9FT2d7l9Bc6FUM5FLjQPp3cFF28FI3qnDFljA= golang.org/x/tools v0.0.0-20210106214847-113979e3529a/go.mod h1:emZCQorbCU4vsT4fOWvOPXz4eW1wZW4PmDk9uLelYpA= golang.org/x/tools v0.1.12/go.mod h1:hNGJHUnrk76NpqgfD5Aqm5Crs+Hm0VOH/i9J2+nxYbc= +golang.org/x/tools v0.6.0/go.mod h1:Xwgl3UAJ/d3gWutnCtw505GrjyAbvKui8lOU390QaIU= golang.org/x/xerrors v0.0.0-20190717185122-a985d3407aa7/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191011141410-1b5146add898/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= golang.org/x/xerrors v0.0.0-20191204190536-9bdfabe68543/go.mod h1:I/5z698sn9Ka8TeJc9MKroUUfqBBauWjQqLJ2OPfmY0= diff --git a/networks/demo/bind.exp b/networks/demo/bind.exp new file mode 100755 index 000000000..a312fd61c --- /dev/null +++ b/networks/demo/bind.exp @@ -0,0 +1,19 @@ +#!/usr/bin/expect + +set symbol [lindex $argv 0] +set contract_address [lindex $argv 1] +set amount [lindex $argv 2] +set expire_time [lindex $argv 3] +set from [lindex $argv 4] +set chain_id [lindex $argv 5] +set home [lindex $argv 6] + +set timeout 30 + if {"${home}" == ""} { + spawn ./bnbcli bridge bind --symbol $symbol --contract-address $contract_address --amount $amount --contract-decimals 18 --expire-time $expire_time --from $from --chain-id $chain_id + } else { + spawn ./bnbcli bridge bind --home $home --symbol $symbol --contract-address $contract_address --amount $amount --contract-decimals 18 --expire-time $expire_time --from $from --chain-id $chain_id + } + expect "Password*" + send "12345678\r" +expect eof diff --git a/networks/demo/burn.exp b/networks/demo/burn.exp new file mode 100644 index 000000000..7134ca5b3 --- /dev/null +++ b/networks/demo/burn.exp @@ -0,0 +1,17 @@ +#!/usr/bin/expect + +set symbol [lindex $argv 0] +set amount [lindex $argv 1] +set from [lindex $argv 2] +set chain_id [lindex $argv 3] +set home [lindex $argv 4] + +set timeout 30 + if {"${home}" == ""} { + spawn ./bnbcli token burn -s $symbol -n $amount --from $from --chain-id $chain_id + } else { + spawn ./bnbcli token burn --home $home -s $symbol -n $amount --from $from --chain-id $chain_id + } + expect "Password*" + send "12345678\r" +expect eof diff --git a/networks/demo/freeze.exp b/networks/demo/freeze.exp new file mode 100644 index 000000000..bbfdadbb8 --- /dev/null +++ b/networks/demo/freeze.exp @@ -0,0 +1,17 @@ +#!/usr/bin/expect + +set symbol [lindex $argv 0] +set amount [lindex $argv 1] +set from [lindex $argv 2] +set chain_id [lindex $argv 3] +set home [lindex $argv 4] + +set timeout 30 + if {"${home}" == ""} { + spawn ./bnbcli token freeze -s $symbol -n $amount --from $from --chain-id $chain_id + } else { + spawn ./bnbcli token freeze --home $home -s $symbol -n $amount --from $from --chain-id $chain_id + } + expect "Password*" + send "12345678\r" +expect eof diff --git a/networks/demo/transfer-out.exp b/networks/demo/transfer-out.exp new file mode 100755 index 000000000..8a67d8bfd --- /dev/null +++ b/networks/demo/transfer-out.exp @@ -0,0 +1,14 @@ +#!/usr/bin/expect + +set home [lindex $argv 0] +set from [lindex $argv 1] +set chain_id [lindex $argv 2] +set amount [lindex $argv 3] +set to [lindex $argv 4] +set expire_time [lindex $argv 5] + +set timeout 30 + spawn ./bnbcli bridge transfer-out --home $home --from $from --chain-id=$chain_id --amount $amount --to $to --expire-time $expire_time + expect "Password*" + send "12345678\r" +expect eof diff --git a/networks/demo/unbind.exp b/networks/demo/unbind.exp new file mode 100755 index 000000000..db733ddc1 --- /dev/null +++ b/networks/demo/unbind.exp @@ -0,0 +1,16 @@ +#!/usr/bin/expect + +set symbol [lindex $argv 0] +set from [lindex $argv 1] +set chain_id [lindex $argv 2] +set home [lindex $argv 3] + +set timeout 30 + if {"${home}" == ""} { + spawn ./bnbcli bridge unbind --symbol $symbol --from $from --chain-id $chain_id + } else { + spawn ./bnbcli bridge unbind --home $home --symbol $symbol --from $from --chain-id $chain_id + } + expect "Password*" + send "12345678\r" +expect eof diff --git a/networks/demo/unfreeze.exp b/networks/demo/unfreeze.exp new file mode 100644 index 000000000..3a345368f --- /dev/null +++ b/networks/demo/unfreeze.exp @@ -0,0 +1,17 @@ +#!/usr/bin/expect + +set symbol [lindex $argv 0] +set amount [lindex $argv 1] +set from [lindex $argv 2] +set chain_id [lindex $argv 3] +set home [lindex $argv 4] + +set timeout 30 + if {"${home}" == ""} { + spawn ./bnbcli token unfreeze -s $symbol -n $amount --from $from --chain-id $chain_id + } else { + spawn ./bnbcli token unfreeze --home $home -s $symbol -n $amount --from $from --chain-id $chain_id + } + expect "Password*" + send "12345678\r" +expect eof diff --git a/scripts/recon_integration_test.sh b/scripts/recon_integration_test.sh new file mode 100644 index 000000000..d8978bf2a --- /dev/null +++ b/scripts/recon_integration_test.sh @@ -0,0 +1,394 @@ +#!/bin/bash + +set -ex + +cd ./build +if [ $? -ne 0 ]; then + echo "path build does not exists" + exit 1 +fi + +cli_home="./testnodecli" +home="./testnoded" +chain_id="bnbchain-1000" + +keys_operation_words="bnb" +chain_operation_words="Committed" + +function prepare_node() { + cp -f ../networks/demo/*.exp . + + rm -rf ${cli_home} + rm -rf ${home} + mkdir ${cli_home} + mkdir ${home} + + secret=$(./bnbchaind init --moniker testnode --home ${home} --home-client ${cli_home} --chain-id ${chain_id} | grep secret | grep -o ":.*" | grep -o "\".*" | sed "s/\"//g") + echo ${secret} >${home}/secret + + $(cd "./${home}/config" && sed -i -e "s/BEP12Height = 9223372036854775807/BEP12Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP3Height = 9223372036854775807/BEP3Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/timeout_commit = \"1s\"/timeout_commit = \"500ms\"/g" config.toml) + $(cd "./${home}/config" && sed -i -e "s/log_level = \"main\:info,state\:info,\*\:error\"/log_level = \"*\:debug\"/g" config.toml) + $(cd "./${home}/config" && sed -i -e "s/\"min_self_delegation\": \"1000000000000\"/\"min_self_delegation\": \"10000000000\"/g" genesis.json) + $(cd "./${home}/config" && sed -i -e "s/BEP3Height = 9223372036854775807/BEP3Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP8Height = 9223372036854775807/BEP8Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP67Height = 9223372036854775807/BEP67Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP82Height = 9223372036854775807/BEP82Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP84Height = 9223372036854775807/BEP84Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP87Height = 9223372036854775807/BEP87Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/FixFailAckPackageHeight = 9223372036854775807/FixFailAckPackageHeight = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/EnableAccountScriptsForCrossChainTransferHeight = 9223372036854775807/EnableAccountScriptsForCrossChainTransferHeight = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP70Height = 9223372036854775807/BEP70Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP128Height = 9223372036854775807/BEP128Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP151Height = 9223372036854775807/BEP151Height = 1/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP153Height = 9223372036854775807/BEP153Height = 2/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP159Height = 9223372036854775807/BEP159Height = 3/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP159Phase2Height = 9223372036854775807/BEP159Phase2Height = 11/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/LimitConsAddrUpdateIntervalHeight = 9223372036854775807/LimitConsAddrUpdateIntervalHeight = 11/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/breatheBlockInterval = 0/breatheBlockInterval = 5/g" app.toml) + $(cd "./${home}/config" && sed -i -e "s/BEP255Height = 9223372036854775807/BEP255Height = 3/g" app.toml) + + # stop and start node + ps -ef | grep bnbchaind | grep testnoded | awk '{print $2}' | xargs kill -9 + ./bnbchaind start --home ${home} >./testnoded/node.log 2>&1 & + + echo ${secret} +} + +function exit_test() { + # stop node + ps -ef | grep bnbchaind | grep testnoded | awk '{print $2}' | xargs kill -9 + exit $1 +} + +function check_operation() { + printf "\n=================== Checking $1 ===================\n" + echo "$2" + + echo "$2" | grep -q $3 + if [ $? -ne 0 ]; then + echo "Checking $1 Failed" + exit_test 1 + fi +} + +secret=$(prepare_node) +result=$(expect ./recover.exp "${secret}" "alice" true) +check_operation "Recover Key" "${result}" "${keys_operation_words}" + +bob_secret="bottom quick strong ranch section decide pepper broken oven demand coin run jacket curious business achieve mule bamboo remain vote kid rigid bench rubber" +bob_val_addr=bva1ddt3ls9fjcd8mh69ujdg3fxc89qle2a7k8spre +bob_pubkey=bcap1zcjduepqes09r5x3kqnv7nlrcrveh5sxsrqxw222wu8999fa2wpnjher4yxst89v4a +bob_pubkey_new=bcap1zcjduepqcde4hk9kac248hqr3vqxle049f9l5zc58rcacy6nphuay5wt6c5q3ydes7 +result=$(expect ./recover.exp "${bob_secret}" "bob" true) +check_operation "Add Key" "${result}" "${keys_operation_words}" + +carl_secret="mad calm portion vendor fine weather thunder ensure simple fish enrich genre plate kind minor random where crop hero soda isolate pelican provide chimney" +result=$(expect ./recover.exp "${carl_secret}" "carl" true) +check_operation "Add Key" "${result}" "${keys_operation_words}" +# wait for the chain +sleep 10 + +alice_addr=$(./bnbcli keys list --home ${cli_home} | grep alice | grep -o "bnb1[0-9a-zA-Z]*") +bob_addr=$(./bnbcli keys list --home ${cli_home} | grep bob | grep -o "bnb1[0-9a-zA-Z]*") +carl_addr=$(./bnbcli keys list --home ${cli_home} | grep carl | grep -o "bnb1[0-9a-zA-Z]*") + +sleep 5 +# send +result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr}) +check_operation "Send Token" "${result}" "${chain_operation_words}" + +sleep 1 +# send +result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${carl_addr}) +check_operation "Send Token" "${result}" "${chain_operation_words}" + +# staking related +function staking() { + # get parameters + result=$(./bnbcli staking parameters --home ${cli_home} --trust-node) + check_operation "Query Staking Parameters" "${result}" "proposer" + + # get params side-params + result=$(./bnbcli params side-params --home ${cli_home} --trust-node --side-chain-id bsc) + check_operation "Query Staking Parameters" "${result}" "StakeParamSet" + + # get validators + result=$(./bnbcli staking validators --home ${cli_home} --trust-node) + check_operation "Get Validators" "${result}" "Operator" + + # get validator + operator_address=$(echo "${result}" | grep Operator | grep -o "bva[0-9a-zA-Z]*" | head -n1) + result=$(./bnbcli staking validator ${operator_address} --home ${cli_home} --trust-node) + check_operation "Get Validator" "${result}" "Operator" + + # get delegations + result=$(./bnbcli staking delegations ${alice_addr} --home ${cli_home} --trust-node) + check_operation "Get Delegations" "${result}" "Validator" + + # get delegation + validator_address=$(echo "${result}" | grep Validator | grep -o "bva[0-9a-zA-Z]*") + delegator_address=$(echo "${result}" | grep Delegator | grep -o "bnb1[0-9a-zA-Z]*") + result=$(./bnbcli staking delegation --address-delegator ${delegator_address} --validator ${validator_address} --home ${cli_home} --trust-node) + check_operation "Get Delegation" "${result}" "Validator" + + # get pool + result=$(./bnbcli staking pool --home ${cli_home} --trust-node) + + # create validator + result=$(expect ./create-validator-open.exp ${cli_home} bob ${chain_id} ${bob_pubkey}) + check_operation "create validator open" "${result}" "${chain_operation_words}" + sleep 5 + result=$(./bnbcli staking validators --home ${cli_home} --trust-node) + check_operation "Get Validators" "${result}" "Operator" + result=$(./bnbcli staking validator ${bob_val_addr} --home ${cli_home} --trust-node) + check_operation "Get Validator" "${result}" "bob" + check_operation "Get Validator" "${result}" "${bob_pubkey}" + + # edit validator + result=$(expect ./edit-validator.exp ${cli_home} bob ${chain_id} ${bob_pubkey_new}) + check_operation "edit validator" "${result}" "${chain_operation_words}" + sleep 5 + result=$(./bnbcli staking validator ${bob_val_addr} --home ${cli_home} --trust-node) + check_operation "Get Validator" "${result}" "bob-new" + check_operation "Get Validator" "${result}" "${bob_pubkey_new}" + bob_val_addr=$(echo "${result}" | grep Operator | grep -o "bva[0-9a-zA-Z]*") + + # run test with go-sdk + cd ../e2e && go run . +} + +# token related +function token() { + sleep 1 + # issue token + result=$(expect ./issue.exp BTC Bitcoin 1000000000000000 true bob ${chain_id} ${cli_home}) + btc_symbol=$(echo "${result}" | tail -n 1 | grep -o "BTC-[0-9A-Z]*") + check_operation "Issue Token" "${result}" "${chain_operation_words}" + + sleep 1 + # bind + result=$(expect ./bind.exp ${btc_symbol} 0x6aade9709155a8386c63c1d2e5939525b960b4e7 10000000000000 4083424190 bob ${chain_id} ${cli_home}) + check_operation "Bind Token" "${result}" "${chain_operation_words}" + + sleep 1 + # issue token + result=$(expect ./issue.exp ETH Ethereum 1000000000000000 true bob ${chain_id} ${cli_home}) + eth_symbol=$(echo "${result}" | tail -n 1 | grep -o "ETH-[0-9A-Z]*") + check_operation "Issue Token" "${result}" "${chain_operation_words}" + + sleep 1 + # freeze token + result=$(expect ./freeze.exp ${btc_symbol} 100000000 bob ${chain_id} ${cli_home}) + check_operation "Freeze Token" "${result}" "${chain_operation_words}" + + sleep 1 + # send + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr}) + check_operation "Send Token" "${result}" "${chain_operation_words}" + + sleep 1 + # multi send + echo ${bob_addr} + result=$(expect ./multi_send.exp ${cli_home} alice ${chain_id} "[{\"to\":\"${bob_addr}\",\"amount\":\"100000000000000:BNB\"},{\"to\":\"${alice_addr}\",\"amount\":\"100000000000000:BNB\"}]") + check_operation "Multi Send Token" "${result}" "${chain_operation_words}" + + sleep 1 + # mint token + result=$(expect ./mint.exp ${btc_symbol} 1000000000000000 bob ${chain_id} ${cli_home}) + check_operation "Mint Token" "${result}" "${chain_operation_words}" + + sleep 1 + # burn token + result=$(expect ./burn.exp ${btc_symbol} 50000000 bob ${chain_id} ${cli_home}) + check_operation "Burn Token" "${result}" "${chain_operation_words}" + + sleep 1 + # unfreeze token + result=$(expect ./unfreeze.exp ${btc_symbol} 100000000 bob ${chain_id} ${cli_home}) + check_operation "Freeze Token" "${result}" "${chain_operation_words}" +} + +# gov related +function gov() { + sleep 1 + # propose list + ((expire_time = $(date '+%s') + 1000)) + lower_case_btc_symbol=$(echo ${btc_symbol} | tr 'A-Z' 'a-z') + result=$(expect ./propose_list.exp ${chain_id} alice 200000000000:BNB ${lower_case_btc_symbol} bnb 100000000 "list BTC/BNB" "list BTC/BNB" ${cli_home} ${expire_time} 5) + check_operation "Propose list" "${result}" "${chain_operation_words}" + + sleep 2 + # vote for propose + result=$(expect ./vote.exp alice ${chain_id} 1 Yes ${cli_home}) + check_operation "Vote" "${result}" "${chain_operation_words}" + +} + +# account related +function account() { + sleep 1 + ## query account balance + result=$(./bnbcli account $bob_addr --trust-node) + balance1=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + + sleep 1 + # set an account flag which isn't bounded to transfer memo checker script + result=$(expect ./set_account_flags.exp 0x02 bob ${chain_id} ${cli_home}) + check_operation "Set account flags" "${result}" "${chain_operation_words}" + + sleep 1 + ## query account balance + result=$(./bnbcli account $bob_addr --trust-node) + balance2=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + check_operation "Check fee deduction for set account flags transaction" "$(expr $balance2 - $balance1)" "100000000" + + sleep 1 + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr}) + check_operation "Send Token" "${result}" "${chain_operation_words}" + + sleep 1 + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr} "123456abcd") + check_operation "Send Token" "${result}" "${chain_operation_words}" + + sleep 1 + # set an account flag which is bounded to transfer memo checker script + result=$(expect ./set_account_flags.exp 0x01 bob ${chain_id} ${cli_home}) + check_operation "Set account flags" "${result}" "${chain_operation_words}" + + sleep 1 + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr}) + check_operation "Send Token" "${result}" "ERROR" + + sleep 1 + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr} "123456abcd") + check_operation "Send Token" "${result}" "ERROR:" + + sleep 1 + result=$(expect ./send.exp ${cli_home} alice ${chain_id} "100000000000000:BNB" ${bob_addr} "1234567890") + check_operation "Send Token" "${result}" "${chain_operation_words}" + +} + +# swap related +function swap() { + sleep 1 + # Create an atomic swap + result=$(expect ./HTLT-cross-chain.exp 2000 "100000000:BNB" "100000000:BNB" $bob_addr 0xf2fbB6C41271064613D6f44C7EE9A6c471Ec9B25 alice ${chain_id} ${cli_home}) + check_operation "Create an atomic swap" "${result}" "${chain_operation_words}" + randomNumber=$(sed 's/Random number: //g' <<<$(echo "${result}" | grep -o "Random number: [0-9a-z]*")) + timestamp=$(sed 's/Timestamp: //g' <<<$(echo "${result}" | grep -o "Timestamp: [0-9]*")) + randomNumberHash=$(sed 's/Random number hash: //g' <<<$(echo "${result}" | grep -o "Random number hash: [0-9a-z]*")) + swapID=$(sed 's/swapID: //g' <<<$(echo "${result}" | tail -n 1 | grep -o "swapID: [0-9a-z]*")) + sleep 1 + + atomicSwap=$(./bnbcli token query-swap --swap-id ${swapID} --trust-node) + swapFrom=$(echo "${atomicSwap}" | jq -r '.from') + check_operation "Check swap creator address" $swapFrom $alice_addr + swapTo=$(echo "${atomicSwap}" | jq -r '.to') + check_operation "swap recipient address" $swapTo $bob_addr + + result=$(./bnbcli account bnb1wxeplyw7x8aahy93w96yhwm7xcq3ke4f8ge93u --trust-node) + swapDeadAddrBalance=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + check_operation "the balance of swap dead address" $swapDeadAddrBalance "100000000" + + result=$(./bnbcli account $bob_addr --trust-node) + balanceBobBeforeClaim=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + + # Claim an atomic swap + result=$(expect ./claim.exp ${swapID} $randomNumber alice ${chain_id} ${cli_home}) + check_operation "claim an atomic swap" "${result}" "${chain_operation_words}" + + sleep 1 + + result=$(./bnbcli account $bob_addr --trust-node) + balanceBobAfterClaim=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + check_operation "Bob balance after claim swap" "$(expr $balanceBobAfterClaim - $balanceBobBeforeClaim)" "100000000" + + # Create an atomic swap + result=$(expect ./HTLT-cross-chain.exp 2000 "100000000:BNB" "100000000:BNB" $alice_addr 0xf2fbB6C41271064613D6f44C7EE9A6c471Ec9B25 bob ${chain_id} ${cli_home}) + check_operation "Create an atomic swap" "${result}" "${chain_operation_words}" + swapID=$(sed 's/swapID: //g' <<<$(echo "${result}" | tail -n 1 | grep -o "swapID: [0-9a-z]*")) + + sleep 1 + + # Refund an atomic swap + result=$(expect ./refund.exp ${swapID} alice ${chain_id} ${cli_home}) + check_operation "refund an atomic swap which is still not expired" "${result}" "ERROR" + + sleep 1 + + result=$(./bnbcli account bnb1wxeplyw7x8aahy93w96yhwm7xcq3ke4f8ge93u --trust-node) + swapDeadAddrBalance=$(echo "${result}" | jq -r '.value.base.coins[0].amount') + check_operation "the balance of swap dead address" $swapDeadAddrBalance "100000000" + + sleep 1 + # Create a single chain atomic swap + result=$(expect ./HTLT-single-chain.exp 2000 "100000000:BNB" "10000:${eth_symbol}" $bob_addr alice ${chain_id} ${cli_home}) + check_operation "Create a single chain atomic swap" "${result}" "${chain_operation_words}" + randomNumber=$(sed 's/Random number: //g' <<<$(echo "${result}" | grep -o "Random number: [0-9a-z]*")) + timestamp=$(sed 's/Timestamp: //g' <<<$(echo "${result}" | grep -o "Timestamp: [0-9]*")) + randomNumberHash=$(sed 's/Random number hash: //g' <<<$(echo "${result}" | grep -o "Random number hash: [0-9a-z]*")) + swapID=$(sed 's/swapID: //g' <<<$(echo "${result}" | tail -n 1 | grep -o "swapID: [0-9a-z]*")) + + sleep 1 + # Deposit to a single chain atomic swap + result=$(expect ./deposit.exp ${swapID} "10000:${eth_symbol}" bob ${chain_id} ${cli_home}) + check_operation "Deposit to a single chain atomic swap" "${result}" "${chain_operation_words}" + + sleep 1 + # Claim a single chain atomic swap + result=$(expect ./claim.exp ${swapID} ${randomNumber} alice ${chain_id} ${cli_home}) + check_operation "claim a single chain atomic swap" "${result}" "${chain_operation_words}" + + sleep 1 + # Deposit to a single chain atomic swap + result=$(expect ./deposit.exp ${swapID} "10000:${eth_symbol}" bob ${chain_id} ${cli_home}) + check_operation "Deposit to a closed single chain atomic swap" "${result}" "ERROR" + + sleep 1 + # Create a single chain atomic swap + result=$(expect ./HTLT-single-chain.exp 360 "100000000:BNB" "10000:${eth_symbol}" $bob_addr alice ${chain_id} ${cli_home}) + check_operation "Create a single chain atomic swap" "${result}" "${chain_operation_words}" + randomNumber=$(sed 's/Random number: //g' <<<$(echo "${result}" | grep -o "Random number: [0-9a-z]*")) + timestamp=$(sed 's/Timestamp: //g' <<<$(echo "${result}" | grep -o "Timestamp: [0-9]*")) + randomNumberHash=$(sed 's/Random number hash: //g' <<<$(echo "${result}" | grep -o "Random number hash: [0-9a-z]*")) + swapID=$(sed 's/swapID: //g' <<<$(echo "${result}" | tail -n 1 | grep -o "swapID: [0-9a-z]*")) + + sleep 1 + # Deposit to a single chain atomic swap + result=$(expect ./deposit.exp ${swapID} "10000:${eth_symbol}" bob ${chain_id} ${cli_home}) + check_operation "Deposit to a single chain atomic swap" "${result}" "${chain_operation_words}" + + sleep 1 + # Deposit to a single chain atomic swap + result=$(expect ./deposit.exp ${swapID} "10000:${eth_symbol}" bob ${chain_id} ${cli_home}) + check_operation "Deposit to a deposited single chain atomic swap" "${result}" "ERROR" + +} + +# bridge related +function bridge() { + echo "skip, due to crosschain needed" + # sleep 1 + # # Transfer out + # result=$(expect ./transfer-out.exp ${cli_home} alice ${chain_id} "10000:${btc_symbol}" 0x4307fa0f0b4a9fe83e4ed88ae93a33b03892be03 4083424190) + # check_operation "Transfer Out" "${result}" "${chain_operation_words}" + + # sleep 1 + # # Unbind + # result=$(expect ./unbind.exp ${btc_symbol} alice ${chain_id} ${cli_home}) + # check_operation "Unbind" "${result}" "${chain_operation_words}" +} + +sleep 10 + +token +bridge +gov +account +swap +staking + +exit_test 0