mirror of
https://github.com/ethereum/go-ethereum.git
synced 2026-02-26 07:37:20 +00:00
account/abi/bind/v2: fix TestDeploymentWithOverrides (#32212)
The root cause of the flaky test was a nonce conflict caused by async contract deployments. This solution defines a custom deployer with automatic nonce management.
This commit is contained in:
parent
532a1c2ca4
commit
66df1f26b8
2 changed files with 35 additions and 2 deletions
|
|
@ -28,6 +28,7 @@ package bind
|
|||
|
||||
import (
|
||||
"errors"
|
||||
"math/big"
|
||||
|
||||
"github.com/ethereum/go-ethereum"
|
||||
"github.com/ethereum/go-ethereum/accounts/abi"
|
||||
|
|
@ -241,3 +242,27 @@ func DefaultDeployer(opts *TransactOpts, backend ContractBackend) DeployFn {
|
|||
return addr, tx, nil
|
||||
}
|
||||
}
|
||||
|
||||
// DeployerWithNonceAssignment is basically identical to DefaultDeployer,
|
||||
// but it additionally tracks the nonce to enable automatic assignment.
|
||||
//
|
||||
// This is especially useful when deploying multiple contracts
|
||||
// from the same address — whether they are independent contracts
|
||||
// or part of a dependency chain that must be deployed in order.
|
||||
func DeployerWithNonceAssignment(opts *TransactOpts, backend ContractBackend) DeployFn {
|
||||
var pendingNonce int64
|
||||
if opts.Nonce != nil {
|
||||
pendingNonce = opts.Nonce.Int64()
|
||||
}
|
||||
return func(input []byte, deployer []byte) (common.Address, *types.Transaction, error) {
|
||||
if pendingNonce != 0 {
|
||||
opts.Nonce = big.NewInt(pendingNonce)
|
||||
}
|
||||
addr, tx, err := DeployContract(opts, deployer, backend, input)
|
||||
if err != nil {
|
||||
return common.Address{}, nil, err
|
||||
}
|
||||
pendingNonce = int64(tx.Nonce() + 1)
|
||||
return addr, tx, nil
|
||||
}
|
||||
}
|
||||
|
|
|
|||
|
|
@ -65,6 +65,14 @@ func makeTestDeployer(backend simulated.Client) func(input, deployer []byte) (co
|
|||
return bind.DefaultDeployer(bind.NewKeyedTransactor(testKey, chainId), backend)
|
||||
}
|
||||
|
||||
// makeTestDeployerWithNonceAssignment is similar to makeTestDeployer,
|
||||
// but it returns a deployer that automatically tracks nonce,
|
||||
// enabling the deployment of multiple contracts from the same account.
|
||||
func makeTestDeployerWithNonceAssignment(backend simulated.Client) func(input, deployer []byte) (common.Address, *types.Transaction, error) {
|
||||
chainId, _ := backend.ChainID(context.Background())
|
||||
return bind.DeployerWithNonceAssignment(bind.NewKeyedTransactor(testKey, chainId), backend)
|
||||
}
|
||||
|
||||
// test that deploying a contract with library dependencies works,
|
||||
// verifying by calling method on the deployed contract.
|
||||
func TestDeploymentLibraries(t *testing.T) {
|
||||
|
|
@ -80,7 +88,7 @@ func TestDeploymentLibraries(t *testing.T) {
|
|||
Contracts: []*bind.MetaData{&nested_libraries.C1MetaData},
|
||||
Inputs: map[string][]byte{nested_libraries.C1MetaData.ID: constructorInput},
|
||||
}
|
||||
res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployer(bindBackend.Client))
|
||||
res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployerWithNonceAssignment(bindBackend.Client))
|
||||
if err != nil {
|
||||
t.Fatalf("err: %+v\n", err)
|
||||
}
|
||||
|
|
@ -122,7 +130,7 @@ func TestDeploymentWithOverrides(t *testing.T) {
|
|||
deploymentParams := &bind.DeploymentParams{
|
||||
Contracts: nested_libraries.C1MetaData.Deps,
|
||||
}
|
||||
res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployer(bindBackend))
|
||||
res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployerWithNonceAssignment(bindBackend))
|
||||
if err != nil {
|
||||
t.Fatalf("err: %+v\n", err)
|
||||
}
|
||||
|
|
|
|||
Loading…
Reference in a new issue