Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

[TT-1345] option to use predeployed contracts in OCR tests #13758

Merged
merged 14 commits into from
Sep 19, 2024
Merged
Show file tree
Hide file tree
Changes from 7 commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
129 changes: 77 additions & 52 deletions integration-tests/actions/actions.go
Original file line number Diff line number Diff line change
Expand Up @@ -12,40 +12,34 @@ import (
"testing"
"time"

"github.com/pelletier/go-toml/v2"

geth "github.com/ethereum/go-ethereum"
"github.com/ethereum/go-ethereum/accounts/abi"
"github.com/ethereum/go-ethereum/accounts/abi/bind"
"github.com/ethereum/go-ethereum/common"
"github.com/ethereum/go-ethereum/core/types"
gethtypes "github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto"
"github.com/ethereum/go-ethereum/rpc"
"github.com/google/uuid"
"github.com/pelletier/go-toml/v2"
"github.com/pkg/errors"
"github.com/rs/zerolog"
"github.com/smartcontractkit/seth"
"github.com/test-go/testify/require"
"go.uber.org/zap/zapcore"

"github.com/smartcontractkit/chainlink-testing-framework/blockchain"
ctfconfig "github.com/smartcontractkit/chainlink-testing-framework/config"
"github.com/smartcontractkit/chainlink-testing-framework/k8s/environment"
"github.com/smartcontractkit/chainlink-testing-framework/logging"
"github.com/smartcontractkit/chainlink-testing-framework/testreporters"
"github.com/smartcontractkit/chainlink-testing-framework/utils/conversions"
"github.com/smartcontractkit/chainlink/integration-tests/contracts"
ethContracts "github.com/smartcontractkit/chainlink/integration-tests/contracts/ethereum"

"github.com/ethereum/go-ethereum/accounts/abi"

"github.com/ethereum/go-ethereum/core/types"
"github.com/ethereum/go-ethereum/crypto"

"github.com/rs/zerolog"

"github.com/ethereum/go-ethereum/common"
"github.com/google/uuid"
"github.com/smartcontractkit/seth"

gethtypes "github.com/ethereum/go-ethereum/core/types"
"github.com/pkg/errors"
"github.com/test-go/testify/require"

ctfconfig "github.com/smartcontractkit/chainlink-testing-framework/config"
"github.com/smartcontractkit/chainlink-testing-framework/utils/testcontext"

"github.com/smartcontractkit/chainlink/integration-tests/client"
"github.com/smartcontractkit/chainlink/integration-tests/contracts"
ethContracts "github.com/smartcontractkit/chainlink/integration-tests/contracts/ethereum"
"github.com/smartcontractkit/chainlink/integration-tests/testconfig/ocr"
"github.com/smartcontractkit/chainlink/integration-tests/types/config/node"
"github.com/smartcontractkit/chainlink/v2/core/gethwrappers/generated/link_token_interface"
"github.com/smartcontractkit/chainlink/v2/core/gethwrappers/generated/operator_factory"
Expand Down Expand Up @@ -601,29 +595,44 @@ func TrackForwarder(
Msg("Forwarder tracked")
}

// DeployOCRv2Contracts deploys a number of OCRv2 contracts and configures them with defaults
func DeployOCRv2Contracts(
// SetupOCRv2Contracts deploys a number of OCRv2 contracts and configures them with defaults
func SetupOCRv2Contracts(
l zerolog.Logger,
seth *seth.Client,
numberOfContracts int,
ocrContractsConfig ocr.OffChainAggregatorsConfig,
lukaszcl marked this conversation as resolved.
Show resolved Hide resolved
linkTokenAddress common.Address,
transmitters []string,
ocrOptions contracts.OffchainOptions,
) ([]contracts.OffchainAggregatorV2, error) {
var ocrInstances []contracts.OffchainAggregatorV2
for contractCount := 0; contractCount < numberOfContracts; contractCount++ {
ocrInstance, err := contracts.DeployOffchainAggregatorV2(
l,
seth,
linkTokenAddress,
ocrOptions,
)
if err != nil {
return nil, fmt.Errorf("OCRv2 instance deployment have failed: %w", err)

if !ocrContractsConfig.UseExistingOffChainAggregatorsContracts() {
for contractCount := 0; contractCount < ocrContractsConfig.GetNumberOfContractsToDeploy(); contractCount++ {
ocrInstance, err := contracts.DeployOffchainAggregatorV2(
l,
seth,
linkTokenAddress,
ocrOptions,
)
if err != nil {
return nil, fmt.Errorf("OCRv2 instance deployment have failed: %w", err)
}
ocrInstances = append(ocrInstances, &ocrInstance)
if (contractCount+1)%ContractDeploymentInterval == 0 { // For large amounts of contract deployments, space things out some
time.Sleep(2 * time.Second)
}
}
ocrInstances = append(ocrInstances, &ocrInstance)
if (contractCount+1)%ContractDeploymentInterval == 0 { // For large amounts of contract deployments, space things out some
time.Sleep(2 * time.Second)
} else {
for _, address := range ocrContractsConfig.GetOffChainAggregatorsContractsAddresses() {
ocrInstance, err := contracts.LoadOffchainAggregatorV2(l, seth, address)
if err != nil {
return nil, fmt.Errorf("OCRv2 instance loading have failed: %w", err)
}
ocrInstances = append(ocrInstances, &ocrInstance)
}

if !ocrContractsConfig.ConfigureExistingOffChainAggregatorsContracts() {
return ocrInstances, nil
}
}

Expand Down Expand Up @@ -772,7 +781,7 @@ func StartNewRound(
func DeployOCRContractsForwarderFlow(
logger zerolog.Logger,
seth *seth.Client,
numberOfContracts int,
ocrContractsConfig ocr.OffChainAggregatorsConfig,
linkTokenContractAddress common.Address,
workerNodes []contracts.ChainlinkNodeWithKeysAndAddress,
forwarderAddresses []common.Address,
Expand All @@ -793,14 +802,14 @@ func DeployOCRContractsForwarderFlow(
return forwarderAddresses, nil
}

return deployAnyOCRv1Contracts(logger, seth, numberOfContracts, linkTokenContractAddress, workerNodes, transmitterPayeesFn, transmitterAddressesFn)
return setupAnyOCRv1Contracts(logger, seth, ocrContractsConfig, linkTokenContractAddress, workerNodes, transmitterPayeesFn, transmitterAddressesFn)
}

// DeployOCRv1Contracts deploys and funds a certain number of offchain aggregator contracts
func DeployOCRv1Contracts(
// SetupOCRv1Contracts deploys and funds a certain number of offchain aggregator contracts
func SetupOCRv1Contracts(
logger zerolog.Logger,
seth *seth.Client,
numberOfContracts int,
ocrContractsConfig ocr.OffChainAggregatorsConfig,
linkTokenContractAddress common.Address,
workerNodes []contracts.ChainlinkNodeWithKeysAndAddress,
) ([]contracts.OffchainAggregator, error) {
Expand Down Expand Up @@ -834,28 +843,44 @@ func DeployOCRv1Contracts(
return transmitterAddresses, nil
}

return deployAnyOCRv1Contracts(logger, seth, numberOfContracts, linkTokenContractAddress, workerNodes, transmitterPayeesFn, transmitterAddressesFn)
return setupAnyOCRv1Contracts(logger, seth, ocrContractsConfig, linkTokenContractAddress, workerNodes, transmitterPayeesFn, transmitterAddressesFn)
}

func deployAnyOCRv1Contracts(
func setupAnyOCRv1Contracts(
logger zerolog.Logger,
seth *seth.Client,
numberOfContracts int,
ocrContractsConfig ocr.OffChainAggregatorsConfig,
linkTokenContractAddress common.Address,
workerNodes []contracts.ChainlinkNodeWithKeysAndAddress,
getTransmitterAndPayeesFn func() ([]string, []string, error),
getTransmitterAddressesFn func() ([]common.Address, error),
) ([]contracts.OffchainAggregator, error) {
// Deploy contracts
var ocrInstances []contracts.OffchainAggregator
for contractCount := 0; contractCount < numberOfContracts; contractCount++ {
ocrInstance, err := contracts.DeployOffchainAggregator(logger, seth, linkTokenContractAddress, contracts.DefaultOffChainAggregatorOptions())
if err != nil {
return nil, fmt.Errorf("OCR instance deployment have failed: %w", err)

if !ocrContractsConfig.UseExistingOffChainAggregatorsContracts() {
// Deploy contracts
for contractCount := 0; contractCount < ocrContractsConfig.GetNumberOfContractsToDeploy(); contractCount++ {
ocrInstance, err := contracts.DeployOffchainAggregator(logger, seth, linkTokenContractAddress, contracts.DefaultOffChainAggregatorOptions())
if err != nil {
return nil, fmt.Errorf("OCR instance deployment have failed: %w", err)
}
ocrInstances = append(ocrInstances, &ocrInstance)
if (contractCount+1)%ContractDeploymentInterval == 0 { // For large amounts of contract deployments, space things out some
time.Sleep(2 * time.Second)
}
}
ocrInstances = append(ocrInstances, &ocrInstance)
if (contractCount+1)%ContractDeploymentInterval == 0 { // For large amounts of contract deployments, space things out some
time.Sleep(2 * time.Second)
} else {
// Load contract wrappers
for _, address := range ocrContractsConfig.GetOffChainAggregatorsContractsAddresses() {
ocrInstance, err := contracts.LoadOffChainAggregator(logger, seth, address)
if err != nil {
return nil, fmt.Errorf("OCR instance loading have failed: %w", err)
}
ocrInstances = append(ocrInstances, &ocrInstance)
}

if !ocrContractsConfig.ConfigureExistingOffChainAggregatorsContracts() {
return ocrInstances, nil
}
}

Expand Down
21 changes: 21 additions & 0 deletions integration-tests/actions/contracts.go
Original file line number Diff line number Diff line change
@@ -0,0 +1,21 @@
package actions

import (
"github.com/rs/zerolog"
"github.com/smartcontractkit/seth"

"github.com/smartcontractkit/chainlink/integration-tests/contracts"
tc "github.com/smartcontractkit/chainlink/integration-tests/testconfig"
)

func GetLinkTokenContract(l zerolog.Logger, sethClient *seth.Client, configWithLinkToken tc.LinkTokenContractConfig) (*contracts.EthereumLinkToken, error) {
if configWithLinkToken.UseExistingLinkTokenContract() {
linkAddress, err := configWithLinkToken.GetLinkTokenContractAddress()
if err != nil {
return nil, err
}

return contracts.LoadLinkTokenContract(l, sethClient, linkAddress)
}
return contracts.DeployLinkTokenContract(l, sethClient)
}
4 changes: 2 additions & 2 deletions integration-tests/chaos/ocr_chaos_test.go
Original file line number Diff line number Diff line change
Expand Up @@ -181,13 +181,13 @@ func TestOCRChaos(t *testing.T) {
ms, err := ctfClient.ConnectMockServer(testEnvironment)
require.NoError(t, err, "Creating mockserver clients shouldn't fail")

linkContract, err := contracts.DeployLinkTokenContract(l, seth)
linkContract, err := actions.GetLinkTokenContract(l, seth, config.OCR)
require.NoError(t, err, "Error deploying link token contract")

err = actions.FundChainlinkNodesFromRootAddress(l, seth, contracts.ChainlinkK8sClientToChainlinkNodeWithKeysAndAddress(chainlinkNodes), big.NewFloat(10))
require.NoError(t, err)

ocrInstances, err := actions.DeployOCRv1Contracts(l, seth, 1, common.HexToAddress(linkContract.Address()), contracts.ChainlinkK8sClientToChainlinkNodeWithKeysAndAddress(workerNodes))
ocrInstances, err := actions.SetupOCRv1Contracts(l, seth, config.OCR, common.HexToAddress(linkContract.Address()), contracts.ChainlinkK8sClientToChainlinkNodeWithKeysAndAddress(workerNodes))
require.NoError(t, err)
err = actions.CreateOCRJobs(ocrInstances, bootstrapNode, workerNodes, 5, ms, fmt.Sprint(seth.ChainID))
require.NoError(t, err)
Expand Down
59 changes: 22 additions & 37 deletions integration-tests/contracts/ethereum_contracts.go
Original file line number Diff line number Diff line change
Expand Up @@ -206,22 +206,17 @@ type EthereumOffchainAggregator struct {
l zerolog.Logger
}

func LoadOffchainAggregator(l zerolog.Logger, seth *seth.Client, contractAddress common.Address) (EthereumOffchainAggregator, error) {
abi, err := offchainaggregator.OffchainAggregatorMetaData.GetAbi()
if err != nil {
return EthereumOffchainAggregator{}, fmt.Errorf("failed to get OffChain Aggregator ABI: %w", err)
}
seth.ContractStore.AddABI("OffChainAggregator", *abi)
seth.ContractStore.AddBIN("OffChainAggregator", common.FromHex(offchainaggregator.OffchainAggregatorMetaData.Bin))
func LoadOffChainAggregator(l zerolog.Logger, sethClient *seth.Client, contractAddress common.Address) (EthereumOffchainAggregator, error) {
loader := seth.NewContractLoader[offchainaggregator.OffchainAggregator](sethClient)
instance, err := loader.LoadContract("LinkToken", contractAddress, offchainaggregator.OffchainAggregatorMetaData.GetAbi, offchainaggregator.NewOffchainAggregator)

ocr, err := offchainaggregator.NewOffchainAggregator(contractAddress, wrappers.MustNewWrappedContractBackend(nil, seth))
if err != nil {
return EthereumOffchainAggregator{}, fmt.Errorf("failed to instantiate OCR instance: %w", err)
return EthereumOffchainAggregator{}, fmt.Errorf("failed to instantiate OCR v2 instance: %w", err)
}

return EthereumOffchainAggregator{
client: seth,
ocr: ocr,
client: sethClient,
ocr: instance,
address: &contractAddress,
l: l,
}, nil
Expand Down Expand Up @@ -359,10 +354,6 @@ func (o *EthereumOffchainAggregator) SetConfig(
return err
}

// fails with error setting OCR config for contract '0x0DCd1Bf9A1b36cE34237eEaFef220932846BCD82': both gasPrice and (maxFeePerGas or maxPriorityFeePerGas) specified
// but we only have gasPrice set... It also fails with the same error when we enable EIP-1559
// fails when we wait for it to be minted, inside the wrapper there's no error when we call it, so it must be something inside smart contract
// that's reverting it and maybe the error message is completely off
_, err = o.client.Decode(o.ocr.SetConfig(o.client.NewTXOpts(), signers, transmitters, threshold, encodedConfigVersion, encodedConfig))
return err
}
Expand Down Expand Up @@ -586,36 +577,36 @@ type EthereumOffchainAggregatorV2 struct {
l zerolog.Logger
}

func LoadOffChainAggregatorV2(l zerolog.Logger, seth *seth.Client, contractAddress common.Address) (EthereumOffchainAggregatorV2, error) {
oAbi, err := ocr2aggregator.OCR2AggregatorMetaData.GetAbi()
func LoadOffchainAggregatorV2(l zerolog.Logger, seth *seth.Client, address common.Address) (EthereumOffchainAggregatorV2, error) {
contractAbi, err := ocr2aggregator.OCR2AggregatorMetaData.GetAbi()
if err != nil {
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to get OffChain Aggregator ABI: %w", err)
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to get OffChain Aggregator v2 ABI: %w", err)
}
seth.ContractStore.AddABI("OffChainAggregatorV2", *oAbi)
seth.ContractStore.AddABI("OffChainAggregatorV2", *contractAbi)
seth.ContractStore.AddBIN("OffChainAggregatorV2", common.FromHex(ocr2aggregator.OCR2AggregatorMetaData.Bin))

ocr2, err := ocr2aggregator.NewOCR2Aggregator(contractAddress, seth.Client)
ocr2, err := ocr2aggregator.NewOCR2Aggregator(address, seth.Client)
if err != nil {
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to instantiate OCR instance: %w", err)
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to instantiate OCRv2 instance: %w", err)
}

return EthereumOffchainAggregatorV2{
client: seth,
contract: ocr2,
address: &contractAddress,
address: &address,
l: l,
}, nil
}

func DeployOffchainAggregatorV2(l zerolog.Logger, seth *seth.Client, linkTokenAddress common.Address, offchainOptions OffchainOptions) (EthereumOffchainAggregatorV2, error) {
oAbi, err := ocr2aggregator.OCR2AggregatorMetaData.GetAbi()
contractAbi, err := ocr2aggregator.OCR2AggregatorMetaData.GetAbi()
if err != nil {
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to get OffChain Aggregator ABI: %w", err)
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to get OffChain Aggregator v2 ABI: %w", err)
}
seth.ContractStore.AddABI("OffChainAggregatorV2", *oAbi)
seth.ContractStore.AddABI("OffChainAggregatorV2", *contractAbi)
seth.ContractStore.AddBIN("OffChainAggregatorV2", common.FromHex(ocr2aggregator.OCR2AggregatorMetaData.Bin))

ocrDeploymentData2, err := seth.DeployContract(seth.NewTXOpts(), "OffChainAggregatorV2", *oAbi, common.FromHex(ocr2aggregator.OCR2AggregatorMetaData.Bin),
ocrDeploymentData2, err := seth.DeployContract(seth.NewTXOpts(), "OffChainAggregatorV2", *contractAbi, common.FromHex(ocr2aggregator.OCR2AggregatorMetaData.Bin),
linkTokenAddress,
offchainOptions.MinimumAnswer,
offchainOptions.MaximumAnswer,
Expand All @@ -626,12 +617,12 @@ func DeployOffchainAggregatorV2(l zerolog.Logger, seth *seth.Client, linkTokenAd
)

if err != nil {
return EthereumOffchainAggregatorV2{}, fmt.Errorf("OCR instance deployment have failed: %w", err)
return EthereumOffchainAggregatorV2{}, fmt.Errorf("OCRv2 instance deployment have failed: %w", err)
}

ocr2, err := ocr2aggregator.NewOCR2Aggregator(ocrDeploymentData2.Address, wrappers.MustNewWrappedContractBackend(nil, seth))
if err != nil {
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to instantiate OCR instance: %w", err)
return EthereumOffchainAggregatorV2{}, fmt.Errorf("failed to instantiate OCRv2 instance: %w", err)
}

return EthereumOffchainAggregatorV2{
Expand Down Expand Up @@ -774,22 +765,16 @@ func DeployLinkTokenContract(l zerolog.Logger, client *seth.Client) (*EthereumLi
}

func LoadLinkTokenContract(l zerolog.Logger, client *seth.Client, address common.Address) (*EthereumLinkToken, error) {
abi, err := link_token_interface.LinkTokenMetaData.GetAbi()
if err != nil {
return &EthereumLinkToken{}, fmt.Errorf("failed to get LinkToken ABI: %w", err)
}
loader := seth.NewContractLoader[link_token_interface.LinkToken](client)
instance, err := loader.LoadContract("LinkToken", address, link_token_interface.LinkTokenMetaData.GetAbi, link_token_interface.NewLinkToken)

client.ContractStore.AddABI("LinkToken", *abi)
client.ContractStore.AddBIN("LinkToken", common.FromHex(link_token_interface.LinkTokenMetaData.Bin))

linkToken, err := link_token_interface.NewLinkToken(address, wrappers.MustNewWrappedContractBackend(nil, client))
if err != nil {
return &EthereumLinkToken{}, fmt.Errorf("failed to instantiate LinkToken instance: %w", err)
}

return &EthereumLinkToken{
client: client,
instance: linkToken,
instance: instance,
address: address,
l: l,
}, nil
Expand Down
5 changes: 3 additions & 2 deletions integration-tests/load/ocr/helper.go
Original file line number Diff line number Diff line change
Expand Up @@ -8,13 +8,13 @@ import (

"github.com/ethereum/go-ethereum/common"
"github.com/rs/zerolog"

"github.com/smartcontractkit/seth"

client2 "github.com/smartcontractkit/chainlink-testing-framework/client"
"github.com/smartcontractkit/chainlink/integration-tests/actions"
"github.com/smartcontractkit/chainlink/integration-tests/client"
"github.com/smartcontractkit/chainlink/integration-tests/contracts"
tc "github.com/smartcontractkit/chainlink/integration-tests/testconfig"
)

func SetupCluster(
Expand All @@ -36,12 +36,13 @@ func SetupCluster(
func SetupFeed(
l zerolog.Logger,
seth *seth.Client,
config *tc.TestConfig,
lta common.Address,
msClient *client2.MockserverClient,
bootstrapNode *client.ChainlinkK8sClient,
workerNodes []*client.ChainlinkK8sClient,
) ([]contracts.OffchainAggregator, error) {
ocrInstances, err := actions.DeployOCRv1Contracts(l, seth, 1, lta, contracts.ChainlinkK8sClientToChainlinkNodeWithKeysAndAddress(workerNodes))
ocrInstances, err := actions.SetupOCRv1Contracts(l, seth, config.OCR, lta, contracts.ChainlinkK8sClientToChainlinkNodeWithKeysAndAddress(workerNodes))
if err != nil {
return nil, err
}
Expand Down
Loading
Loading