move package test/ => integration/
This commit is contained in:
@@ -0,0 +1,82 @@
|
||||
package integration
|
||||
|
||||
import (
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"math/big"
|
||||
"net/http"
|
||||
|
||||
"github.com/ethereum/go-ethereum/common"
|
||||
"github.com/ethereum/go-ethereum/rpc"
|
||||
"github.com/ethereum/go-ethereum/statediff/types"
|
||||
)
|
||||
|
||||
type ContractDeployed struct {
|
||||
Address common.Address `json:"address"`
|
||||
TransactionHash common.Hash `json:"txHash"`
|
||||
BlockNumber int64 `json:"blockNumber"`
|
||||
BlockHash common.Hash `json:"blockHash"`
|
||||
}
|
||||
|
||||
type ContractDestroyed struct {
|
||||
BlockNumber int64 `json:"blockNumber"`
|
||||
}
|
||||
|
||||
type Tx struct {
|
||||
From string `json:"from"`
|
||||
To string `json:"to"`
|
||||
Value *big.Int `json:"value"`
|
||||
TransactionHash string `json:"txHash"`
|
||||
BlockNumber int64 `json:"blockNumber"`
|
||||
BlockHash string `json:"blockHash"`
|
||||
}
|
||||
|
||||
type StorageKey struct {
|
||||
Key string `json:"key"`
|
||||
}
|
||||
|
||||
type CountIncremented struct {
|
||||
BlockNumber *big.Int `json:"blockNumber"`
|
||||
}
|
||||
|
||||
const ContractServerUrl = "http://localhost:3000"
|
||||
|
||||
// Factory which creates endpoint functions
|
||||
func MakeGetAndDecodeFunc[R any](format string) func(...interface{}) (*R, error) {
|
||||
return func(params ...interface{}) (*R, error) {
|
||||
params = append([]interface{}{ContractServerUrl}, params...)
|
||||
url := fmt.Sprintf(format, params...)
|
||||
res, err := http.Get(url)
|
||||
if err != nil {
|
||||
return nil, err
|
||||
}
|
||||
defer res.Body.Close()
|
||||
|
||||
if res.StatusCode != http.StatusOK {
|
||||
return nil, fmt.Errorf("%s: %s", url, res.Status)
|
||||
}
|
||||
|
||||
var data R
|
||||
decoder := json.NewDecoder(res.Body)
|
||||
return &data, decoder.Decode(&data)
|
||||
}
|
||||
}
|
||||
|
||||
var (
|
||||
DeployContract = MakeGetAndDecodeFunc[ContractDeployed]("%s/v1/deployContract")
|
||||
DestroyContract = MakeGetAndDecodeFunc[ContractDestroyed]("%s/v1/destroyContract?addr=%s")
|
||||
DeploySLVContract = MakeGetAndDecodeFunc[ContractDeployed]("%s/v1/deploySLVContract")
|
||||
DestroySLVContract = MakeGetAndDecodeFunc[ContractDestroyed]("%s/v1/destroySLVContract?addr=%s")
|
||||
SendEth = MakeGetAndDecodeFunc[Tx]("%s/v1/sendEth?to=%s&value=%s")
|
||||
GetStorageSlotKey = MakeGetAndDecodeFunc[StorageKey]("%s/v1/getStorageKey?contract=%s&label=%s")
|
||||
IncrementCount = MakeGetAndDecodeFunc[CountIncremented]("%s/v1/incrementCount%s?addr=%s")
|
||||
Create2Contract = MakeGetAndDecodeFunc[ContractDeployed]("%s/v1/create2Contract?contract=%s&salt=%s")
|
||||
)
|
||||
|
||||
func ClearWatchedAddresses(gethRPCClient *rpc.Client) error {
|
||||
gethMethod := "statediff_watchAddress"
|
||||
args := []types.WatchAddressArg{}
|
||||
|
||||
// Clear watched addresses
|
||||
return gethRPCClient.Call(nil, gethMethod, types.Clear, args)
|
||||
}
|
||||
@@ -0,0 +1,378 @@
|
||||
package integration_test
|
||||
|
||||
import (
|
||||
"context"
|
||||
"math/big"
|
||||
"math/rand"
|
||||
|
||||
"github.com/ethereum/go-ethereum"
|
||||
"github.com/ethereum/go-ethereum/common"
|
||||
. "github.com/onsi/ginkgo/v2"
|
||||
. "github.com/onsi/gomega"
|
||||
|
||||
"github.com/cerc-io/ipld-eth-server/v5/integration"
|
||||
"github.com/cerc-io/ipld-eth-server/v5/pkg/eth"
|
||||
)
|
||||
|
||||
var _ = Describe("Direct proxy integration test", Label("proxy"), func() {
|
||||
ctx := context.Background()
|
||||
|
||||
var contract *integration.ContractDeployed
|
||||
var tx *integration.Tx
|
||||
var contractErr error
|
||||
var txErr error
|
||||
|
||||
Describe("get Block", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("get not existing block by number", func() {
|
||||
blockNum := contract.BlockNumber + 100
|
||||
|
||||
gethBlock, err := gethClient.BlockByNumber(ctx, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(gethBlock).To(BeZero())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByNumber(ctx, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(ipldBlock).To(BeZero())
|
||||
})
|
||||
|
||||
It("get not existing block by hash", func() {
|
||||
gethBlock, err := gethClient.BlockByHash(ctx, nonExistingBlockHash)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(gethBlock).To(BeZero())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByHash(ctx, nonExistingBlockHash)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(ipldBlock).To(BeZero())
|
||||
})
|
||||
|
||||
It("get block by number", func() {
|
||||
blockNum := contract.BlockNumber
|
||||
|
||||
_, err := gethClient.BlockByNumber(ctx, big.NewInt(blockNum))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.BlockByNumber(ctx, big.NewInt(blockNum))
|
||||
Expect(err).To(HaveOccurred())
|
||||
})
|
||||
|
||||
It("get block by hash", func() {
|
||||
_, err := gethClient.BlockByHash(ctx, contract.BlockHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.BlockByHash(ctx, contract.BlockHash)
|
||||
Expect(err).To(HaveOccurred())
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Transaction", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("Get tx by hash", func() {
|
||||
_, _, err := gethClient.TransactionByHash(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, _, err = ipldClient.TransactionByHash(ctx, contract.TransactionHash)
|
||||
Expect(err).To(HaveOccurred())
|
||||
Expect(err.Error()).To(ContainSubstring("not found"))
|
||||
})
|
||||
|
||||
It("Get tx by block hash and index", func() {
|
||||
_, err := gethClient.TransactionInBlock(ctx, contract.BlockHash, 0)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.TransactionInBlock(ctx, contract.BlockHash, 0)
|
||||
Expect(err).To(HaveOccurred())
|
||||
Expect(err.Error()).To(ContainSubstring("not found"))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Receipt", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("Get tx receipt", func() {
|
||||
_, err := gethClient.TransactionReceipt(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.TransactionReceipt(ctx, contract.TransactionHash)
|
||||
Expect(err).To(HaveOccurred())
|
||||
Expect(err.Error()).To(ContainSubstring("not found"))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("FilterLogs", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("with blockhash", func() {
|
||||
blockHash := contract.BlockHash
|
||||
filterQuery := ethereum.FilterQuery{
|
||||
//Addresses: addresses,
|
||||
BlockHash: &blockHash,
|
||||
Topics: [][]common.Hash{},
|
||||
}
|
||||
|
||||
gethLogs, err := gethClient.FilterLogs(ctx, filterQuery)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldLogs, err := ipldClient.FilterLogs(ctx, filterQuery)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
// not empty list
|
||||
Expect(gethLogs).ToNot(BeEmpty())
|
||||
// empty list
|
||||
Expect(ipldLogs).To(BeEmpty())
|
||||
})
|
||||
})
|
||||
|
||||
Describe("CodeAt", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("gets code of deployed contract with block number", func() {
|
||||
_, err := gethClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(ipldCode).To(BeEmpty())
|
||||
})
|
||||
It("gets code of contract that doesn't exist at this height", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethCode).To(BeEmpty())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
|
||||
It("gets code at non-existing address without block number", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethCode).To(BeEmpty())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
It("gets code of deployed contract without block number", func() {
|
||||
_, err := gethClient.CodeAt(ctx, contract.Address, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(ipldCode).To(BeEmpty())
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Get balance", func() {
|
||||
var newAddress common.Address
|
||||
rand.Read(newAddress[:])
|
||||
|
||||
BeforeEach(func() {
|
||||
tx, txErr = integration.SendEth(newAddress, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("gets balance for an account with eth without block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethBalance.String()).To(Equal("10000000000000000"))
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, newAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(ipldBalance.String()).To(Equal("0"))
|
||||
})
|
||||
It("gets balance for an account with eth with block number", func() {
|
||||
_, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
})
|
||||
It("gets historical balance for an account with eth with block number", func() {
|
||||
_, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
})
|
||||
|
||||
It("gets balance for a non-existing account without block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
It("gets balance for an non-existing block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber+3))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, nonExistingAddress, big.NewInt(tx.BlockNumber+3))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Get Storage", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("gets ERC20 total supply (without block number)", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethStorage)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(ipldStorage).To(Equal(make([]byte, 32)))
|
||||
})
|
||||
|
||||
It("gets ERC20 total supply (with block number)", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethStorage)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
_, err = ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing account", func() {
|
||||
_, err := gethClient.StorageAt(ctx, nonExistingAddress, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.StorageAt(ctx, nonExistingAddress, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing contract slot", func() {
|
||||
_, err := gethClient.StorageAt(ctx, contract.Address, randomHash, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.StorageAt(ctx, contract.Address, randomHash, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing contract", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(0))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(0))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing block number", func() {
|
||||
blockNum := contract.BlockNumber + 100
|
||||
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("get storage after self destruct", func() {
|
||||
tx, err := integration.DestroyContract(contract.Address)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethStorage1, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
gethStorage2, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethStorage1).NotTo(Equal(gethStorage2))
|
||||
Expect(gethStorage2).To(Equal(eth.EmptyNodeValue))
|
||||
|
||||
_, err = ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
_, err = ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
// Query the current block
|
||||
ipldStorage3, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(eth.EmptyNodeValue).To(Equal(ipldStorage3))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("eth call", func() {
|
||||
var msg ethereum.CallMsg
|
||||
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
msg = ethereum.CallMsg{
|
||||
To: &contract.Address,
|
||||
Data: common.Hex2Bytes("18160ddd"), // totalSupply()
|
||||
}
|
||||
})
|
||||
|
||||
It("calls totalSupply() without block number", func() {
|
||||
gethResult, err := gethClient.CallContract(ctx, msg, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethResult)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldResult, err := ipldClient.CallContract(ctx, msg, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethResult).To(Equal(ipldResult))
|
||||
})
|
||||
|
||||
It("calls totalSupply() with block number", func() {
|
||||
gethResult, err := gethClient.CallContract(ctx, msg, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethResult)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldResult, err := ipldClient.CallContract(ctx, msg, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethResult).To(Equal(ipldResult))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Chain ID", func() {
|
||||
It("Check chain id", func() {
|
||||
_, err := gethClient.ChainID(ctx)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
_, err = ipldClient.ChainID(ctx)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
})
|
||||
})
|
||||
@@ -0,0 +1,53 @@
|
||||
package integration_test
|
||||
|
||||
import (
|
||||
"os"
|
||||
"strconv"
|
||||
"testing"
|
||||
|
||||
"github.com/ethereum/go-ethereum/ethclient"
|
||||
"github.com/ethereum/go-ethereum/rpc"
|
||||
. "github.com/onsi/ginkgo/v2"
|
||||
. "github.com/onsi/gomega"
|
||||
)
|
||||
|
||||
func TestIntegration(t *testing.T) {
|
||||
RegisterFailHandler(Fail)
|
||||
RunSpecs(t, "integration test suite")
|
||||
}
|
||||
|
||||
var (
|
||||
gethHttpPath = "http://127.0.0.1:8545"
|
||||
ipldEthHttpPath = "http://127.0.0.1:8081"
|
||||
|
||||
gethClient *ethclient.Client
|
||||
ipldClient *ethclient.Client
|
||||
gethRPCClient *rpc.Client
|
||||
ipldRPCClient *rpc.Client
|
||||
|
||||
testChainId int64 = 99
|
||||
)
|
||||
|
||||
var _ = BeforeSuite(func() {
|
||||
var err error
|
||||
|
||||
envChainID := os.Getenv("ETH_CHAIN_ID")
|
||||
if len(envChainID) == 0 {
|
||||
panic("ETH_CHAIN_ID must be set")
|
||||
}
|
||||
testChainId, err = strconv.ParseInt(envChainID, 10, 64)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
if path := os.Getenv("ETH_HTTP_PATH"); len(path) != 0 {
|
||||
gethHttpPath = "http://" + path
|
||||
}
|
||||
if path := os.Getenv("SERVER_HTTP_PATH"); len(path) != 0 {
|
||||
ipldEthHttpPath = "http://" + path
|
||||
}
|
||||
|
||||
gethClient, err = ethclient.Dial(gethHttpPath)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldClient, err = ethclient.Dial(ipldEthHttpPath)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
@@ -0,0 +1,547 @@
|
||||
package integration_test
|
||||
|
||||
import (
|
||||
"context"
|
||||
"math/big"
|
||||
"math/rand"
|
||||
"time"
|
||||
|
||||
"github.com/ethereum/go-ethereum"
|
||||
"github.com/ethereum/go-ethereum/common"
|
||||
"github.com/ethereum/go-ethereum/core/types"
|
||||
"github.com/ethereum/go-ethereum/crypto"
|
||||
"github.com/ethereum/go-ethereum/rlp"
|
||||
. "github.com/onsi/ginkgo/v2"
|
||||
. "github.com/onsi/gomega"
|
||||
|
||||
integration "github.com/cerc-io/ipld-eth-server/v5/integration"
|
||||
"github.com/cerc-io/ipld-eth-server/v5/pkg/eth"
|
||||
)
|
||||
|
||||
var (
|
||||
nonExistingBlockHash = common.HexToHash("0x111111111111111111111111111111111111111111111111111111111111111")
|
||||
nonExistingAddress = common.HexToAddress("0x1111111111111111111111111111111111111111")
|
||||
randomAddr = common.HexToAddress("0x1C3ab14BBaD3D99F4203bd7a11aCB94882050E6f")
|
||||
randomHash = crypto.Keccak256Hash(randomAddr.Bytes())
|
||||
|
||||
erc20TotalSupply, _ = new(big.Int).SetString("1000000000000000000000", 10)
|
||||
ercTotalSupplyIndex = common.HexToHash("0x2")
|
||||
|
||||
delayInterval = time.Second * 1
|
||||
)
|
||||
|
||||
var _ = Describe("Basic integration test", func() {
|
||||
ctx := context.Background()
|
||||
|
||||
var contract *integration.ContractDeployed
|
||||
var tx *integration.Tx
|
||||
var contractErr error
|
||||
var txErr error
|
||||
|
||||
Describe("get Block", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
time.Sleep(delayInterval)
|
||||
})
|
||||
|
||||
It("get not existing block by number", func() {
|
||||
blockNum := big.NewInt(contract.BlockNumber + 100)
|
||||
|
||||
gethBlock, err := gethClient.BlockByNumber(ctx, blockNum)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(gethBlock).To(BeZero())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByNumber(ctx, blockNum)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(ipldBlock).To(BeZero())
|
||||
})
|
||||
|
||||
It("get not existing block by hash", func() {
|
||||
gethBlock, err := gethClient.BlockByHash(ctx, nonExistingBlockHash)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(gethBlock).To(BeZero())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByHash(ctx, nonExistingBlockHash)
|
||||
Expect(err).To(MatchError(ethereum.NotFound))
|
||||
Expect(ipldBlock).To(BeZero())
|
||||
})
|
||||
|
||||
It("get block by number", func() {
|
||||
blockNum := big.NewInt(contract.BlockNumber)
|
||||
|
||||
gethBlock, err := gethClient.BlockByNumber(ctx, blockNum)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByNumber(ctx, blockNum)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
// check headers are equals
|
||||
Expect(gethBlock.Header()).To(Equal(ipldBlock.Header()))
|
||||
|
||||
gethTxs := gethBlock.Transactions()
|
||||
ipldTxs := ipldBlock.Transactions()
|
||||
|
||||
Expect(gethTxs.Len()).To(Equal(ipldTxs.Len()))
|
||||
Expect(types.TxDifference(gethTxs, ipldTxs).Len()).To(Equal(0))
|
||||
})
|
||||
|
||||
It("get block by hash", func() {
|
||||
gethBlock, err := gethClient.BlockByHash(ctx, contract.BlockHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBlock, err := ipldClient.BlockByHash(ctx, contract.BlockHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
// check headers are equals
|
||||
compareBlocks(gethBlock, ipldBlock)
|
||||
|
||||
gethTxs := gethBlock.Transactions()
|
||||
ipldTxs := ipldBlock.Transactions()
|
||||
|
||||
Expect(gethTxs.Len()).To(Equal(ipldTxs.Len()))
|
||||
Expect(types.TxDifference(gethTxs, ipldTxs).Len()).To(Equal(0))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Transaction", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("Get tx by hash", func() {
|
||||
gethTx, _, err := gethClient.TransactionByHash(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldTx, _, err := ipldClient.TransactionByHash(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
compareTxs(gethTx, ipldTx)
|
||||
|
||||
Expect(gethTx.Hash()).To(Equal(ipldTx.Hash()))
|
||||
})
|
||||
|
||||
It("Get tx by block hash and index", func() {
|
||||
gethTx, err := gethClient.TransactionInBlock(ctx, contract.BlockHash, 0)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldTx, err := ipldClient.TransactionInBlock(ctx, contract.BlockHash, 0)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
compareTxs(gethTx, ipldTx)
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Receipt", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("Get tx receipt", func() {
|
||||
gethReceipt, err := gethClient.TransactionReceipt(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldReceipt, err := ipldClient.TransactionReceipt(ctx, contract.TransactionHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethReceipt).To(Equal(ipldReceipt))
|
||||
|
||||
rlpGeth, err := rlp.EncodeToBytes(gethReceipt)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
rlpIpld, err := rlp.EncodeToBytes(ipldReceipt)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(rlpGeth).To(Equal(rlpIpld))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("FilterLogs", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("with blockhash", func() {
|
||||
blockHash := contract.BlockHash
|
||||
filterQuery := ethereum.FilterQuery{
|
||||
//Addresses: addresses,
|
||||
BlockHash: &blockHash,
|
||||
Topics: [][]common.Hash{},
|
||||
}
|
||||
|
||||
gethLogs, err := gethClient.FilterLogs(ctx, filterQuery)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldLogs, err := ipldClient.FilterLogs(ctx, filterQuery)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
// not empty list
|
||||
Expect(gethLogs).ToNot(BeEmpty())
|
||||
|
||||
Expect(len(gethLogs)).To(Equal(len(ipldLogs)))
|
||||
Expect(gethLogs).To(Equal(ipldLogs))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("CodeAt", func() {
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("gets code at non-existing address without block number", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethCode).To(BeEmpty())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
It("gets code of deployed contract without block number", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, contract.Address, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
It("gets code of deployed contract with block number", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
It("gets code of contract that doesn't exist at this height", func() {
|
||||
gethCode, err := gethClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCode, err := ipldClient.CodeAt(ctx, contract.Address, big.NewInt(contract.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethCode).To(BeEmpty())
|
||||
Expect(gethCode).To(Equal(ipldCode))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Get balance", func() {
|
||||
var newAddress common.Address
|
||||
rand.Read(newAddress[:])
|
||||
|
||||
BeforeEach(func() {
|
||||
tx, txErr = integration.SendEth(newAddress, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("gets balance for an account with eth with block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
It("gets balance for an account with eth without block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, newAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
|
||||
It("gets historical balance for an account with eth with block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
It("gets balance for a non-existing account without block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, nonExistingAddress, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
It("gets balance for an non-existing block number", func() {
|
||||
gethBalance, err := gethClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber+3))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
ipldBalance, err := ipldClient.BalanceAt(ctx, newAddress, big.NewInt(tx.BlockNumber+3))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
Expect(gethBalance).To(Equal(ipldBalance))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Get Storage", func() {
|
||||
var contractSalt string
|
||||
countAIndex := common.HexToHash("0x5")
|
||||
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
Expect(contract.BlockNumber).ToNot(BeZero())
|
||||
|
||||
contractSalt = common.Bytes2Hex(contract.BlockHash[:10])
|
||||
})
|
||||
|
||||
It("gets ERC20 total supply (with block number)", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethStorage)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets ERC20 total supply (without block number)", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethStorage)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing account", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, nonExistingAddress, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, nonExistingAddress, ercTotalSupplyIndex, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing contract slot", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, randomHash, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, randomHash, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing contract", func() {
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(0))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(0))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for non-existing block number", func() {
|
||||
blockNum := contract.BlockNumber + 100
|
||||
gethStorage, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(blockNum))
|
||||
Expect(err).To(MatchError("header not found"))
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
})
|
||||
|
||||
It("gets storage for SLV countA after tx", func() {
|
||||
slvContract, contractErr := integration.Create2Contract("SLVToken", contractSalt)
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
gethStorage, err := gethClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvContract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
slvCountA := new(big.Int).SetBytes(gethStorage)
|
||||
|
||||
err = waitForBlock(ctx, ipldClient, slvContract.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvContract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCountA := new(big.Int).SetBytes(ipldStorage)
|
||||
Expect(ipldCountA).To(Equal(slvCountA))
|
||||
|
||||
inc, err := integration.IncrementCount("A", slvContract.Address)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
slvCountA.Add(slvCountA, big.NewInt(1))
|
||||
|
||||
ipldStorage, err = ipldClient.StorageAt(ctx, slvContract.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldCountA = new(big.Int).SetBytes(ipldStorage)
|
||||
Expect(ipldCountA).To(Equal(slvCountA))
|
||||
})
|
||||
|
||||
It("gets storage after destruction and redeploy", func() {
|
||||
slvContract, contractErr := integration.Create2Contract("SLVToken", contractSalt)
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
tx, err := integration.DestroyContract(contract.Address)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
slvTx, err := integration.DestroyContract(slvContract.Address)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethStorage1, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
gethStorage2, err := gethClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethStorage1).NotTo(Equal(gethStorage2))
|
||||
Expect(gethStorage2).To(Equal(eth.EmptyNodeValue))
|
||||
|
||||
ipldStorage1, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber-1))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
ipldStorage2, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(ipldStorage1).To(Equal(gethStorage1))
|
||||
Expect(ipldStorage2).To(Equal(gethStorage2))
|
||||
|
||||
// Query the current block
|
||||
ipldStorage3, err := ipldClient.StorageAt(ctx, contract.Address, ercTotalSupplyIndex, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(ipldStorage2).To(Equal(ipldStorage3))
|
||||
|
||||
// Check for SLV contract
|
||||
gethStorage, err := gethClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvTx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(gethStorage).To(Equal(eth.EmptyNodeValue))
|
||||
|
||||
ipldStorage, err := ipldClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvTx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(ipldStorage).To(Equal(gethStorage))
|
||||
|
||||
// Redeploy to same address
|
||||
slvContract, contractErr = integration.Create2Contract("SLVToken", contractSalt)
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
gethStorage, err = gethClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvContract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldStorage, err = ipldClient.StorageAt(ctx, slvContract.Address, countAIndex, big.NewInt(slvContract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethStorage).To(Equal(ipldStorage))
|
||||
ipldCountA := new(big.Int).SetBytes(ipldStorage)
|
||||
Expect(ipldCountA.String()).To(Equal("0"))
|
||||
|
||||
})
|
||||
})
|
||||
|
||||
Describe("eth call", func() {
|
||||
var msg ethereum.CallMsg
|
||||
|
||||
BeforeEach(func() {
|
||||
contract, contractErr = integration.DeployContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
msg = ethereum.CallMsg{
|
||||
To: &contract.Address,
|
||||
Data: common.Hex2Bytes("18160ddd"), // totalSupply()
|
||||
}
|
||||
})
|
||||
|
||||
It("calls totalSupply() without block number", func() {
|
||||
gethResult, err := gethClient.CallContract(ctx, msg, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethResult)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldResult, err := ipldClient.CallContract(ctx, msg, nil)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethResult).To(Equal(ipldResult))
|
||||
})
|
||||
|
||||
It("calls totalSupply() with block number", func() {
|
||||
gethResult, err := gethClient.CallContract(ctx, msg, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethResult)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldResult, err := ipldClient.CallContract(ctx, msg, big.NewInt(contract.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethResult).To(Equal(ipldResult))
|
||||
})
|
||||
|
||||
It("calls totalSupply() with block hash", func() {
|
||||
gethResult, err := gethClient.CallContractAtHash(ctx, msg, contract.BlockHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
gethTotalSupply := new(big.Int).SetBytes(gethResult)
|
||||
Expect(gethTotalSupply).To(Equal(erc20TotalSupply))
|
||||
|
||||
ipldResult, err := ipldClient.CallContractAtHash(ctx, msg, contract.BlockHash)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethResult).To(Equal(ipldResult))
|
||||
})
|
||||
})
|
||||
|
||||
Describe("Chain ID", func() {
|
||||
It("Check chain id", func() {
|
||||
gethChainId, err := gethClient.ChainID(ctx)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldChainId, err := ipldClient.ChainID(ctx)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethChainId).To(Equal(ipldChainId))
|
||||
})
|
||||
})
|
||||
})
|
||||
|
||||
func compareBlocks(block1 *types.Block, block2 *types.Block) {
|
||||
GinkgoHelper()
|
||||
Expect(block1.Header()).To(Equal(block2.Header()))
|
||||
Expect(block1.Uncles()).To(Equal(block2.Uncles()))
|
||||
|
||||
txs1 := block1.Transactions()
|
||||
txs2 := block2.Transactions()
|
||||
|
||||
Expect(len(txs1)).To(Equal(len(txs2)))
|
||||
for i, tx := range txs1 {
|
||||
compareTxs(tx, txs2[i])
|
||||
}
|
||||
}
|
||||
|
||||
func compareTxs(tx1 *types.Transaction, tx2 *types.Transaction) {
|
||||
GinkgoHelper()
|
||||
Expect(tx1.Data()).To(Equal(tx2.Data()))
|
||||
Expect(tx1.Hash()).To(Equal(tx2.Hash()))
|
||||
Expect(tx1.Size()).To(Equal(tx2.Size()))
|
||||
|
||||
signer := types.NewLondonSigner(big.NewInt(testChainId))
|
||||
|
||||
gethSender, err := types.Sender(signer, tx1)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldSender, err := types.Sender(signer, tx2)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
Expect(gethSender).To(Equal(ipldSender))
|
||||
}
|
||||
@@ -0,0 +1,28 @@
|
||||
package integration_test
|
||||
|
||||
import (
|
||||
"context"
|
||||
"errors"
|
||||
"time"
|
||||
|
||||
"github.com/ethereum/go-ethereum/ethclient"
|
||||
)
|
||||
|
||||
func waitForBlock(ctx context.Context, client *ethclient.Client, target int64) error {
|
||||
timeout := 10 * time.Second
|
||||
for {
|
||||
select {
|
||||
case <-time.After(timeout):
|
||||
return errors.New("timed out")
|
||||
default:
|
||||
latest, err := client.BlockNumber(ctx)
|
||||
if err != nil {
|
||||
return err
|
||||
}
|
||||
if uint64(target) <= latest {
|
||||
return nil
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
}
|
||||
@@ -0,0 +1,627 @@
|
||||
package integration_test
|
||||
|
||||
import (
|
||||
"context"
|
||||
"math/big"
|
||||
|
||||
"github.com/ethereum/go-ethereum/common"
|
||||
"github.com/ethereum/go-ethereum/rpc"
|
||||
sdtypes "github.com/ethereum/go-ethereum/statediff/types"
|
||||
. "github.com/onsi/ginkgo/v2"
|
||||
. "github.com/onsi/gomega"
|
||||
|
||||
integration "github.com/cerc-io/ipld-eth-server/v5/integration"
|
||||
)
|
||||
|
||||
var (
|
||||
gethMethod = "statediff_watchAddress"
|
||||
ipldMethod = "vdb_watchAddress"
|
||||
)
|
||||
|
||||
var _ = Describe("WatchAddress integration test", func() {
|
||||
var (
|
||||
ctx = context.Background()
|
||||
|
||||
txErr error
|
||||
contractErr error
|
||||
incErr error
|
||||
|
||||
tx *integration.Tx
|
||||
inc *integration.CountIncremented
|
||||
|
||||
contract1 *integration.ContractDeployed
|
||||
contract2 *integration.ContractDeployed
|
||||
contract3 *integration.ContractDeployed
|
||||
|
||||
countAIndex common.Hash
|
||||
|
||||
prevBalance1 *big.Int
|
||||
prevBalance2 *big.Int
|
||||
prevBalance3 *big.Int
|
||||
|
||||
actualBalance1 *big.Int
|
||||
actualBalance2 *big.Int
|
||||
actualBalance3 *big.Int
|
||||
|
||||
prevCountA1 *big.Int
|
||||
prevCountA2 *big.Int
|
||||
prevCountA3 *big.Int
|
||||
|
||||
actualCountA1 *big.Int
|
||||
actualCountA2 *big.Int
|
||||
actualCountA3 *big.Int
|
||||
)
|
||||
|
||||
BeforeEach(func() {
|
||||
var err error
|
||||
|
||||
gethRPCClient, err = rpc.Dial(gethHttpPath)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
ipldRPCClient, err = rpc.Dial(ipldEthHttpPath)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
It("test init", func() {
|
||||
// Deploy three contracts
|
||||
contract1, contractErr = integration.DeploySLVContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
contract2, contractErr = integration.DeploySLVContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
contract3, contractErr = integration.DeploySLVContract()
|
||||
Expect(contractErr).ToNot(HaveOccurred())
|
||||
|
||||
// Get the storage slot key
|
||||
storageSlotAKey, err := integration.GetStorageSlotKey("SLVToken", "countA")
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countAIndex = common.HexToHash(storageSlotAKey.Key)
|
||||
|
||||
// Clear out watched addresses
|
||||
err = integration.ClearWatchedAddresses(gethRPCClient)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
|
||||
// Get initial balances for all the contracts
|
||||
// Contract 1
|
||||
actualBalance1 = big.NewInt(0)
|
||||
initBalance1, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(contract1.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(initBalance1.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1 = big.NewInt(0)
|
||||
|
||||
// Contract 2
|
||||
actualBalance2 = big.NewInt(0)
|
||||
initBalance2, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(contract2.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(initBalance2.String()).To(Equal(actualBalance2.String()))
|
||||
prevBalance2 = big.NewInt(0)
|
||||
|
||||
// Contract 3
|
||||
actualBalance3 = big.NewInt(0)
|
||||
initBalance3, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(contract3.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(initBalance3.String()).To(Equal(actualBalance3.String()))
|
||||
prevBalance3 = big.NewInt(0)
|
||||
|
||||
// Get initial storage values for the contracts
|
||||
// Contract 1, countA
|
||||
actualCountA1 = big.NewInt(0)
|
||||
ipldCountA1Storage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, big.NewInt(contract1.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
ipldCountA1 := new(big.Int).SetBytes(ipldCountA1Storage)
|
||||
Expect(ipldCountA1.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1 = big.NewInt(0)
|
||||
|
||||
// Contract 2, countA
|
||||
actualCountA2 = big.NewInt(0)
|
||||
ipldCountA2Storage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, big.NewInt(contract2.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
ipldCountA2 := new(big.Int).SetBytes(ipldCountA2Storage)
|
||||
Expect(ipldCountA2.String()).To(Equal("0"))
|
||||
prevCountA2 = big.NewInt(0)
|
||||
|
||||
// Contract 3, countA
|
||||
actualCountA3 = big.NewInt(0)
|
||||
ipldCountA3Storage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, big.NewInt(contract3.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
ipldCountA3 := new(big.Int).SetBytes(ipldCountA3Storage)
|
||||
Expect(ipldCountA3.String()).To(Equal("0"))
|
||||
prevCountA3 = big.NewInt(0)
|
||||
})
|
||||
|
||||
defer It("test cleanup", func() {
|
||||
// Clear out watched addresses
|
||||
err := integration.ClearWatchedAddresses(gethRPCClient)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
})
|
||||
|
||||
Context("no contracts being watched", func() {
|
||||
It("indexes state for all the contracts", func() {
|
||||
// WatchedAddresses = []
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1.Set(actualBalance1)
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(actualBalance2.String()))
|
||||
prevBalance2.Set(actualBalance2)
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(actualBalance3.String()))
|
||||
prevBalance3.Set(actualBalance3)
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1.Set(actualCountA1)
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(actualCountA2.String()))
|
||||
prevCountA2.Set(actualCountA2)
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(actualCountA3.String()))
|
||||
prevCountA3.Set(actualCountA3)
|
||||
})
|
||||
})
|
||||
|
||||
Context("one contract being watched", func() {
|
||||
It("indexes state only for the watched contract", func() {
|
||||
operation := sdtypes.Add
|
||||
args := []sdtypes.WatchAddressArg{
|
||||
{
|
||||
Address: contract1.Address.String(),
|
||||
CreatedAt: uint64(contract1.BlockNumber),
|
||||
},
|
||||
}
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).ToNot(HaveOccurred())
|
||||
|
||||
// WatchedAddresses = [Contract1]
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1.Set(actualBalance1)
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(prevBalance2.String()))
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(prevBalance3.String()))
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1.Set(actualCountA1)
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(prevCountA2.String()))
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(prevCountA3.String()))
|
||||
})
|
||||
})
|
||||
|
||||
Context("contract added to a non-empty watch-list", func() {
|
||||
It("indexes state only for the watched contracts", func() {
|
||||
operation := sdtypes.Add
|
||||
args := []sdtypes.WatchAddressArg{
|
||||
{
|
||||
Address: contract2.Address.String(),
|
||||
CreatedAt: uint64(contract2.BlockNumber),
|
||||
},
|
||||
}
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).ToNot(HaveOccurred())
|
||||
|
||||
// WatchedAddresses = [Contract1, Contract2]
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1.Set(actualBalance1)
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(actualBalance2.String()))
|
||||
prevBalance2.Set(actualBalance2)
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(prevBalance3.String()))
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1.Set(actualCountA1)
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(actualCountA2.String()))
|
||||
prevCountA2.Set(actualCountA2)
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(prevCountA3.String()))
|
||||
})
|
||||
})
|
||||
|
||||
Context("contract removed from the watch-list", func() {
|
||||
It("indexes state only for the watched contract", func() {
|
||||
operation := sdtypes.Remove
|
||||
args := []sdtypes.WatchAddressArg{
|
||||
{
|
||||
Address: contract1.Address.String(),
|
||||
CreatedAt: uint64(contract1.BlockNumber),
|
||||
},
|
||||
}
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).ToNot(HaveOccurred())
|
||||
|
||||
// WatchedAddresses = [Contract2]
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(prevBalance1.String()))
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(actualBalance2.String()))
|
||||
prevBalance2.Set(actualBalance2)
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(prevBalance3.String()))
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(prevCountA1.String()))
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(actualCountA2.String()))
|
||||
prevCountA2.Set(actualCountA2)
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(prevCountA3.String()))
|
||||
})
|
||||
})
|
||||
|
||||
Context("list of watched addresses set", func() {
|
||||
It("indexes state only for the watched contracts", func() {
|
||||
operation := sdtypes.Set
|
||||
args := []sdtypes.WatchAddressArg{
|
||||
{
|
||||
Address: contract1.Address.String(),
|
||||
CreatedAt: uint64(contract1.BlockNumber),
|
||||
},
|
||||
{
|
||||
Address: contract3.Address.String(),
|
||||
CreatedAt: uint64(contract3.BlockNumber),
|
||||
},
|
||||
}
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).ToNot(HaveOccurred())
|
||||
|
||||
// WatchedAddresses = [Contract1, Contract3]
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1.Set(actualBalance1)
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(prevBalance2.String()))
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(actualBalance3.String()))
|
||||
prevBalance3.Set(actualBalance3)
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1.Set(actualCountA1)
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(prevCountA2.String()))
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(actualCountA3.String()))
|
||||
prevCountA3.Set(actualCountA3)
|
||||
})
|
||||
})
|
||||
|
||||
Context("list of watched addresses cleared", func() {
|
||||
It("indexes state for all the contracts", func() {
|
||||
operation := sdtypes.Clear
|
||||
args := []sdtypes.WatchAddressArg{}
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).ToNot(HaveOccurred())
|
||||
|
||||
// WatchedAddresses = []
|
||||
// Send eth to all three contract accounts
|
||||
// Contract 1
|
||||
tx, txErr = integration.SendEth(contract1.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance1.Add(actualBalance1, big.NewInt(10000000000000000))
|
||||
|
||||
balance1AfterTransfer, err := ipldClient.BalanceAt(ctx, contract1.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance1AfterTransfer.String()).To(Equal(actualBalance1.String()))
|
||||
prevBalance1.Set(actualBalance1)
|
||||
|
||||
// Contract 2
|
||||
tx, txErr = integration.SendEth(contract2.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance2.Add(actualBalance2, big.NewInt(10000000000000000))
|
||||
|
||||
balance2AfterTransfer, err := ipldClient.BalanceAt(ctx, contract2.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance2AfterTransfer.String()).To(Equal(actualBalance2.String()))
|
||||
prevBalance2.Set(actualBalance2)
|
||||
|
||||
// Contract 3
|
||||
tx, txErr = integration.SendEth(contract3.Address, "0.01")
|
||||
Expect(txErr).ToNot(HaveOccurred())
|
||||
actualBalance3.Add(actualBalance3, big.NewInt(10000000000000000))
|
||||
|
||||
balance3AfterTransfer, err := ipldClient.BalanceAt(ctx, contract3.Address, big.NewInt(tx.BlockNumber))
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
Expect(balance3AfterTransfer.String()).To(Equal(actualBalance3.String()))
|
||||
prevBalance3.Set(actualBalance3)
|
||||
|
||||
// Increment counts
|
||||
// Contract 1, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract1.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA1.Add(actualCountA1, big.NewInt(1))
|
||||
|
||||
countA1AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract1.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA1AfterIncrement := new(big.Int).SetBytes(countA1AfterIncrementStorage)
|
||||
Expect(countA1AfterIncrement.String()).To(Equal(actualCountA1.String()))
|
||||
prevCountA1.Set(actualCountA1)
|
||||
|
||||
// Contract 2, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract2.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA2.Add(actualCountA2, big.NewInt(1))
|
||||
|
||||
countA2AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract2.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA2AfterIncrement := new(big.Int).SetBytes(countA2AfterIncrementStorage)
|
||||
Expect(countA2AfterIncrement.String()).To(Equal(actualCountA2.String()))
|
||||
prevCountA2.Set(actualCountA2)
|
||||
|
||||
// Contract 3, countA
|
||||
inc, incErr = integration.IncrementCount("A", contract3.Address)
|
||||
Expect(incErr).ToNot(HaveOccurred())
|
||||
actualCountA3.Add(actualCountA3, big.NewInt(1))
|
||||
|
||||
countA3AfterIncrementStorage, err := ipldClient.StorageAt(ctx, contract3.Address, countAIndex, inc.BlockNumber)
|
||||
Expect(err).ToNot(HaveOccurred())
|
||||
countA3AfterIncrement := new(big.Int).SetBytes(countA3AfterIncrementStorage)
|
||||
Expect(countA3AfterIncrement.String()).To(Equal(actualCountA3.String()))
|
||||
prevCountA3.Set(actualCountA3)
|
||||
})
|
||||
})
|
||||
|
||||
Context("with invalid args", func() {
|
||||
It("returns an error on invalid operation arg", func() {
|
||||
operation := "WrongOp"
|
||||
args := []sdtypes.WatchAddressArg{}
|
||||
|
||||
gethErr := gethRPCClient.Call(nil, gethMethod, operation, args)
|
||||
Expect(gethErr).To(HaveOccurred())
|
||||
Expect(gethErr.Error()).To(ContainSubstring("unexpected operation"))
|
||||
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).To(HaveOccurred())
|
||||
Expect(ipldErr.Error()).To(ContainSubstring("unexpected operation"))
|
||||
|
||||
Expect(ipldErr).To(Equal(gethErr))
|
||||
})
|
||||
|
||||
It("returns an error on args of invalid type", func() {
|
||||
operation := sdtypes.Add
|
||||
args := []string{"WrongArg"}
|
||||
|
||||
gethErr := gethRPCClient.Call(nil, gethMethod, operation, args)
|
||||
Expect(gethErr).To(HaveOccurred())
|
||||
Expect(gethErr.Error()).To(ContainSubstring("WatchAddressArg"))
|
||||
|
||||
ipldErr := ipldRPCClient.Call(nil, ipldMethod, operation, args)
|
||||
Expect(ipldErr).To(HaveOccurred())
|
||||
Expect(ipldErr.Error()).To(ContainSubstring("WatchAddressArg"))
|
||||
|
||||
Expect(ipldErr).To(Equal(gethErr))
|
||||
})
|
||||
})
|
||||
})
|
||||
Reference in New Issue
Block a user