|
|
@@ -22,6 +22,7 @@ import "github.com/ethereum/go-ethereum/accounts/abi"
|
|
|
type tmplData struct {
|
|
|
Package string // Name of the package to place the generated file in
|
|
|
Contracts map[string]*tmplContract // List of contracts to generate into this file
|
|
|
+ Libraries map[string]string // Map the bytecode's link pattern to the library name
|
|
|
}
|
|
|
|
|
|
// tmplContract contains the data needed to generate an individual contract binding.
|
|
|
@@ -34,7 +35,9 @@ type tmplContract struct {
|
|
|
Calls map[string]*tmplMethod // Contract calls that only read state data
|
|
|
Transacts map[string]*tmplMethod // Contract calls that write state data
|
|
|
Events map[string]*tmplEvent // Contract events accessors
|
|
|
+ Libraries map[string]string // Same as tmplData, but filtered to only keep what the contract needs
|
|
|
Structs map[string]*tmplStruct // Contract struct type definitions
|
|
|
+ Library bool
|
|
|
}
|
|
|
|
|
|
// tmplMethod is a wrapper around an abi.Method that contains a few preprocessed
|
|
|
@@ -113,15 +116,14 @@ var (
|
|
|
{{if $contract.FuncSigs}}
|
|
|
// {{.Type}}FuncSigs maps the 4-byte function signature to its string representation.
|
|
|
var {{.Type}}FuncSigs = map[string]string{
|
|
|
- {{range $strsig, $binsig := .FuncSigs}}
|
|
|
- "{{$binsig}}": "{{$strsig}}",
|
|
|
+ {{range $strsig, $binsig := .FuncSigs}}"{{$binsig}}": "{{$strsig}}",
|
|
|
{{end}}
|
|
|
}
|
|
|
{{end}}
|
|
|
|
|
|
{{if .InputBin}}
|
|
|
// {{.Type}}Bin is the compiled bytecode used for deploying new contracts.
|
|
|
- const {{.Type}}Bin = ` + "`" + `{{.InputBin}}` + "`" + `
|
|
|
+ var {{.Type}}Bin = "0x{{.InputBin}}"
|
|
|
|
|
|
// Deploy{{.Type}} deploys a new Ethereum contract, binding an instance of {{.Type}} to it.
|
|
|
func Deploy{{.Type}}(auth *bind.TransactOpts, backend bind.ContractBackend {{range .Constructor.Inputs}}, {{.Name}} {{bindtype .Type $structs}}{{end}}) (common.Address, *types.Transaction, *{{.Type}}, error) {
|
|
|
@@ -129,6 +131,10 @@ var (
|
|
|
if err != nil {
|
|
|
return common.Address{}, nil, nil, err
|
|
|
}
|
|
|
+ {{range $pattern, $name := .Libraries}}
|
|
|
+ {{decapitalise $name}}Addr, _, _, _ := Deploy{{capitalise $name}}(auth, backend)
|
|
|
+ {{$contract.Type}}Bin = strings.Replace({{$contract.Type}}Bin, "__${{$pattern}}$__", {{decapitalise $name}}Addr.String()[2:], -1)
|
|
|
+ {{end}}
|
|
|
address, tx, contract, err := bind.DeployContract(auth, parsed, common.FromHex({{.Type}}Bin), backend {{range .Constructor.Inputs}}, {{.Name}}{{end}})
|
|
|
if err != nil {
|
|
|
return common.Address{}, nil, nil, err
|
|
|
@@ -503,7 +509,7 @@ import java.util.*;
|
|
|
|
|
|
{{range $contract := .Contracts}}
|
|
|
{{$structs := $contract.Structs}}
|
|
|
-public class {{.Type}} {
|
|
|
+{{if not .Library}}public {{end}}class {{.Type}} {
|
|
|
// ABI is the input ABI used to generate the binding from.
|
|
|
public final static String ABI = "{{.InputABI}}";
|
|
|
{{if $contract.FuncSigs}}
|
|
|
@@ -511,8 +517,7 @@ public class {{.Type}} {
|
|
|
public final static Map<String, String> {{.Type}}FuncSigs;
|
|
|
static {
|
|
|
Hashtable<String, String> temp = new Hashtable<String, String>();
|
|
|
- {{range $strsig, $binsig := .FuncSigs}}
|
|
|
- temp.put("{{$binsig}}", "{{$strsig}}");
|
|
|
+ {{range $strsig, $binsig := .FuncSigs}}temp.put("{{$binsig}}", "{{$strsig}}");
|
|
|
{{end}}
|
|
|
{{.Type}}FuncSigs = Collections.unmodifiableMap(temp);
|
|
|
}
|
|
|
@@ -524,9 +529,18 @@ public class {{.Type}} {
|
|
|
// deploy deploys a new Ethereum contract, binding an instance of {{.Type}} to it.
|
|
|
public static {{.Type}} deploy(TransactOpts auth, EthereumClient client{{range .Constructor.Inputs}}, {{bindtype .Type $structs}} {{.Name}}{{end}}) throws Exception {
|
|
|
Interfaces args = Geth.newInterfaces({{(len .Constructor.Inputs)}});
|
|
|
+ String bytecode = BYTECODE;
|
|
|
+ {{if .Libraries}}
|
|
|
+
|
|
|
+ // "link" contract to dependent libraries by deploying them first.
|
|
|
+ {{range $pattern, $name := .Libraries}}
|
|
|
+ {{capitalise $name}} {{decapitalise $name}}Inst = {{capitalise $name}}.deploy(auth, client);
|
|
|
+ bytecode = bytecode.replace("__${{$pattern}}$__", {{decapitalise $name}}Inst.Address.getHex().substring(2));
|
|
|
+ {{end}}
|
|
|
+ {{end}}
|
|
|
{{range $index, $element := .Constructor.Inputs}}Interface arg{{$index}} = Geth.newInterface();arg{{$index}}.set{{namedtype (bindtype .Type $structs) .Type}}({{.Name}});args.set({{$index}},arg{{$index}});
|
|
|
{{end}}
|
|
|
- return new {{.Type}}(Geth.deployContract(auth, ABI, Geth.decodeFromHex(BYTECODE), client, args));
|
|
|
+ return new {{.Type}}(Geth.deployContract(auth, ABI, Geth.decodeFromHex(bytecode), client, args));
|
|
|
}
|
|
|
|
|
|
// Internal constructor used by contract deployment.
|