diff --git a/accounts/abi/abigen/bind.go b/accounts/abi/abigen/bind.go index 42653c4fe1..56e5e214de 100644 --- a/accounts/abi/abigen/bind.go +++ b/accounts/abi/abigen/bind.go @@ -351,8 +351,8 @@ func bindTopicType(kind abi.Type, structs map[string]*tmplStruct) string { } // bindStructType converts a Solidity tuple type to a Go one and records the mapping -// in the given map. -// Notably, this function will resolve and record nested struct recursively. +// in the given map. Notably, this function will resolve and record nested struct +// recursively. func bindStructType(kind abi.Type, structs map[string]*tmplStruct) string { switch kind.T { case abi.TupleTy: @@ -374,7 +374,11 @@ func bindStructType(kind abi.Type, structs map[string]*tmplStruct) string { name := abi.ToCamelCase(kind.TupleRawNames[i]) name = abi.ResolveNameConflict(name, func(s string) bool { return names[s] }) names[name] = true - fields = append(fields, &tmplField{Type: bindStructType(*elem, structs), Name: name, SolKind: *elem}) + fields = append(fields, &tmplField{ + Type: bindStructType(*elem, structs), + Name: name, + SolKind: *elem, + }) } name := kind.TupleRawName if name == "" { @@ -410,7 +414,6 @@ func decapitalise(input string) string { if len(input) == 0 { return input } - goForm := abi.ToCamelCase(input) return strings.ToLower(goForm[:1]) + goForm[1:] } diff --git a/accounts/abi/abigen/bindv2.go b/accounts/abi/abigen/bindv2.go index a494c7f5d2..d730b4fb16 100644 --- a/accounts/abi/abigen/bindv2.go +++ b/accounts/abi/abigen/bindv2.go @@ -31,7 +31,8 @@ import ( "github.com/ethereum/go-ethereum/accounts/abi" ) -// underlyingBindType returns the underlying Go type represented by the given type, panicking if it is not a pointer type. +// underlyingBindType returns the underlying Go type represented by the given +// type, panicking if it is not a pointer type. func underlyingBindType(typ abi.Type) string { goType := typ.GetType() if goType.Kind() != reflect.Pointer { @@ -45,20 +46,23 @@ func isPointerType(typ abi.Type) bool { return typ.GetType().Kind() == reflect.Pointer } -// binder is used during the conversion of an ABI definition into Go bindings (as part of the execution of BindV2) -// in contrast to contractBinder, binder contains binding-generation-state that is shared between contracts: +// binder is used during the conversion of an ABI definition into Go bindings +// (as part of the execution of BindV2). In contrast to contractBinder, binder +// contains binding-generation-state that is shared between contracts: // -// a global struct map of structs emitted by all contracts is tracked and expanded. Structs generated in the bindings -// are not prefixed with the contract name that uses them (to keep the generated bindings less verbose). +// a global struct map of structs emitted by all contracts is tracked and expanded. +// Structs generated in the bindings are not prefixed with the contract name +// that uses them (to keep the generated bindings less verbose). // -// This contrasts to other per-contract -// state (constructor/method/event/error pack/unpack methods) which are guaranteed to be unique because of their association -// with the uniquely-named owning contract (whether prefixed in the generated symbol name, or as a member method on a -// contract struct). +// This contrasts to other per-contract state (constructor/method/event/error, +// pack/unpack methods) which are guaranteed to be unique because of their +// association with the uniquely-named owning contract (whether prefixed in the +// generated symbol name, or as a member method on a contract struct). // -// In addition, binder contains the input alias map. -// In BindV2, a binder is instantiated to produce a set of tmplContractV2 and tmplStruct objects from the provided ABI -// definition. These are used as part of the input to rendering the binding template. +// In addition, binder contains the input alias map. In BindV2, a binder is +// instantiated to produce a set of tmplContractV2 and tmplStruct objects from +// the provided ABI definition. These are used as part of the input to rendering +// the binding template. type binder struct { // contracts is the map of each individual contract requested binding. // It is keyed by the contract name provided in the ABI definition. @@ -69,8 +73,9 @@ type binder struct { // and the solidity type signature of the struct structs map[string]*tmplStruct - // aliases is a map for renaming instances of named events/functions/errors to specified values. - // it is keyed by source symbol name, and values are what the replacement name should be. + // aliases is a map for renaming instances of named events/functions/errors + // to specified values. it is keyed by source symbol name, and values are + // what the replacement name should be. aliases map[string]string } @@ -80,9 +85,10 @@ func (b *binder) BindStructType(typ abi.Type) { bindStructType(typ, b.structs) } -// contractBinder holds state for binding of a single contract. -// It is a type registry for compiling maps of identifiers that will be emitted in generated bindings. -// It also sanitizes/converts information contained in the ABI definition into a data-format that is amenable for rendering the templates. +// contractBinder holds state for binding of a single contract. It is a type +// registry for compiling maps of identifiers that will be emitted in generated +// bindings. It also sanitizes/converts information contained in the ABI +// definition into a data-format that is amenable for rendering the templates. type contractBinder struct { binder *binder @@ -108,10 +114,12 @@ func newContractBinder(binder *binder) *contractBinder { } } -// registerIdentifier applies alias renaming, name normalization (conversion to camel case), and registers the normalized -// name in the specified identifier map. It returns an error if the normalized name already exists in the map. +// registerIdentifier applies alias renaming, name normalization (conversion to +// camel case), and registers the normalized name in the specified identifier map. +// It returns an error if the normalized name already exists in the map. func (cb *contractBinder) registerIdentifier(identifiers map[string]bool, original string) (normalized string, err error) { normalized = abi.ToCamelCase(alias(cb.binder.aliases, original)) + // Name shouldn't start with a digit. It will make the generated code invalid. if len(normalized) > 0 && unicode.IsDigit(rune(normalized[0])) { normalized = fmt.Sprintf("E%s", normalized) @@ -120,7 +128,6 @@ func (cb *contractBinder) registerIdentifier(identifiers map[string]bool, origin return ok }) } - if _, ok := identifiers[normalized]; ok { return "", fmt.Errorf("duplicate symbol '%s'", normalized) } @@ -128,19 +135,18 @@ func (cb *contractBinder) registerIdentifier(identifiers map[string]bool, origin return normalized, nil } -// bindMethod registers a method to be emitted in the bindings. -// The name, inputs and outputs are normalized. If any inputs are -// struct-type their structs are registered to be emitted in the bindings. -// Any methods that return more than one output have their result coalesced -// into a struct. +// bindMethod registers a method to be emitted in the bindings. The name, inputs +// and outputs are normalized. If any inputs are struct-type their structs are +// registered to be emitted in the bindings. Any methods that return more than +// one output have their result coalesced into a struct. func (cb *contractBinder) bindMethod(original abi.Method) error { normalized := original normalizedName, err := cb.registerIdentifier(cb.callIdentifiers, original.Name) if err != nil { return err } - normalized.Name = normalizedName + normalized.Inputs = normalizeArgs(original.Inputs) for _, input := range normalized.Inputs { if hasStruct(input.Type) { @@ -157,17 +163,22 @@ func (cb *contractBinder) bindMethod(original abi.Method) error { } } isStructured := structured(original.Outputs) - // if the call returns multiple values, coallesce them into a struct + + // If the call returns multiple values, coalesced them into a struct if len(normalized.Outputs) > 1 { isStructured = true } - - cb.calls[original.Name] = &tmplMethod{Original: original, Normalized: normalized, Structured: isStructured} + cb.calls[original.Name] = &tmplMethod{ + Original: original, + Normalized: normalized, + Structured: isStructured, + } return nil } -// normalize a set of arguments by stripping underscores, giving a generic name in the case where -// the arg name collides with a reserved Go keyword, and finally converting to camel-case. +// normalize a set of arguments by stripping underscores, giving a generic name +// in the case where the arg name collides with a reserved Go keyword, and finally +// converting to camel-case. func normalizeArgs(args abi.Arguments) abi.Arguments { args = slices.Clone(args) used := make(map[string]bool) @@ -246,8 +257,9 @@ func parseLibraryDeps(unlinkedCode string) (res []string) { return res } -// iterSorted iterates the map in the lexicographic order of the keys calling onItem on each. If the callback returns -// an error, iteration is halted and the error is returned from iterSorted. +// iterSorted iterates the map in the lexicographic order of the keys calling +// onItem on each. If the callback returns an error, iteration is halted and +// the error is returned from iterSorted. func iterSorted[V any](inp map[string]V, onItem func(string, V) error) error { var sortedKeys []string for key := range inp { @@ -293,21 +305,18 @@ func BindV2(types []string, abis []string, bytecodes []string, pkg string, libs if err != nil { return "", err } - err = iterSorted(evmABI.Events, func(_ string, original abi.Event) error { return cb.bindEvent(original) }) if err != nil { return "", err } - err = iterSorted(evmABI.Errors, func(_ string, original abi.Error) error { return cb.bindError(original) }) if err != nil { return "", err } - b.contracts[types[i]] = newTmplContractV2(types[i], abis[i], bytecodes[i], evmABI.Constructor, cb) } @@ -315,7 +324,6 @@ func BindV2(types []string, abis []string, bytecodes []string, pkg string, libs for pattern, name := range libs { invertedLibs[name] = pattern } - data := tmplDataV2{ Package: pkg, Contracts: b.contracts, diff --git a/accounts/abi/bind/old.go b/accounts/abi/bind/old.go index ed62a4ebd4..d5e657be9f 100644 --- a/accounts/abi/bind/old.go +++ b/accounts/abi/bind/old.go @@ -252,6 +252,7 @@ type MetaData struct { func (m *MetaData) GetAbi() (*abi.ABI, error) { m.mu.Lock() defer m.mu.Unlock() + if m.parsedABI != nil { return m.parsedABI, nil } diff --git a/accounts/abi/bind/v2/backend.go b/accounts/abi/bind/v2/backend.go index 2d9a35e5fb..2f5f17b31e 100644 --- a/accounts/abi/bind/v2/backend.go +++ b/accounts/abi/bind/v2/backend.go @@ -44,9 +44,9 @@ var ( // an empty contract behind. ErrNoCodeAfterDeploy = errors.New("no contract code after deployment") - // Returned by WaitDeployed when the receipt for the transaction hash does not contain - // a contract address. This error may indicated that the transaction hash was not a - // CREATE transaction. + // ErrNoAddressInReceipt is returned by WaitDeployed when the receipt for the + // transaction hash does not contain a contract address. This error may indicate + // that the transaction hash was not a CREATE transaction. ErrNoAddressInReceipt = errors.New("no contract address in receipt") ) diff --git a/accounts/abi/bind/v2/base.go b/accounts/abi/bind/v2/base.go index 75b55198eb..ab35e79872 100644 --- a/accounts/abi/bind/v2/base.go +++ b/accounts/abi/bind/v2/base.go @@ -23,11 +23,10 @@ import ( "strings" "sync" - "github.com/ethereum/go-ethereum/event" - "github.com/ethereum/go-ethereum/accounts/abi" "github.com/ethereum/go-ethereum/common" "github.com/ethereum/go-ethereum/core/types" + "github.com/ethereum/go-ethereum/event" ) const basefeeWiggleMultiplier = 2 @@ -91,17 +90,17 @@ type MetaData struct { ABI string // the raw ABI definition (JSON) Deps []*MetaData // library dependencies of the contract - // For bindings that were compiled from combined-json ID is the Solidity library pattern: a 34 character prefix - // of the hex encoding of the keccak256 + // For bindings that were compiled from combined-json ID is the Solidity + // library pattern: a 34 character prefix of the hex encoding of the keccak256 // hash of the fully qualified 'library name', i.e. the path of the source file. // - // For contracts compiled from the ABI definition alone, this is the type name of the contract (as specified - // in the ABI definition or overridden via the --type flag). + // For contracts compiled from the ABI definition alone, this is the type name + // of the contract (as specified in the ABI definition or overridden via the + // --type flag). // - // This is a unique identifier of a contract within a compilation unit. When used as part of a multi-contract - // deployment with library dependencies, the ID is used to link - // contracts during deployment using - // [LinkAndDeploy]. + // This is a unique identifier of a contract within a compilation unit. When + // used as part of a multi-contract deployment with library dependencies, the + // ID is used to link contracts during deployment using [LinkAndDeploy]. ID string mu sync.Mutex @@ -112,6 +111,7 @@ type MetaData struct { func (m *MetaData) ParseABI() (*abi.ABI, error) { m.mu.Lock() defer m.mu.Unlock() + if m.parsedABI != nil { return m.parsedABI, nil } diff --git a/accounts/abi/bind/v2/boundcontractv1.go b/accounts/abi/bind/v2/boundcontractv1.go index c1fd3dd056..f7859c68f5 100644 --- a/accounts/abi/bind/v2/boundcontractv1.go +++ b/accounts/abi/bind/v2/boundcontractv1.go @@ -37,9 +37,10 @@ func NewBoundContractV1(address common.Address, abi abi.ABI, caller ContractCall } // Call invokes the (constant) contract method with params as input values and -// sets the output to result. The result type might be a single field for simple -// returns, a slice of interfaces for anonymous returns and a struct for named -// returns. +// sets the output to result. +// +// The result type might be a single field for simple returns, a slice of interfaces +// for anonymous returns and a struct for named returns. func (c *BoundContractV1) Call(opts *CallOpts, results *[]any, method string, params ...any) error { if results == nil { results = new([]any) @@ -49,23 +50,24 @@ func (c *BoundContractV1) Call(opts *CallOpts, results *[]any, method string, pa if err != nil { return err } - output, err := c.call(opts, input) if err != nil { return err } - if len(*results) == 0 { res, err := c.abi.Unpack(method, output) + if err != nil { + return err + } *results = res - return err + return nil } res := *results return c.abi.UnpackIntoInterface(res[0], method, output) } -// CallRaw executes an eth_call against the contract with the raw calldata as -// input. It returns the call's return data or an error. +// CallRaw executes an eth_call against the contract with the raw call data as +// input. It returns the call's return data or an error. func (c *BoundContractV1) CallRaw(opts *CallOpts, input []byte) ([]byte, error) { return c.call(opts, input) } @@ -143,13 +145,13 @@ func (c *BoundContractV1) Transact(opts *TransactOpts, method string, params ... return c.transact(opts, &c.address, input) } -// RawTransact initiates a transaction with the given raw calldata as the input. -// It's usually used to initiate transactions for invoking **Fallback** function. +// RawTransact initiates a transaction with the given raw call data as the input. func (c *BoundContractV1) RawTransact(opts *TransactOpts, calldata []byte) (*types.Transaction, error) { return c.transact(opts, &c.address, calldata) } -// RawCreationTransact initiates a contract-creation transaction with the given raw calldata as the input. +// RawCreationTransact initiates a contract-creation transaction with the given +// raw call data as the input. func (c *BoundContractV1) RawCreationTransact(opts *TransactOpts, calldata []byte) (*types.Transaction, error) { return c.transact(opts, nil, calldata) } @@ -282,9 +284,8 @@ func (c *BoundContractV1) estimateGasLimit(opts *TransactOpts, contract *common. func (c *BoundContractV1) getNonce(opts *TransactOpts) (uint64, error) { if opts.Nonce == nil { return c.transactor.PendingNonceAt(ensureContext(opts.Context), opts.From) - } else { - return opts.Nonce.Uint64(), nil } + return opts.Nonce.Uint64(), nil } // transact executes an actual transaction invocation, first deriving any missing diff --git a/accounts/abi/bind/v2/dep_tree.go b/accounts/abi/bind/v2/dep_tree.go index dcf981b329..6121103123 100644 --- a/accounts/abi/bind/v2/dep_tree.go +++ b/accounts/abi/bind/v2/dep_tree.go @@ -1,3 +1,19 @@ +// Copyright 2025 The go-ethereum Authors +// This file is part of the go-ethereum library. +// +// The go-ethereum library is free software: you can redistribute it and/or modify +// it under the terms of the GNU Lesser General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// The go-ethereum library is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU Lesser General Public License for more details. +// +// You should have received a copy of the GNU Lesser General Public License +// along with the go-ethereum library. If not, see . + package bind import ( @@ -10,9 +26,9 @@ import ( "github.com/ethereum/go-ethereum/core/types" ) -// DeploymentParams represents parameters needed to deploy a -// set of contracts. It takes an optional override -// list to specify contracts/libraries that have already been deployed on-chain. +// DeploymentParams represents parameters needed to deploy a set of contracts. +// It takes an optional override list to specify contracts/libraries that have +// already been deployed on-chain. type DeploymentParams struct { Contracts []*MetaData @@ -25,7 +41,8 @@ type DeploymentParams struct { Overrides map[string]common.Address } -// validate determines whether the contracts specified in the DeploymentParams instance have provided deployer bytecode. +// validate determines whether the contracts specified in the DeploymentParams +// instance have provided deployer bytecode. func (d *DeploymentParams) validate() error { for _, meta := range d.Contracts { if meta.Bin == "" { @@ -39,19 +56,20 @@ func (d *DeploymentParams) validate() error { // of a set of contracts: the pending deployment transactions, and the addresses // where the contracts will be deployed at. type DeploymentResult struct { - // map of contract MetaData Id to deploy transaction + // Map of contract MetaData Id to deploy transaction Txs map[string]*types.Transaction - // map of contract MetaData Id to deployed contract address - Addrs map[string]common.Address + // Map of contract MetaData Id to deployed contract address + Addresses map[string]common.Address } // DeployFn deploys a contract given a deployer and optional input. It returns // the address of the deployed contract and the deployment transaction, or an error if the deployment failed. type DeployFn func(input, deployer []byte) (common.Address, *types.Transaction, error) -// depTreeDeployer is responsible for taking a dependency, deploying-and-linking its components in the proper -// order. A depTreeDeployer cannot be used after calling LinkAndDeploy other than to retrieve the deployment result. +// depTreeDeployer is responsible for taking a dependency, deploying-and-linking +// its components in the proper order. A depTreeDeployer cannot be used after +// calling LinkAndDeploy other than to retrieve the deployment result. type depTreeDeployer struct { deployedAddrs map[string]common.Address deployerTxs map[string]*types.Transaction @@ -68,7 +86,6 @@ func newDepTreeDeployer(deployParams *DeploymentParams, deployFn DeployFn) *depT if inputs == nil { inputs = make(map[string][]byte) } - return &depTreeDeployer{ deployFn: deployFn, deployedAddrs: deployedAddrs, @@ -77,21 +94,23 @@ func newDepTreeDeployer(deployParams *DeploymentParams, deployFn DeployFn) *depT } } -// linkAndDeploy recursively deploys a contract and its dependencies: starting by linking/deploying its dependencies. -// The deployment result (deploy addresses/txs or an error) is stored in the depTreeDeployer object. +// linkAndDeploy recursively deploys a contract and its dependencies: starting by +// linking/deploying its dependencies. The deployment result (deploy addresses/txs +// or an error) is stored in the depTreeDeployer object. func (d *depTreeDeployer) linkAndDeploy(metadata *MetaData) (common.Address, error) { // Don't deploy already deployed contracts if addr, ok := d.deployedAddrs[metadata.ID]; ok { return addr, nil } - // if this contract/library depends on other libraries deploy them (and their dependencies) first + // If this contract/library depends on other libraries deploy them + // (and their dependencies) first deployerCode := metadata.Bin for _, dep := range metadata.Deps { addr, err := d.linkAndDeploy(dep) if err != nil { return common.Address{}, err } - // link their deployed addresses into the bytecode to produce + // Link their deployed addresses into the bytecode to produce deployerCode = strings.ReplaceAll(deployerCode, "__$"+dep.ID+"$__", strings.ToLower(addr.String()[2:])) } // Finally, deploy the contract. @@ -110,29 +129,30 @@ func (d *depTreeDeployer) linkAndDeploy(metadata *MetaData) (common.Address, err // result returns a result for this deployment, or an error if it failed. func (d *depTreeDeployer) result() *DeploymentResult { - // remove the override addresses from the resulting deployedAddrs + // remove the override addresses from the resulting deployed addresses for pattern := range d.deployedAddrs { if _, ok := d.deployerTxs[pattern]; !ok { delete(d.deployedAddrs, pattern) } } return &DeploymentResult{ - Txs: d.deployerTxs, - Addrs: d.deployedAddrs, + Txs: d.deployerTxs, + Addresses: d.deployedAddrs, } } // LinkAndDeploy deploys a specified set of contracts and their dependent -// libraries. If an error occurs, only contracts which were successfully +// libraries. If an error occurs, only contracts which were successfully // deployed are returned in the result. // -// In the case where multiple contracts share a common dependency: the shared dependency will only be deployed once. -func LinkAndDeploy(deployParams *DeploymentParams, deploy DeployFn) (res *DeploymentResult, err error) { - if err := deployParams.validate(); err != nil { +// In the case where multiple contracts share a common dependency: the shared +// dependency will only be deployed once. +func LinkAndDeploy(params *DeploymentParams, deploy DeployFn) (*DeploymentResult, error) { + if err := params.validate(); err != nil { return nil, err } - deployer := newDepTreeDeployer(deployParams, deploy) - for _, contract := range deployParams.Contracts { + deployer := newDepTreeDeployer(params, deploy) + for _, contract := range params.Contracts { if _, err := deployer.linkAndDeploy(contract); err != nil { return deployer.result(), err } diff --git a/accounts/abi/bind/v2/dep_tree_test.go b/accounts/abi/bind/v2/dep_tree_test.go index 827ba25518..e686e3fec4 100644 --- a/accounts/abi/bind/v2/dep_tree_test.go +++ b/accounts/abi/bind/v2/dep_tree_test.go @@ -19,7 +19,6 @@ package bind import ( "fmt" "regexp" - "sync" "testing" "github.com/ethereum/go-ethereum/common" @@ -39,19 +38,18 @@ type linkTestCase struct { func copyMetaData(m *MetaData) *MetaData { m.mu.Lock() defer m.mu.Unlock() + var deps []*MetaData if len(m.Deps) > 0 { for _, dep := range m.Deps { deps = append(deps, copyMetaData(dep)) } } - return &MetaData{ Bin: m.Bin, ABI: m.ABI, Deps: deps, ID: m.ID, - mu: sync.Mutex{}, parsedABI: m.parsedABI, } } @@ -137,10 +135,11 @@ func linkDeps(deps map[string]*MetaData) []*MetaData { return rootMetadatas } -// internalLinkDeps is the internal recursing logic of linkDeps: It links the contract referred to by MetaData -// given the depMap (map of solidity link pattern to contract metadata object), deleting contract entries from the roots -// map if they were referenced as dependencies. It returns a new MetaData object which is the linked version of metadata -// parameter. +// internalLinkDeps is the internal recursing logic of linkDeps: +// It links the contract referred to by MetaData given the depMap (map of solidity +// link pattern to contract metadata object), deleting contract entries from the +// roots map if they were referenced as dependencies. It returns a new MetaData +// object which is the linked version of metadata parameter. func internalLinkDeps(metadata *MetaData, depMap map[string]*MetaData, roots *map[string]struct{}) *MetaData { linked := copyMetaData(metadata) depPatterns := parseLibraryDeps(metadata.Bin) @@ -153,13 +152,13 @@ func internalLinkDeps(metadata *MetaData, depMap map[string]*MetaData, roots *ma } func testLinkCase(tcInput linkTestCaseInput) error { - testAddr := crypto.PubkeyToAddress(testKey.PublicKey) - var testAddrNonce uint64 - overridesAddrs := make(map[common.Address]struct{}) - + var ( + testAddr = crypto.PubkeyToAddress(testKey.PublicKey) + overridesAddrs = make(map[common.Address]struct{}) + overrideAddrs = make(map[rune]common.Address) + ) // generate deterministic addresses for the override set. rand.Seed(42) - overrideAddrs := make(map[rune]common.Address) for contract := range tcInput.overrides { var addr common.Address rand.Read(addr[:]) @@ -177,6 +176,7 @@ func testLinkCase(tcInput linkTestCaseInput) error { } } + var testAddrNonce uint64 mockDeploy := func(input []byte, deployer []byte) (common.Address, *types.Transaction, error) { contractAddr := crypto.CreateAddress(testAddr, testAddrNonce) testAddrNonce++ @@ -225,11 +225,11 @@ func testLinkCase(tcInput linkTestCaseInput) error { } if len(res.Txs) != len(tcInput.expectDeployed) { - return fmt.Errorf("got %d deployed contracts. expected %d.\n", len(res.Addrs), len(tcInput.expectDeployed)) + return fmt.Errorf("got %d deployed contracts. expected %d.\n", len(res.Addresses), len(tcInput.expectDeployed)) } for contract := range tcInput.expectDeployed { pattern := crypto.Keccak256Hash([]byte(string(contract))).String()[2:36] - if _, ok := res.Addrs[pattern]; !ok { + if _, ok := res.Addresses[pattern]; !ok { return fmt.Errorf("expected contract %s was not deployed\n", string(contract)) } } diff --git a/accounts/abi/bind/v2/lib.go b/accounts/abi/bind/v2/lib.go index 881b8b3b33..919e277255 100644 --- a/accounts/abi/bind/v2/lib.go +++ b/accounts/abi/bind/v2/lib.go @@ -80,7 +80,8 @@ func WatchEvents[Ev ContractEvent](c BoundContract, opts *WatchOpts, unpack func }), nil } -// EventIterator is returned from FilterLogs and is used to iterate over the raw logs and unpacked data for events. +// EventIterator is returned from FilterLogs and is used to iterate over the raw +// logs and unpacked data for events. type EventIterator[T any] struct { event *T // event containing the contract specifics and raw log @@ -182,7 +183,7 @@ func Transact(c BoundContract, opt *TransactOpts, packedInput []byte) (*types.Tr } // DeployContract deploys a contract onto the Ethereum blockchain and binds the -// deployment address with a Go wrapper. It expects its parameters to be abi-encoded +// deployment address with a Go wrapper. It expects its parameters to be abi-encoded // bytes. func DeployContract(opts *TransactOpts, bytecode []byte, backend ContractBackend, packedParams []byte) (common.Address, *types.Transaction, error) { c := NewBoundContractV1(common.Address{}, abi.ABI{}, backend, backend, backend) @@ -190,11 +191,11 @@ func DeployContract(opts *TransactOpts, bytecode []byte, backend ContractBackend if err != nil { return common.Address{}, nil, err } - address := crypto.CreateAddress(opts.From, tx.Nonce()) - return address, tx, nil + return crypto.CreateAddress(opts.From, tx.Nonce()), tx, nil } -// DefaultDeployer returns a DeployFn that signs and submits creation transactions using the given signer. +// DefaultDeployer returns a DeployFn that signs and submits creation transactions +// using the given signer. func DefaultDeployer(ctx context.Context, from common.Address, backend ContractBackend, signer SignerFn) DeployFn { opts := &TransactOpts{ From: from, diff --git a/accounts/abi/bind/v2/lib_test.go b/accounts/abi/bind/v2/lib_test.go index 51d9dd811a..d89e8b5387 100644 --- a/accounts/abi/bind/v2/lib_test.go +++ b/accounts/abi/bind/v2/lib_test.go @@ -18,13 +18,10 @@ package bind_test import ( "context" - "encoding/json" - "io" "math/big" "testing" "time" - "github.com/ethereum/go-ethereum/accounts/abi" "github.com/ethereum/go-ethereum/accounts/abi/bind/backends" "github.com/ethereum/go-ethereum/accounts/abi/bind/v2" "github.com/ethereum/go-ethereum/accounts/abi/bind/v2/internal/contracts/events" @@ -43,17 +40,6 @@ import ( var testKey, _ = crypto.HexToECDSA("b71c71a67e1177ad4e901695e1b4b9ee17ae16c6668d313eac2f96dbcda3f291") var testAddr = crypto.PubkeyToAddress(testKey.PublicKey) -// JSON returns a parsed ABI interface and error if it failed. -func JSON(reader io.Reader) (abi.ABI, error) { - dec := json.NewDecoder(reader) - - var instance abi.ABI - if err := dec.Decode(&instance); err != nil { - return abi.ABI{}, err - } - return instance, nil -} - func testSetup() (*backends.SimulatedBackend, error) { backend := simulated.NewBackend( types.GenesisAlloc{ @@ -65,7 +51,7 @@ func testSetup() (*backends.SimulatedBackend, error) { ) // we should just be able to use the backend directly, instead of using - // this deprecated interface. However, the simulated backend no longer + // this deprecated interface. However, the simulated backend no longer // implements backends.SimulatedBackend... bindBackend := backends.SimulatedBackend{ Backend: backend, @@ -87,7 +73,6 @@ func makeTestDeployer(backend bind.ContractBackend) func(input, deployer []byte) } return signedTx, nil } - return bind.DefaultDeployer(context.Background(), testAddr, backend, sign) } @@ -112,8 +97,8 @@ func TestDeploymentLibraries(t *testing.T) { } bindBackend.Commit() - if len(res.Addrs) != 5 { - t.Fatalf("deployment should have generated 5 addresses. got %d", len(res.Addrs)) + if len(res.Addresses) != 5 { + t.Fatalf("deployment should have generated 5 addresses. got %d", len(res.Addresses)) } for _, tx := range res.Txs { _, err = bind.WaitDeployed(context.Background(), bindBackend, tx.Hash()) @@ -123,7 +108,7 @@ func TestDeploymentLibraries(t *testing.T) { } doInput := c.PackDo(big.NewInt(1)) - contractAddr := res.Addrs[nested_libraries.C1MetaData.ID] + contractAddr := res.Addresses[nested_libraries.C1MetaData.ID] callOpts := &bind.CallOpts{From: common.Address{}, Context: context.Background()} instance := c.Instance(bindBackend, contractAddr) internalCallCount, err := bind.Call(instance, callOpts, doInput, c.UnpackDo) @@ -154,8 +139,8 @@ func TestDeploymentWithOverrides(t *testing.T) { } bindBackend.Commit() - if len(res.Addrs) != 4 { - t.Fatalf("deployment should have generated 4 addresses. got %d", len(res.Addrs)) + if len(res.Addresses) != 4 { + t.Fatalf("deployment should have generated 4 addresses. got %d", len(res.Addresses)) } for _, tx := range res.Txs { _, err = bind.WaitDeployed(context.Background(), bindBackend, tx.Hash()) @@ -166,7 +151,7 @@ func TestDeploymentWithOverrides(t *testing.T) { c := nested_libraries.NewC1() constructorInput := c.PackConstructor(big.NewInt(42), big.NewInt(1)) - overrides := res.Addrs + overrides := res.Addresses // deploy the contract deploymentParams = &bind.DeploymentParams{ @@ -180,8 +165,8 @@ func TestDeploymentWithOverrides(t *testing.T) { } bindBackend.Commit() - if len(res.Addrs) != 1 { - t.Fatalf("deployment should have generated 1 address. got %d", len(res.Addrs)) + if len(res.Addresses) != 1 { + t.Fatalf("deployment should have generated 1 address. got %d", len(res.Addresses)) } for _, tx := range res.Txs { _, err = bind.WaitDeployed(context.Background(), bindBackend, tx.Hash()) @@ -192,7 +177,7 @@ func TestDeploymentWithOverrides(t *testing.T) { // call the deployed contract and make sure it returns the correct result doInput := c.PackDo(big.NewInt(1)) - instance := c.Instance(bindBackend, res.Addrs[nested_libraries.C1MetaData.ID]) + instance := c.Instance(bindBackend, res.Addresses[nested_libraries.C1MetaData.ID]) callOpts := new(bind.CallOpts) internalCallCount, err := bind.Call(instance, callOpts, doInput, c.UnpackDo) if err != nil { @@ -231,8 +216,9 @@ func TestEvents(t *testing.T) { if err != nil { t.Fatalf("error setting up testing env: %v", err) } - - deploymentParams := &bind.DeploymentParams{Contracts: []*bind.MetaData{&events.CMetaData}} + deploymentParams := &bind.DeploymentParams{ + Contracts: []*bind.MetaData{&events.CMetaData}, + } res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployer(backend)) if err != nil { t.Fatalf("error deploying contract for testing: %v", err) @@ -244,7 +230,7 @@ func TestEvents(t *testing.T) { } c := events.NewC() - instance := c.Instance(backend, res.Addrs[events.CMetaData.ID]) + instance := c.Instance(backend, res.Addresses[events.CMetaData.ID]) newCBasic1Ch := make(chan *events.CBasic1) newCBasic2Ch := make(chan *events.CBasic2) @@ -330,8 +316,9 @@ func TestErrors(t *testing.T) { if err != nil { t.Fatalf("error setting up testing env: %v", err) } - - deploymentParams := &bind.DeploymentParams{Contracts: []*bind.MetaData{&solc_errors.CMetaData}} + deploymentParams := &bind.DeploymentParams{ + Contracts: []*bind.MetaData{&solc_errors.CMetaData}, + } res, err := bind.LinkAndDeploy(deploymentParams, makeTestDeployer(backend)) if err != nil { t.Fatalf("error deploying contract for testing: %v", err) @@ -343,9 +330,9 @@ func TestErrors(t *testing.T) { } c := solc_errors.NewC() - instance := c.Instance(backend, res.Addrs[solc_errors.CMetaData.ID]) + instance := c.Instance(backend, res.Addresses[solc_errors.CMetaData.ID]) packedInput := c.PackFoo() - opts := &bind.CallOpts{From: res.Addrs[solc_errors.CMetaData.ID]} + opts := &bind.CallOpts{From: res.Addresses[solc_errors.CMetaData.ID]} _, err = bind.Call[struct{}](instance, opts, packedInput, nil) if err == nil { t.Fatalf("expected call to fail")