forked from TrueCloudLab/neoneo-go
rpcbinding: handle more complex non-structured types
This commit is contained in:
parent
ce67e6795e
commit
c058ab5604
4 changed files with 285 additions and 45 deletions
2
cli/smartcontract/testdata/types/config.yml
vendored
2
cli/smartcontract/testdata/types/config.yml
vendored
|
@ -1,3 +1,3 @@
|
||||||
name: "Types"
|
name: "Types"
|
||||||
sourceurl: https://github.com/nspcc-dev/neo-go/
|
sourceurl: https://github.com/nspcc-dev/neo-go/
|
||||||
safemethods: ["bool", "int", "bytes", "string", "hash160", "hash256", "publicKey", "signature", "bools", "ints", "bytess", "strings", "hash160s", "hash256s", "publicKeys", "signatures"]
|
safemethods: ["bool", "int", "bytes", "string", "hash160", "hash256", "publicKey", "signature", "bools", "ints", "bytess", "strings", "hash160s", "hash256s", "publicKeys", "signatures", "aAAStrings", "maps", "crazyMaps"]
|
||||||
|
|
199
cli/smartcontract/testdata/types/rpcbindings.out
vendored
199
cli/smartcontract/testdata/types/rpcbindings.out
vendored
|
@ -2,11 +2,15 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"errors"
|
||||||
|
"fmt"
|
||||||
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
|
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
|
||||||
"github.com/nspcc-dev/neo-go/pkg/neorpc/result"
|
"github.com/nspcc-dev/neo-go/pkg/neorpc/result"
|
||||||
"github.com/nspcc-dev/neo-go/pkg/rpcclient/unwrap"
|
"github.com/nspcc-dev/neo-go/pkg/rpcclient/unwrap"
|
||||||
"github.com/nspcc-dev/neo-go/pkg/util"
|
"github.com/nspcc-dev/neo-go/pkg/util"
|
||||||
|
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
|
||||||
"math/big"
|
"math/big"
|
||||||
|
"unicode/utf8"
|
||||||
)
|
)
|
||||||
|
|
||||||
// Hash contains contract hash.
|
// Hash contains contract hash.
|
||||||
|
@ -28,6 +32,64 @@ func NewReader(invoker Invoker) *ContractReader {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
// AAAStrings invokes `aAAStrings` method of contract.
|
||||||
|
func (c *ContractReader) AAAStrings(s [][][]string) ([][][]string, error) {
|
||||||
|
return func (item stackitem.Item, err error) ([][][]string, error) {
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return func (item stackitem.Item) ([][][]string, error) {
|
||||||
|
arr, ok := item.Value().([]stackitem.Item)
|
||||||
|
if !ok {
|
||||||
|
return nil, errors.New("not an array")
|
||||||
|
}
|
||||||
|
res := make([][][]string, len(arr))
|
||||||
|
for i := range res {
|
||||||
|
res[i], err = func (item stackitem.Item) ([][]string, error) {
|
||||||
|
arr, ok := item.Value().([]stackitem.Item)
|
||||||
|
if !ok {
|
||||||
|
return nil, errors.New("not an array")
|
||||||
|
}
|
||||||
|
res := make([][]string, len(arr))
|
||||||
|
for i := range res {
|
||||||
|
res[i], err = func (item stackitem.Item) ([]string, error) {
|
||||||
|
arr, ok := item.Value().([]stackitem.Item)
|
||||||
|
if !ok {
|
||||||
|
return nil, errors.New("not an array")
|
||||||
|
}
|
||||||
|
res := make([]string, len(arr))
|
||||||
|
for i := range res {
|
||||||
|
res[i], err = func (item stackitem.Item) (string, error) {
|
||||||
|
b, err := item.TryBytes()
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if !utf8.Valid(b) {
|
||||||
|
return "", errors.New("not a UTF-8 string")
|
||||||
|
}
|
||||||
|
return string(b), nil
|
||||||
|
} (arr[i])
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (arr[i])
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (arr[i])
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (item)
|
||||||
|
} (unwrap.Item(c.invoker.Call(Hash, "aAAStrings", s)))
|
||||||
|
}
|
||||||
|
|
||||||
// Bool invokes `bool` method of contract.
|
// Bool invokes `bool` method of contract.
|
||||||
func (c *ContractReader) Bool(b bool) (bool, error) {
|
func (c *ContractReader) Bool(b bool) (bool, error) {
|
||||||
return unwrap.Bool(c.invoker.Call(Hash, "bool", b))
|
return unwrap.Bool(c.invoker.Call(Hash, "bool", b))
|
||||||
|
@ -48,6 +110,97 @@ func (c *ContractReader) Bytess(b [][]byte) ([][]byte, error) {
|
||||||
return unwrap.ArrayOfBytes(c.invoker.Call(Hash, "bytess", b))
|
return unwrap.ArrayOfBytes(c.invoker.Call(Hash, "bytess", b))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// CrazyMaps invokes `crazyMaps` method of contract.
|
||||||
|
func (c *ContractReader) CrazyMaps(m map[*big.Int][]map[string][]util.Uint160) (map[*big.Int][]map[string][]util.Uint160, error) {
|
||||||
|
return func (item stackitem.Item, err error) (map[*big.Int][]map[string][]util.Uint160, error) {
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return func (item stackitem.Item) (map[*big.Int][]map[string][]util.Uint160, error) {
|
||||||
|
m, ok := item.Value().([]stackitem.MapElement)
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("%s is not a map", item.Type().String())
|
||||||
|
}
|
||||||
|
res := make(map[*big.Int][]map[string][]util.Uint160)
|
||||||
|
for i := range m {
|
||||||
|
k, err := m[i].Key.TryInteger()
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
v, err := func (item stackitem.Item) ([]map[string][]util.Uint160, error) {
|
||||||
|
arr, ok := item.Value().([]stackitem.Item)
|
||||||
|
if !ok {
|
||||||
|
return nil, errors.New("not an array")
|
||||||
|
}
|
||||||
|
res := make([]map[string][]util.Uint160, len(arr))
|
||||||
|
for i := range res {
|
||||||
|
res[i], err = func (item stackitem.Item) (map[string][]util.Uint160, error) {
|
||||||
|
m, ok := item.Value().([]stackitem.MapElement)
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("%s is not a map", item.Type().String())
|
||||||
|
}
|
||||||
|
res := make(map[string][]util.Uint160)
|
||||||
|
for i := range m {
|
||||||
|
k, err := func (item stackitem.Item) (string, error) {
|
||||||
|
b, err := item.TryBytes()
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if !utf8.Valid(b) {
|
||||||
|
return "", errors.New("not a UTF-8 string")
|
||||||
|
}
|
||||||
|
return string(b), nil
|
||||||
|
} (m[i].Key)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
v, err := func (item stackitem.Item) ([]util.Uint160, error) {
|
||||||
|
arr, ok := item.Value().([]stackitem.Item)
|
||||||
|
if !ok {
|
||||||
|
return nil, errors.New("not an array")
|
||||||
|
}
|
||||||
|
res := make([]util.Uint160, len(arr))
|
||||||
|
for i := range res {
|
||||||
|
res[i], err = func (item stackitem.Item) (util.Uint160, error) {
|
||||||
|
b, err := item.TryBytes()
|
||||||
|
if err != nil {
|
||||||
|
return util.Uint160{}, err
|
||||||
|
}
|
||||||
|
u, err := util.Uint160DecodeBytesBE(b)
|
||||||
|
if err != nil {
|
||||||
|
return util.Uint160{}, err
|
||||||
|
}
|
||||||
|
return u, nil
|
||||||
|
} (arr[i])
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (m[i].Value)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
res[k] = v
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (arr[i])
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (m[i].Value)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
res[k] = v
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (item)
|
||||||
|
} (unwrap.Item(c.invoker.Call(Hash, "crazyMaps", m)))
|
||||||
|
}
|
||||||
|
|
||||||
// Hash160 invokes `hash160` method of contract.
|
// Hash160 invokes `hash160` method of contract.
|
||||||
func (c *ContractReader) Hash160(h util.Uint160) (util.Uint160, error) {
|
func (c *ContractReader) Hash160(h util.Uint160) (util.Uint160, error) {
|
||||||
return unwrap.Uint160(c.invoker.Call(Hash, "hash160", h))
|
return unwrap.Uint160(c.invoker.Call(Hash, "hash160", h))
|
||||||
|
@ -78,6 +231,52 @@ func (c *ContractReader) Ints(i []*big.Int) ([]*big.Int, error) {
|
||||||
return unwrap.ArrayOfBigInts(c.invoker.Call(Hash, "ints", i))
|
return unwrap.ArrayOfBigInts(c.invoker.Call(Hash, "ints", i))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// Maps invokes `maps` method of contract.
|
||||||
|
func (c *ContractReader) Maps(m map[string]string) (map[string]string, error) {
|
||||||
|
return func (item stackitem.Item, err error) (map[string]string, error) {
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
return func (item stackitem.Item) (map[string]string, error) {
|
||||||
|
m, ok := item.Value().([]stackitem.MapElement)
|
||||||
|
if !ok {
|
||||||
|
return nil, fmt.Errorf("%s is not a map", item.Type().String())
|
||||||
|
}
|
||||||
|
res := make(map[string]string)
|
||||||
|
for i := range m {
|
||||||
|
k, err := func (item stackitem.Item) (string, error) {
|
||||||
|
b, err := item.TryBytes()
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if !utf8.Valid(b) {
|
||||||
|
return "", errors.New("not a UTF-8 string")
|
||||||
|
}
|
||||||
|
return string(b), nil
|
||||||
|
} (m[i].Key)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
v, err := func (item stackitem.Item) (string, error) {
|
||||||
|
b, err := item.TryBytes()
|
||||||
|
if err != nil {
|
||||||
|
return "", err
|
||||||
|
}
|
||||||
|
if !utf8.Valid(b) {
|
||||||
|
return "", errors.New("not a UTF-8 string")
|
||||||
|
}
|
||||||
|
return string(b), nil
|
||||||
|
} (m[i].Value)
|
||||||
|
if err != nil {
|
||||||
|
return nil, err
|
||||||
|
}
|
||||||
|
res[k] = v
|
||||||
|
}
|
||||||
|
return res, nil
|
||||||
|
} (item)
|
||||||
|
} (unwrap.Item(c.invoker.Call(Hash, "maps", m)))
|
||||||
|
}
|
||||||
|
|
||||||
// PublicKey invokes `publicKey` method of contract.
|
// PublicKey invokes `publicKey` method of contract.
|
||||||
func (c *ContractReader) PublicKey(k *keys.PublicKey) (*keys.PublicKey, error) {
|
func (c *ContractReader) PublicKey(k *keys.PublicKey) (*keys.PublicKey, error) {
|
||||||
return unwrap.PublicKey(c.invoker.Call(Hash, "publicKey", k))
|
return unwrap.PublicKey(c.invoker.Call(Hash, "publicKey", k))
|
||||||
|
|
12
cli/smartcontract/testdata/types/types.go
vendored
12
cli/smartcontract/testdata/types/types.go
vendored
|
@ -67,3 +67,15 @@ func PublicKeys(k []interop.PublicKey) []interop.PublicKey {
|
||||||
func Signatures(s []interop.Signature) []interop.Signature {
|
func Signatures(s []interop.Signature) []interop.Signature {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func AAAStrings(s [][][]string) [][][]string {
|
||||||
|
return s
|
||||||
|
}
|
||||||
|
|
||||||
|
func Maps(m map[string]string) map[string]string {
|
||||||
|
return m
|
||||||
|
}
|
||||||
|
|
||||||
|
func CrazyMaps(m map[int][]map[string][]interop.Hash160) map[int][]map[string][]interop.Hash160 {
|
||||||
|
return m
|
||||||
|
}
|
||||||
|
|
|
@ -19,18 +19,20 @@ func (c *ContractReader) {{.Name}}({{range $index, $arg := .Arguments -}}
|
||||||
{{- if ne $index 0}}, {{end}}
|
{{- if ne $index 0}}, {{end}}
|
||||||
{{- .Name}} {{.Type}}
|
{{- .Name}} {{.Type}}
|
||||||
{{- end}}) {{if .ReturnType }}({{ .ReturnType }}, error) {
|
{{- end}}) {{if .ReturnType }}({{ .ReturnType }}, error) {
|
||||||
return {{if .CallFlag -}}
|
return {{if and (not .ItemTo) (eq .Unwrapper "Item")}}func (item stackitem.Item, err error) ({{ .ReturnType }}, error) {
|
||||||
unwrap.{{.CallFlag}}(c.invoker.Call(Hash, "{{ .NameABI }}"{{/* CallFlag field is used for function name */}}
|
if err != nil {
|
||||||
{{- else -}}
|
return nil, err
|
||||||
itemTo{{ cutPointer .ReturnType }}(unwrap.Item(c.invoker.Call(Hash, "{{ .NameABI }}"{{/* CallFlag field is used for function name */}}
|
}
|
||||||
{{- end -}}
|
return {{etTypeConverter .ExtendedReturn "item"}}
|
||||||
{{- range $arg := .Arguments -}}, {{.Name}}{{end}})){{if not .CallFlag}}){{end}}
|
} ( {{- end -}} {{if .ItemTo -}} itemTo{{ .ItemTo }}( {{- end -}}
|
||||||
|
unwrap.{{.Unwrapper}}(c.invoker.Call(Hash, "{{ .NameABI }}"
|
||||||
|
{{- range $arg := .Arguments -}}, {{.Name}}{{end -}} )) {{- if or .ItemTo (eq .Unwrapper "Item") -}} ) {{- end}}
|
||||||
{{- else -}} (*result.Invoke, error) {
|
{{- else -}} (*result.Invoke, error) {
|
||||||
c.invoker.Call(Hash, "{{ .NameABI }}"
|
c.invoker.Call(Hash, "{{ .NameABI }}"
|
||||||
{{- range $arg := .Arguments -}}, {{.Name}}{{end}})
|
{{- range $arg := .Arguments -}}, {{.Name}}{{end}})
|
||||||
{{- end}}
|
{{- end}}
|
||||||
}
|
}
|
||||||
{{- if eq .CallFlag "SessionIterator"}}
|
{{- if eq .Unwrapper "SessionIterator"}}
|
||||||
|
|
||||||
// {{.Name}}Expanded is similar to {{.Name}} (uses the same contract
|
// {{.Name}}Expanded is similar to {{.Name}} (uses the same contract
|
||||||
// method), but can be useful if the server used doesn't support sessions and
|
// method), but can be useful if the server used doesn't support sessions and
|
||||||
|
@ -245,7 +247,7 @@ type (
|
||||||
ContractTmpl struct {
|
ContractTmpl struct {
|
||||||
binding.ContractTmpl
|
binding.ContractTmpl
|
||||||
|
|
||||||
SafeMethods []binding.MethodTmpl
|
SafeMethods []SafeMethodTmpl
|
||||||
NamedTypes map[string]binding.ExtendedType
|
NamedTypes map[string]binding.ExtendedType
|
||||||
|
|
||||||
IsNep11D bool
|
IsNep11D bool
|
||||||
|
@ -256,6 +258,13 @@ type (
|
||||||
HasWriter bool
|
HasWriter bool
|
||||||
HasIterator bool
|
HasIterator bool
|
||||||
}
|
}
|
||||||
|
|
||||||
|
SafeMethodTmpl struct {
|
||||||
|
binding.MethodTmpl
|
||||||
|
Unwrapper string
|
||||||
|
ItemTo string
|
||||||
|
ExtendedReturn binding.ExtendedType
|
||||||
|
}
|
||||||
)
|
)
|
||||||
|
|
||||||
// NewConfig initializes and returns a new config instance.
|
// NewConfig initializes and returns a new config instance.
|
||||||
|
@ -518,7 +527,15 @@ func scTemplateToRPC(cfg binding.Config, ctr ContractTmpl, imports map[string]st
|
||||||
for i := 0; i < len(ctr.Methods); i++ {
|
for i := 0; i < len(ctr.Methods); i++ {
|
||||||
abim := cfg.Manifest.ABI.GetMethod(ctr.Methods[i].NameABI, len(ctr.Methods[i].Arguments))
|
abim := cfg.Manifest.ABI.GetMethod(ctr.Methods[i].NameABI, len(ctr.Methods[i].Arguments))
|
||||||
if abim.Safe {
|
if abim.Safe {
|
||||||
ctr.SafeMethods = append(ctr.SafeMethods, ctr.Methods[i])
|
ctr.SafeMethods = append(ctr.SafeMethods, SafeMethodTmpl{MethodTmpl: ctr.Methods[i]})
|
||||||
|
et, ok := cfg.Types[abim.Name]
|
||||||
|
if ok {
|
||||||
|
ctr.SafeMethods[len(ctr.SafeMethods)-1].ExtendedReturn = et
|
||||||
|
if abim.ReturnType == smartcontract.ArrayType && len(et.Name) > 0 {
|
||||||
|
imports["errors"] = struct{}{}
|
||||||
|
ctr.SafeMethods[len(ctr.SafeMethods)-1].ItemTo = cutPointer(ctr.Methods[i].ReturnType)
|
||||||
|
}
|
||||||
|
}
|
||||||
ctr.Methods = append(ctr.Methods[:i], ctr.Methods[i+1:]...)
|
ctr.Methods = append(ctr.Methods[:i], ctr.Methods[i+1:]...)
|
||||||
i--
|
i--
|
||||||
} else {
|
} else {
|
||||||
|
@ -529,27 +546,12 @@ func scTemplateToRPC(cfg binding.Config, ctr ContractTmpl, imports map[string]st
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
for _, et := range cfg.NamedTypes {
|
for _, et := range cfg.NamedTypes {
|
||||||
for _, fet := range et.Fields {
|
addETImports(et, ctr.NamedTypes, imports)
|
||||||
_, pkg := extendedTypeToGo(fet.ExtendedType, ctr.NamedTypes)
|
|
||||||
if pkg != "" {
|
|
||||||
imports[pkg] = struct{}{}
|
|
||||||
}
|
|
||||||
// Additional packages used during decoding.
|
|
||||||
switch fet.Base {
|
|
||||||
case smartcontract.StringType:
|
|
||||||
imports["unicode/utf8"] = struct{}{}
|
|
||||||
case smartcontract.PublicKeyType:
|
|
||||||
imports["crypto/elliptic"] = struct{}{}
|
|
||||||
case smartcontract.MapType:
|
|
||||||
imports["fmt"] = struct{}{}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
if len(cfg.NamedTypes) > 0 {
|
if len(cfg.NamedTypes) > 0 {
|
||||||
imports["errors"] = struct{}{}
|
imports["errors"] = struct{}{}
|
||||||
}
|
}
|
||||||
|
|
||||||
// We're misusing CallFlag field for function name here.
|
|
||||||
for i := range ctr.SafeMethods {
|
for i := range ctr.SafeMethods {
|
||||||
switch ctr.SafeMethods[i].ReturnType {
|
switch ctr.SafeMethods[i].ReturnType {
|
||||||
case "interface{}":
|
case "interface{}":
|
||||||
|
@ -559,49 +561,50 @@ func scTemplateToRPC(cfg binding.Config, ctr ContractTmpl, imports map[string]st
|
||||||
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
||||||
imports["github.com/nspcc-dev/neo-go/pkg/neorpc/result"] = struct{}{}
|
imports["github.com/nspcc-dev/neo-go/pkg/neorpc/result"] = struct{}{}
|
||||||
ctr.SafeMethods[i].ReturnType = "uuid.UUID, result.Iterator"
|
ctr.SafeMethods[i].ReturnType = "uuid.UUID, result.Iterator"
|
||||||
ctr.SafeMethods[i].CallFlag = "SessionIterator"
|
ctr.SafeMethods[i].Unwrapper = "SessionIterator"
|
||||||
ctr.HasIterator = true
|
ctr.HasIterator = true
|
||||||
} else {
|
} else {
|
||||||
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
||||||
ctr.SafeMethods[i].ReturnType = "stackitem.Item"
|
ctr.SafeMethods[i].ReturnType = "stackitem.Item"
|
||||||
ctr.SafeMethods[i].CallFlag = "Item"
|
ctr.SafeMethods[i].Unwrapper = "Item"
|
||||||
}
|
}
|
||||||
case "bool":
|
case "bool":
|
||||||
ctr.SafeMethods[i].CallFlag = "Bool"
|
ctr.SafeMethods[i].Unwrapper = "Bool"
|
||||||
case "*big.Int":
|
case "*big.Int":
|
||||||
ctr.SafeMethods[i].CallFlag = "BigInt"
|
ctr.SafeMethods[i].Unwrapper = "BigInt"
|
||||||
case "string":
|
case "string":
|
||||||
ctr.SafeMethods[i].CallFlag = "UTF8String"
|
ctr.SafeMethods[i].Unwrapper = "UTF8String"
|
||||||
case "util.Uint160":
|
case "util.Uint160":
|
||||||
ctr.SafeMethods[i].CallFlag = "Uint160"
|
ctr.SafeMethods[i].Unwrapper = "Uint160"
|
||||||
case "util.Uint256":
|
case "util.Uint256":
|
||||||
ctr.SafeMethods[i].CallFlag = "Uint256"
|
ctr.SafeMethods[i].Unwrapper = "Uint256"
|
||||||
case "*keys.PublicKey":
|
case "*keys.PublicKey":
|
||||||
ctr.SafeMethods[i].CallFlag = "PublicKey"
|
ctr.SafeMethods[i].Unwrapper = "PublicKey"
|
||||||
case "[]byte":
|
case "[]byte":
|
||||||
ctr.SafeMethods[i].CallFlag = "Bytes"
|
ctr.SafeMethods[i].Unwrapper = "Bytes"
|
||||||
case "[]interface{}":
|
case "[]interface{}":
|
||||||
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
imports["github.com/nspcc-dev/neo-go/pkg/vm/stackitem"] = struct{}{}
|
||||||
ctr.SafeMethods[i].ReturnType = "[]stackitem.Item"
|
ctr.SafeMethods[i].ReturnType = "[]stackitem.Item"
|
||||||
ctr.SafeMethods[i].CallFlag = "Array"
|
ctr.SafeMethods[i].Unwrapper = "Array"
|
||||||
case "*stackitem.Map":
|
case "*stackitem.Map":
|
||||||
ctr.SafeMethods[i].CallFlag = "Map"
|
ctr.SafeMethods[i].Unwrapper = "Map"
|
||||||
case "[]bool":
|
case "[]bool":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfBools"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfBools"
|
||||||
case "[]*big.Int":
|
case "[]*big.Int":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfBigInts"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfBigInts"
|
||||||
case "[][]byte":
|
case "[][]byte":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfBytes"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfBytes"
|
||||||
case "[]string":
|
case "[]string":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfUTF8Strings"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfUTF8Strings"
|
||||||
case "[]util.Uint160":
|
case "[]util.Uint160":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfUint160"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfUint160"
|
||||||
case "[]util.Uint256":
|
case "[]util.Uint256":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfUint256"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfUint256"
|
||||||
case "keys.PublicKeys":
|
case "keys.PublicKeys":
|
||||||
ctr.SafeMethods[i].CallFlag = "ArrayOfPublicKeys"
|
ctr.SafeMethods[i].Unwrapper = "ArrayOfPublicKeys"
|
||||||
default:
|
default:
|
||||||
ctr.SafeMethods[i].CallFlag = ""
|
addETImports(ctr.SafeMethods[i].ExtendedReturn, ctr.NamedTypes, imports)
|
||||||
|
ctr.SafeMethods[i].Unwrapper = "Item"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -629,6 +632,32 @@ func scTemplateToRPC(cfg binding.Config, ctr ContractTmpl, imports map[string]st
|
||||||
return ctr
|
return ctr
|
||||||
}
|
}
|
||||||
|
|
||||||
|
func addETImports(et binding.ExtendedType, named map[string]binding.ExtendedType, imports map[string]struct{}) {
|
||||||
|
_, pkg := extendedTypeToGo(et, named)
|
||||||
|
if pkg != "" {
|
||||||
|
imports[pkg] = struct{}{}
|
||||||
|
}
|
||||||
|
// Additional packages used during decoding.
|
||||||
|
switch et.Base {
|
||||||
|
case smartcontract.StringType:
|
||||||
|
imports["unicode/utf8"] = struct{}{}
|
||||||
|
imports["errors"] = struct{}{}
|
||||||
|
case smartcontract.PublicKeyType:
|
||||||
|
imports["crypto/elliptic"] = struct{}{}
|
||||||
|
case smartcontract.MapType:
|
||||||
|
imports["fmt"] = struct{}{}
|
||||||
|
}
|
||||||
|
if et.Value != nil {
|
||||||
|
addETImports(*et.Value, named, imports)
|
||||||
|
}
|
||||||
|
if et.Base == smartcontract.MapType {
|
||||||
|
addETImports(binding.ExtendedType{Base: et.Key}, named, imports)
|
||||||
|
}
|
||||||
|
for i := range et.Fields {
|
||||||
|
addETImports(et.Fields[i].ExtendedType, named, imports)
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
func cutPointer(s string) string {
|
func cutPointer(s string) string {
|
||||||
if s[0] == '*' {
|
if s[0] == '*' {
|
||||||
return s[1:]
|
return s[1:]
|
||||||
|
|
Loading…
Reference in a new issue