Commit 4efefa6e authored by QM's avatar QM

add ethinterface.go

parent 4ddc2e22
......@@ -36,12 +36,10 @@ func PrepareTestEnv() (bind.ContractBackend, *ethtxs.DeployPara) {
}
alloc[addr] = account
}
gasLimit := uint64(100000000)
sim := backends.NewSimulatedBackend(alloc, gasLimit)
InitPowers := []*big.Int{big.NewInt(80), big.NewInt(10), big.NewInt(10)}
para := &ethtxs.DeployPara{
DeployPrivateKey: genesiskey,
Deployer: genesisAddr,
......@@ -55,12 +53,6 @@ func PrepareTestEnv() (bind.ContractBackend, *ethtxs.DeployPara) {
}
func PrepareTestEnvironment(deployerPrivateKey string, ethValidatorAddrKeys []string) (bind.ContractBackend, *ethtxs.DeployPara) {
//var deployerPrivateKey = "8656d2bc732a8a816a461ba5e2d8aac7c7f85c26a813df30d5327210465eb230"
//var ethValidatorAddrKeyA = "3fa21584ae2e4fd74db9b58e2386f5481607dfa4d7ba0617aaa7858e5025dc1e"
//var ethValidatorAddrKeyB = "a5f3063552f4483cfc20ac4f40f45b798791379862219de9e915c64722c1d400"
//var ethValidatorAddrKeyC = "bbf5e65539e9af0eb0cfac30bad475111054b09c11d668fc0731d54ea777471e"
//var ethValidatorAddrKeyD = "c9fa31d7984edf81b8ef3b40c761f1847f6fcd5711ab2462da97dc458f1f896b"
genesiskey, _ := crypto.HexToECDSA(deployerPrivateKey)
alloc := make(core.GenesisAlloc)
genesisAddr := crypto.PubkeyToAddress(genesiskey.PublicKey)
......@@ -70,12 +62,6 @@ func PrepareTestEnvironment(deployerPrivateKey string, ethValidatorAddrKeys []st
}
alloc[genesisAddr] = genesisAccount
//ethValidatorAddrKey := make([]string, 0)
//ethValidatorAddrKey = append(ethValidatorAddrKey, ethValidatorAddrKeyA)
//ethValidatorAddrKey = append(ethValidatorAddrKey, ethValidatorAddrKeyB)
//ethValidatorAddrKey = append(ethValidatorAddrKey, ethValidatorAddrKeyC)
//ethValidatorAddrKey = append(ethValidatorAddrKey, ethValidatorAddrKeyD)
var InitValidators []common.Address
var ValidatorPriKey []*ecdsa.PrivateKey
for _, v := range ethValidatorAddrKeys {
......
package ethinterface
import (
"context"
"math/big"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/accounts/abi/bind/backends"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
)
type EthClientSpec interface {
bind.ContractBackend
TransactionReceipt(ctx context.Context, txHash common.Hash) (*types.Receipt, error)
BalanceAt(ctx context.Context, account common.Address, blockNumber *big.Int) (*big.Int, error)
HeaderByNumber(ctx context.Context, number *big.Int) (*types.Header, error)
}
type SimExtend struct {
*backends.SimulatedBackend
}
func (sim *SimExtend) HeaderByNumber(ctx context.Context, number *big.Int) (*types.Header, error) {
return sim.Blockchain().CurrentBlock().Header(), nil
}
......@@ -3,14 +3,13 @@ package ethtxs
import (
"context"
"errors"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethcontract/generated"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethclient"
)
func GetOperator(client *ethclient.Client, sender, bridgeBank common.Address) (common.Address, error) {
func GetOperator(client ethinterface.EthClientSpec, sender, bridgeBank common.Address) (common.Address, error) {
header, err := client.HeaderByNumber(context.Background(), nil)
if err != nil {
txslog.Error("GetOperator", "Failed to get HeaderByNumber due to:", err.Error())
......@@ -68,7 +67,7 @@ func IsProphecyPending(claimID [32]byte, validator common.Address, chain33Bridge
return active, nil
}
func GetBalance(client *ethclient.Client, tokenAddr, owner string) (string, error) {
func GetBalance(client ethinterface.EthClientSpec, tokenAddr, owner string) (string, error) {
//查询ERC20余额
if tokenAddr != "" {
bridgeToken, err := generated.NewBridgeToken(common.HexToAddress(tokenAddr), client)
......@@ -113,13 +112,13 @@ func GetLockedFunds(bridgeBank *generated.BridgeBank, tokenAddrStr string) (stri
return balance.String(), nil
}
func GetDepositFunds(backend bind.ContractBackend, tokenAddrStr string) (string, error) {
func GetDepositFunds(client ethinterface.EthClientSpec, tokenAddrStr string) (string, error) {
if tokenAddrStr == "" {
return "", errors.New("nil token address")
}
tokenAddr := common.HexToAddress(tokenAddrStr)
bridgeToken, err := generated.NewBridgeToken(tokenAddr, backend)
bridgeToken, err := generated.NewBridgeToken(tokenAddr, client)
if nil != err {
return "", err
}
......
......@@ -4,39 +4,39 @@ import (
"errors"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethcontract/generated"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
"github.com/ethereum/go-ethereum/common"
)
func RecoverContractHandler(backend bind.ContractBackend, sender, registry common.Address) (*X2EthContracts, *X2EthDeployInfo, error) {
bridgeBankAddr, err := GetAddressFromBridgeRegistry(backend, sender, registry, BridgeBank)
func RecoverContractHandler(client ethinterface.EthClientSpec, sender, registry common.Address) (*X2EthContracts, *X2EthDeployInfo, error) {
bridgeBankAddr, err := GetAddressFromBridgeRegistry(client, sender, registry, BridgeBank)
if nil != err {
return nil, nil, errors.New("Failed to get addr for bridgeBank from registry")
return nil, nil, errors.New("failed to get addr for bridgeBank from registry")
}
bridgeBank, err := generated.NewBridgeBank(*bridgeBankAddr, backend)
bridgeBank, err := generated.NewBridgeBank(*bridgeBankAddr, client)
if nil != err {
return nil, nil, errors.New("Failed to NewBridgeBank")
return nil, nil, errors.New("failed to NewBridgeBank")
}
chain33BridgeAddr, err := GetAddressFromBridgeRegistry(backend, sender, registry, Chain33Bridge)
chain33BridgeAddr, err := GetAddressFromBridgeRegistry(client, sender, registry, Chain33Bridge)
if nil != err {
return nil, nil, errors.New("Failed to get addr for chain33BridgeAddr from registry")
return nil, nil, errors.New("failed to get addr for chain33BridgeAddr from registry")
}
chain33Bridge, err := generated.NewChain33Bridge(*chain33BridgeAddr, backend)
chain33Bridge, err := generated.NewChain33Bridge(*chain33BridgeAddr, client)
if nil != err {
return nil, nil, errors.New("Failed to NewChain33Bridge")
return nil, nil, errors.New("failed to NewChain33Bridge")
}
oracleAddr, err := GetAddressFromBridgeRegistry(backend, sender, registry, Oracle)
oracleAddr, err := GetAddressFromBridgeRegistry(client, sender, registry, Oracle)
if nil != err {
return nil, nil, errors.New("Failed to get addr for oracleBridgeAddr from registry")
return nil, nil, errors.New("failed to get addr for oracleBridgeAddr from registry")
}
oracle, err := generated.NewOracle(*oracleAddr, backend)
oracle, err := generated.NewOracle(*oracleAddr, client)
if nil != err {
return nil, nil, errors.New("Failed to NewOracle")
return nil, nil, errors.New("failed to NewOracle")
}
registryInstance, _ := generated.NewBridgeRegistry(registry, backend)
registryInstance, _ := generated.NewBridgeRegistry(registry, client)
x2EthContracts := &X2EthContracts{
BridgeRegistry: registryInstance,
BridgeBank: bridgeBank,
......@@ -54,14 +54,14 @@ func RecoverContractHandler(backend bind.ContractBackend, sender, registry commo
return x2EthContracts, x2EthDeployInfo, nil
}
func RecoverOracleInstance(backend bind.ContractBackend, sender, registry common.Address) (*generated.Oracle, error) {
oracleAddr, err := GetAddressFromBridgeRegistry(backend, sender, registry, Oracle)
func RecoverOracleInstance(client ethinterface.EthClientSpec, sender, registry common.Address) (*generated.Oracle, error) {
oracleAddr, err := GetAddressFromBridgeRegistry(client, sender, registry, Oracle)
if nil != err {
return nil, errors.New("Failed to get addr for oracleBridgeAddr from registry")
return nil, errors.New("failed to get addr for oracleBridgeAddr from registry")
}
oracle, err := generated.NewOracle(*oracleAddr, backend)
oracle, err := generated.NewOracle(*oracleAddr, client)
if nil != err {
return nil, errors.New("Failed to NewOracle")
return nil, errors.New("failed to NewOracle")
}
return oracle, nil
......
......@@ -4,12 +4,11 @@ import (
"context"
"log"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/ethclient"
bridgeRegistry "github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethcontract/generated"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
ebrelayerTypes "github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/types"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/common"
)
// ContractRegistry :
......@@ -32,8 +31,8 @@ func (d ContractRegistry) String() string {
}
// GetAddressFromBridgeRegistry : utility method which queries the requested contract address from the BridgeRegistry
func GetAddressFromBridgeRegistry(backend bind.ContractBackend, sender, registry common.Address, target ContractRegistry) (address *common.Address, err error) {
header, err := backend.(*ethclient.Client).HeaderByNumber(context.Background(), nil)
func GetAddressFromBridgeRegistry(client ethinterface.EthClientSpec, sender, registry common.Address, target ContractRegistry) (address *common.Address, err error) {
header, err := client.HeaderByNumber(context.Background(), nil)
if err != nil {
txslog.Error("GetAddressFromBridgeRegistry", "Failed to get HeaderByNumber due to:", err.Error())
return nil, err
......@@ -48,7 +47,7 @@ func GetAddressFromBridgeRegistry(backend bind.ContractBackend, sender, registry
}
// Initialize BridgeRegistry instance
registryInstance, err := bridgeRegistry.NewBridgeRegistry(registry, backend)
registryInstance, err := bridgeRegistry.NewBridgeRegistry(registry, client)
if err != nil {
txslog.Error("GetAddressFromBridgeRegistry", "Failed to NewBridgeRegistry to:", err.Error())
return nil, err
......@@ -86,7 +85,7 @@ func GetAddressFromBridgeRegistry(backend bind.ContractBackend, sender, registry
}
// GetDeployHeight : 获取合约部署高度
func GetDeployHeight(client *ethclient.Client, sender, registry common.Address) (height int64, err error) {
func GetDeployHeight(client ethinterface.EthClientSpec, sender, registry common.Address) (height int64, err error) {
header, err := client.HeaderByNumber(context.Background(), nil)
if err != nil {
txslog.Error("GetAddressFromBridgeRegistry", "Failed to get HeaderByNumber due to:", err.Error())
......
......@@ -2,8 +2,8 @@ package ethtxs
import (
"crypto/ecdsa"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
"github.com/ethereum/go-ethereum/common/hexutil"
"github.com/33cn/chain33/common/log/log15"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethcontract/generated"
......@@ -23,10 +23,10 @@ const (
)
// RelayOracleClaimToEthereum : relays the provided burn or lock to Chain33Bridge contract on the Ethereum network
func RelayOracleClaimToEthereum(oracleInstance *generated.Oracle, backend bind.ContractBackend, sender common.Address, event events.Event, claim ProphecyClaim, privateKey *ecdsa.PrivateKey, chain33TxHash []byte) (txhash string, err error) {
txslog.Info("RelayProphecyClaimToEthereum", "sender", sender.String(), "event", event, "chain33Sender", common.ToHex(claim.Chain33Sender), "ethereumReceiver", claim.EthereumReceiver.String(), "TokenAddress", claim.TokenContractAddress.String(), "symbol", claim.Symbol, "Amount", claim.Amount.String(), "claimType", claim.ClaimType.String())
func RelayOracleClaimToEthereum(oracleInstance *generated.Oracle, client ethinterface.EthClientSpec, sender common.Address, event events.Event, claim ProphecyClaim, privateKey *ecdsa.PrivateKey, chain33TxHash []byte) (txhash string, err error) {
txslog.Info("RelayProphecyClaimToEthereum", "sender", sender.String(), "event", event, "chain33Sender", hexutil.Encode(claim.Chain33Sender), "ethereumReceiver", claim.EthereumReceiver.String(), "TokenAddress", claim.TokenContractAddress.String(), "symbol", claim.Symbol, "Amount", claim.Amount.String(), "claimType", claim.ClaimType.String())
auth, err := PrepareAuth(backend, privateKey, sender)
auth, err := PrepareAuth(client, privateKey, sender)
if nil != err {
txslog.Error("RelayProphecyClaimToEthereum", "PrepareAuth err", err.Error())
return "", err
......
......@@ -8,6 +8,7 @@ import (
"sync"
"time"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
"github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/common"
......@@ -15,7 +16,6 @@ import (
"github.com/ethereum/go-ethereum/common/math"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/crypto/secp256k1"
"github.com/ethereum/go-ethereum/ethclient"
solsha3 "github.com/miguelmota/go-solidity-sha3"
)
......@@ -34,8 +34,6 @@ func (ethTxStatus EthTxStatus) String() string {
const (
PendingDuration4TxExeuction = 300
EthTxFail = EthTxStatus(0)
EthTxSuccess = EthTxStatus(1)
EthTxPending = EthTxStatus(2)
)
......@@ -64,7 +62,7 @@ func prefixMessage(message common.Hash, key *ecdsa.PrivateKey) ([]byte, []byte)
return sig, prefixed
}
func getNonce(sender common.Address, backend bind.ContractBackend) (*big.Int, error) {
func getNonce(sender common.Address, client ethinterface.EthClientSpec) (*big.Int, error) {
if nonceMutex, exist := addr2Nonce[sender]; exist {
nonceMutex.rw.Lock()
defer nonceMutex.rw.Unlock()
......@@ -74,7 +72,7 @@ func getNonce(sender common.Address, backend bind.ContractBackend) (*big.Int, er
return big.NewInt(nonceMutex.nonce), nil
}
nonce, err := backend.PendingNonceAt(context.Background(), sender)
nonce, err := client.PendingNonceAt(context.Background(), sender)
if nil != err {
return nil, err
}
......@@ -95,43 +93,41 @@ func revokeNonce(sender common.Address) (*big.Int, error) {
txslog.Debug("revokeNonce", "address", sender.String(), "nonce", nonceMutex.nonce)
return big.NewInt(nonceMutex.nonce), nil
}
return nil, errors.New("Address doesn't exist tx")
return nil, errors.New("address doesn't exist tx")
}
func PrepareAuth(backend bind.ContractBackend, privateKey *ecdsa.PrivateKey, transactor common.Address) (*bind.TransactOpts, error) {
//var backend bind.ContractBackend = client
//client *ethclient.Client
if nil == privateKey || nil == backend {
txslog.Error("PrepareAuth", "nil input parameter", "backend", backend, "privateKey", privateKey)
func PrepareAuth(client ethinterface.EthClientSpec, privateKey *ecdsa.PrivateKey, transactor common.Address) (*bind.TransactOpts, error) {
if nil == privateKey || nil == client {
txslog.Error("PrepareAuth", "nil input parameter", "client", client, "privateKey", privateKey)
return nil, errors.New("nil input parameter")
}
ctx := context.Background()
gasPrice, err := backend.SuggestGasPrice(ctx)
gasPrice, err := client.SuggestGasPrice(ctx)
if err != nil {
txslog.Error("PrepareAuth", "Failed to SuggestGasPrice due to:", err.Error())
return nil, errors.New("Failed to get suggest gas price")
return nil, errors.New("failed to get suggest gas price")
}
auth := bind.NewKeyedTransactor(privateKey)
auth.Value = big.NewInt(0) // in wei
auth.GasLimit = GasLimit4Deploy
auth.GasPrice = gasPrice
if auth.Nonce, err = getNonce(transactor, backend); err != nil {
if auth.Nonce, err = getNonce(transactor, client); err != nil {
return nil, err
}
return auth, nil
}
func waitEthTxFinished(client *ethclient.Client, txhash common.Hash, txName string) error {
func waitEthTxFinished(client ethinterface.EthClientSpec, txhash common.Hash, txName string) error {
txslog.Info(txName, "Wait for tx to be finished executing with hash", txhash.String())
timeout := time.NewTimer(PendingDuration4TxExeuction * time.Second)
oneSecondtimeout := time.NewTicker(5 * time.Second)
for {
select {
case <-timeout.C:
return errors.New("Eth tx timeout")
return errors.New("eth tx timeout")
case <-oneSecondtimeout.C:
_, err := client.TransactionReceipt(context.Background(), txhash)
if err == ethereum.NotFound {
......@@ -145,7 +141,7 @@ func waitEthTxFinished(client *ethclient.Client, txhash common.Hash, txName stri
}
}
func GetEthTxStatus(client *ethclient.Client, txhash common.Hash) string {
func GetEthTxStatus(client ethinterface.EthClientSpec, txhash common.Hash) string {
receipt, err := client.TransactionReceipt(context.Background(), txhash)
if nil != err {
return EthTxPending.String()
......
......@@ -11,15 +11,13 @@ import (
"sync/atomic"
"time"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/ethclient"
dbm "github.com/33cn/chain33/common/db"
log "github.com/33cn/chain33/common/log/log15"
"github.com/33cn/chain33/rpc/jsonclient"
rpctypes "github.com/33cn/chain33/rpc/types"
chain33Types "github.com/33cn/chain33/types"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethcontract/generated"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethinterface"
relayerTx "github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/ethtxs"
"github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/events"
syncTx "github.com/33cn/plugin/plugin/dapp/x2ethereum/ebrelayer/relayer/chain33/transceiver/sync"
......@@ -33,7 +31,7 @@ var relayerLog = log.New("module", "chain33_relayer")
type Relayer4Chain33 struct {
syncTxReceipts *syncTx.TxReceipts
ethBackend bind.ContractBackend
ethClient ethinterface.EthClientSpec
rpcLaddr string //用户向指定的blockchain节点进行rpc调用
fetchHeightPeriodMs int64
db dbm.DB
......@@ -53,7 +51,7 @@ type Relayer4Chain33 struct {
// StartChain33Relayer : initializes a relayer which witnesses events on the chain33 network and relays them to Ethereum
func StartChain33Relayer(ctx context.Context, syncTxConfig *ebTypes.SyncTxConfig, registryAddr, provider string, db dbm.DB) *Relayer4Chain33 {
relayer := &Relayer4Chain33{
chian33Relayer := &Relayer4Chain33{
rpcLaddr: syncTxConfig.Chain33Host,
fetchHeightPeriodMs: syncTxConfig.FetchHeightPeriodMs,
unlock: make(chan int),
......@@ -76,12 +74,12 @@ func StartChain33Relayer(ctx context.Context, syncTxConfig *ebTypes.SyncTxConfig
if err != nil {
panic(err)
}
relayer.ethBackend = client
relayer.totalTx4Chain33ToEth = relayer.getTotalTxAmount2Eth()
relayer.statusCheckedIndex = relayer.getStatusCheckedIndex()
chian33Relayer.ethClient = client
chian33Relayer.totalTx4Chain33ToEth = chian33Relayer.getTotalTxAmount2Eth()
chian33Relayer.statusCheckedIndex = chian33Relayer.getStatusCheckedIndex()
go relayer.syncProc(syncCfg)
return relayer
go chian33Relayer.syncProc(syncCfg)
return chian33Relayer
}
func (chain33Relayer *Relayer4Chain33) QueryTxhashRelay2Eth() ebTypes.Txhashes {
......@@ -97,7 +95,7 @@ func (chain33Relayer *Relayer4Chain33) syncProc(syncCfg *ebTypes.SyncTxReceiptCo
chain33Relayer.syncTxReceipts = syncTx.StartSyncTxReceipt(syncCfg, chain33Relayer.db)
chain33Relayer.lastHeight4Tx = chain33Relayer.loadLastSyncHeight()
oracleInstance, err := relayerTx.RecoverOracleInstance(chain33Relayer.ethBackend, chain33Relayer.bridgeRegistryAddr, chain33Relayer.bridgeRegistryAddr)
oracleInstance, err := relayerTx.RecoverOracleInstance(chain33Relayer.ethClient, chain33Relayer.bridgeRegistryAddr, chain33Relayer.bridgeRegistryAddr)
if err != nil {
panic(err.Error())
}
......@@ -137,7 +135,7 @@ func (chain33Relayer *Relayer4Chain33) onNewHeightProc(currentHeight int64) {
relayerLog.Error("onNewHeightProc", "getEthTxhash for index ", index, "error", err.Error())
break
}
status := relayerTx.GetEthTxStatus(chain33Relayer.ethBackend.(*ethclient.Client), txhash)
status := relayerTx.GetEthTxStatus(chain33Relayer.ethClient, txhash)
//按照提交交易的先后顺序检查交易,只要出现当前交易还在pending状态,就不再检查后续交易,等到下个区块再从该交易进行检查
//TODO:可能会由于网络和打包挖矿的原因,使得交易执行顺序和提交顺序有差别,后续完善该检查逻辑
if status == relayerTx.EthTxPending.String() {
......@@ -221,7 +219,7 @@ func (chain33Relayer *Relayer4Chain33) handleBurnLockMsg(claimEvent events.Event
prophecyClaim := relayerTx.Chain33MsgToProphecyClaim(*chain33Msg)
// Relay the Chain33Msg to the Ethereum network
txhash, err := relayerTx.RelayOracleClaimToEthereum(chain33Relayer.oracleInstance, chain33Relayer.ethBackend, chain33Relayer.ethSender, claimEvent, prophecyClaim, chain33Relayer.privateKey4Ethereum, chain33TxHash)
txhash, err := relayerTx.RelayOracleClaimToEthereum(chain33Relayer.oracleInstance, chain33Relayer.ethClient, chain33Relayer.ethSender, claimEvent, prophecyClaim, chain33Relayer.privateKey4Ethereum, chain33TxHash)
if nil != err {
return err
}
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment