manifest: move ABI code into file of its own
Make it a little more convenient to work with it.
This commit is contained in:
parent
60dfffc574
commit
211fe307ee
2 changed files with 102 additions and 93 deletions
102
pkg/smartcontract/manifest/abi.go
Normal file
102
pkg/smartcontract/manifest/abi.go
Normal file
|
@ -0,0 +1,102 @@
|
|||
package manifest
|
||||
|
||||
import (
|
||||
"errors"
|
||||
|
||||
"github.com/nspcc-dev/neo-go/pkg/vm/stackitem"
|
||||
)
|
||||
|
||||
const (
|
||||
// MethodInit is a name for default initialization method.
|
||||
MethodInit = "_initialize"
|
||||
|
||||
// MethodDeploy is a name for default method called during contract deployment.
|
||||
MethodDeploy = "_deploy"
|
||||
|
||||
// MethodVerify is a name for default verification method.
|
||||
MethodVerify = "verify"
|
||||
|
||||
// MethodOnNEP17Payment is name of the method which is called when contract receives NEP-17 tokens.
|
||||
MethodOnNEP17Payment = "onNEP17Payment"
|
||||
|
||||
// MethodOnNEP11Payment is the name of the method which is called when contract receives NEP-11 tokens.
|
||||
MethodOnNEP11Payment = "onNEP11Payment"
|
||||
)
|
||||
|
||||
// ABI represents a contract application binary interface.
|
||||
type ABI struct {
|
||||
Methods []Method `json:"methods"`
|
||||
Events []Event `json:"events"`
|
||||
}
|
||||
|
||||
// GetMethod returns methods with the specified name.
|
||||
func (a *ABI) GetMethod(name string, paramCount int) *Method {
|
||||
for i := range a.Methods {
|
||||
if a.Methods[i].Name == name && (paramCount == -1 || len(a.Methods[i].Parameters) == paramCount) {
|
||||
return &a.Methods[i]
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// GetEvent returns event with the specified name.
|
||||
func (a *ABI) GetEvent(name string) *Event {
|
||||
for i := range a.Events {
|
||||
if a.Events[i].Name == name {
|
||||
return &a.Events[i]
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// ToStackItem converts ABI to stackitem.Item.
|
||||
func (a *ABI) ToStackItem() stackitem.Item {
|
||||
methods := make([]stackitem.Item, len(a.Methods))
|
||||
for i := range a.Methods {
|
||||
methods[i] = a.Methods[i].ToStackItem()
|
||||
}
|
||||
events := make([]stackitem.Item, len(a.Events))
|
||||
for i := range a.Events {
|
||||
events[i] = a.Events[i].ToStackItem()
|
||||
}
|
||||
return stackitem.NewStruct([]stackitem.Item{
|
||||
stackitem.Make(methods),
|
||||
stackitem.Make(events),
|
||||
})
|
||||
}
|
||||
|
||||
// FromStackItem converts stackitem.Item to ABI.
|
||||
func (a *ABI) FromStackItem(item stackitem.Item) error {
|
||||
if item.Type() != stackitem.StructT {
|
||||
return errors.New("invalid ABI stackitem type")
|
||||
}
|
||||
str := item.Value().([]stackitem.Item)
|
||||
if len(str) != 2 {
|
||||
return errors.New("invalid ABI stackitem length")
|
||||
}
|
||||
if str[0].Type() != stackitem.ArrayT {
|
||||
return errors.New("invalid Methods stackitem type")
|
||||
}
|
||||
methods := str[0].Value().([]stackitem.Item)
|
||||
a.Methods = make([]Method, len(methods))
|
||||
for i := range methods {
|
||||
m := new(Method)
|
||||
if err := m.FromStackItem(methods[i]); err != nil {
|
||||
return err
|
||||
}
|
||||
a.Methods[i] = *m
|
||||
}
|
||||
if str[1].Type() != stackitem.ArrayT {
|
||||
return errors.New("invalid Events stackitem type")
|
||||
}
|
||||
events := str[1].Value().([]stackitem.Item)
|
||||
a.Events = make([]Event, len(events))
|
||||
for i := range events {
|
||||
e := new(Event)
|
||||
if err := e.FromStackItem(events[i]); err != nil {
|
||||
return err
|
||||
}
|
||||
a.Events[i] = *e
|
||||
}
|
||||
return nil
|
||||
}
|
|
@ -13,33 +13,12 @@ const (
|
|||
// MaxManifestSize is a max length for a valid contract manifest.
|
||||
MaxManifestSize = math.MaxUint16
|
||||
|
||||
// MethodInit is a name for default initialization method.
|
||||
MethodInit = "_initialize"
|
||||
|
||||
// MethodDeploy is a name for default method called during contract deployment.
|
||||
MethodDeploy = "_deploy"
|
||||
|
||||
// MethodVerify is a name for default verification method.
|
||||
MethodVerify = "verify"
|
||||
|
||||
// MethodOnNEP17Payment is name of the method which is called when contract receives NEP-17 tokens.
|
||||
MethodOnNEP17Payment = "onNEP17Payment"
|
||||
|
||||
// MethodOnNEP11Payment is the name of the method which is called when contract receives NEP-11 tokens.
|
||||
MethodOnNEP11Payment = "onNEP11Payment"
|
||||
|
||||
// NEP10StandardName represents the name of NEP10 smartcontract standard.
|
||||
NEP10StandardName = "NEP-10"
|
||||
// NEP17StandardName represents the name of NEP17 smartcontract standard.
|
||||
NEP17StandardName = "NEP-17"
|
||||
)
|
||||
|
||||
// ABI represents a contract application binary interface.
|
||||
type ABI struct {
|
||||
Methods []Method `json:"methods"`
|
||||
Events []Event `json:"events"`
|
||||
}
|
||||
|
||||
// Manifest represens contract metadata.
|
||||
type Manifest struct {
|
||||
// Name is a contract's name.
|
||||
|
@ -80,26 +59,6 @@ func DefaultManifest(name string) *Manifest {
|
|||
return m
|
||||
}
|
||||
|
||||
// GetMethod returns methods with the specified name.
|
||||
func (a *ABI) GetMethod(name string, paramCount int) *Method {
|
||||
for i := range a.Methods {
|
||||
if a.Methods[i].Name == name && (paramCount == -1 || len(a.Methods[i].Parameters) == paramCount) {
|
||||
return &a.Methods[i]
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// GetEvent returns event with the specified name.
|
||||
func (a *ABI) GetEvent(name string) *Event {
|
||||
for i := range a.Events {
|
||||
if a.Events[i].Name == name {
|
||||
return &a.Events[i]
|
||||
}
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
||||
// CanCall returns true is current contract is allowed to call
|
||||
// method of another contract with specified hash.
|
||||
func (m *Manifest) CanCall(hash util.Uint160, toCall *Manifest, method string) bool {
|
||||
|
@ -246,55 +205,3 @@ func (m *Manifest) FromStackItem(item stackitem.Item) error {
|
|||
}
|
||||
return json.Unmarshal(extra, &m.Extra)
|
||||
}
|
||||
|
||||
// ToStackItem converts ABI to stackitem.Item.
|
||||
func (a *ABI) ToStackItem() stackitem.Item {
|
||||
methods := make([]stackitem.Item, len(a.Methods))
|
||||
for i := range a.Methods {
|
||||
methods[i] = a.Methods[i].ToStackItem()
|
||||
}
|
||||
events := make([]stackitem.Item, len(a.Events))
|
||||
for i := range a.Events {
|
||||
events[i] = a.Events[i].ToStackItem()
|
||||
}
|
||||
return stackitem.NewStruct([]stackitem.Item{
|
||||
stackitem.Make(methods),
|
||||
stackitem.Make(events),
|
||||
})
|
||||
}
|
||||
|
||||
// FromStackItem converts stackitem.Item to ABI.
|
||||
func (a *ABI) FromStackItem(item stackitem.Item) error {
|
||||
if item.Type() != stackitem.StructT {
|
||||
return errors.New("invalid ABI stackitem type")
|
||||
}
|
||||
str := item.Value().([]stackitem.Item)
|
||||
if len(str) != 2 {
|
||||
return errors.New("invalid ABI stackitem length")
|
||||
}
|
||||
if str[0].Type() != stackitem.ArrayT {
|
||||
return errors.New("invalid Methods stackitem type")
|
||||
}
|
||||
methods := str[0].Value().([]stackitem.Item)
|
||||
a.Methods = make([]Method, len(methods))
|
||||
for i := range methods {
|
||||
m := new(Method)
|
||||
if err := m.FromStackItem(methods[i]); err != nil {
|
||||
return err
|
||||
}
|
||||
a.Methods[i] = *m
|
||||
}
|
||||
if str[1].Type() != stackitem.ArrayT {
|
||||
return errors.New("invalid Events stackitem type")
|
||||
}
|
||||
events := str[1].Value().([]stackitem.Item)
|
||||
a.Events = make([]Event, len(events))
|
||||
for i := range events {
|
||||
e := new(Event)
|
||||
if err := e.FromStackItem(events[i]); err != nil {
|
||||
return err
|
||||
}
|
||||
a.Events[i] = *e
|
||||
}
|
||||
return nil
|
||||
}
|
||||
|
|
Loading…
Reference in a new issue