2021-03-16 19:55:17 +00:00
|
|
|
package client
|
|
|
|
|
2021-03-22 09:13:08 +00:00
|
|
|
// Various non-policy things from native contracts.
|
2021-03-16 19:55:17 +00:00
|
|
|
|
|
|
|
import (
|
2021-03-24 10:12:33 +00:00
|
|
|
"errors"
|
2021-03-16 19:55:17 +00:00
|
|
|
"fmt"
|
2022-02-09 13:07:07 +00:00
|
|
|
"math/big"
|
2021-03-16 19:55:17 +00:00
|
|
|
|
|
|
|
"github.com/nspcc-dev/neo-go/pkg/core/native/nativenames"
|
2021-03-22 17:34:27 +00:00
|
|
|
"github.com/nspcc-dev/neo-go/pkg/core/native/noderoles"
|
|
|
|
"github.com/nspcc-dev/neo-go/pkg/crypto/keys"
|
2022-01-25 09:40:19 +00:00
|
|
|
"github.com/nspcc-dev/neo-go/pkg/rpc/client/nns"
|
2021-03-22 17:34:27 +00:00
|
|
|
"github.com/nspcc-dev/neo-go/pkg/smartcontract"
|
2021-05-14 16:38:04 +00:00
|
|
|
"github.com/nspcc-dev/neo-go/pkg/util"
|
2021-03-16 19:55:17 +00:00
|
|
|
)
|
|
|
|
|
|
|
|
// GetOraclePrice invokes `getPrice` method on a native Oracle contract.
|
|
|
|
func (c *Client) GetOraclePrice() (int64, error) {
|
2022-03-01 10:17:37 +00:00
|
|
|
oracleHash, err := c.GetNativeContractHash(nativenames.Oracle)
|
2021-03-16 19:55:17 +00:00
|
|
|
if err != nil {
|
|
|
|
return 0, fmt.Errorf("failed to get native Oracle hash: %w", err)
|
|
|
|
}
|
|
|
|
return c.invokeNativeGetMethod(oracleHash, "getPrice")
|
|
|
|
}
|
2021-03-16 19:59:04 +00:00
|
|
|
|
2021-05-14 16:38:04 +00:00
|
|
|
// GetNNSPrice invokes `getPrice` method on a NeoNameService contract with the specified hash.
|
|
|
|
func (c *Client) GetNNSPrice(nnsHash util.Uint160) (int64, error) {
|
2021-03-16 19:59:04 +00:00
|
|
|
return c.invokeNativeGetMethod(nnsHash, "getPrice")
|
|
|
|
}
|
2021-03-16 20:03:51 +00:00
|
|
|
|
|
|
|
// GetGasPerBlock invokes `getGasPerBlock` method on a native NEO contract.
|
|
|
|
func (c *Client) GetGasPerBlock() (int64, error) {
|
2021-07-21 09:19:55 +00:00
|
|
|
return c.getFromNEO("getGasPerBlock")
|
|
|
|
}
|
|
|
|
|
|
|
|
// GetCandidateRegisterPrice invokes `getRegisterPrice` method on native NEO contract.
|
|
|
|
func (c *Client) GetCandidateRegisterPrice() (int64, error) {
|
|
|
|
return c.getFromNEO("getRegisterPrice")
|
|
|
|
}
|
|
|
|
|
|
|
|
func (c *Client) getFromNEO(meth string) (int64, error) {
|
2021-03-16 20:03:51 +00:00
|
|
|
neoHash, err := c.GetNativeContractHash(nativenames.Neo)
|
|
|
|
if err != nil {
|
|
|
|
return 0, fmt.Errorf("failed to get native NEO hash: %w", err)
|
|
|
|
}
|
2021-07-21 09:19:55 +00:00
|
|
|
return c.invokeNativeGetMethod(neoHash, meth)
|
2021-03-16 20:03:51 +00:00
|
|
|
}
|
2021-03-22 17:34:27 +00:00
|
|
|
|
|
|
|
// GetDesignatedByRole invokes `getDesignatedByRole` method on a native RoleManagement contract.
|
|
|
|
func (c *Client) GetDesignatedByRole(role noderoles.Role, index uint32) (keys.PublicKeys, error) {
|
|
|
|
rmHash, err := c.GetNativeContractHash(nativenames.Designation)
|
|
|
|
if err != nil {
|
|
|
|
return nil, fmt.Errorf("failed to get native RoleManagement hash: %w", err)
|
|
|
|
}
|
|
|
|
result, err := c.InvokeFunction(rmHash, "getDesignatedByRole", []smartcontract.Parameter{
|
|
|
|
{
|
|
|
|
Type: smartcontract.IntegerType,
|
2022-02-09 13:07:07 +00:00
|
|
|
Value: big.NewInt(int64(role)),
|
2021-03-22 17:34:27 +00:00
|
|
|
},
|
|
|
|
{
|
|
|
|
Type: smartcontract.IntegerType,
|
2022-02-09 13:07:07 +00:00
|
|
|
Value: big.NewInt(int64(index)),
|
2021-03-22 17:34:27 +00:00
|
|
|
},
|
|
|
|
}, nil)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
err = getInvocationError(result)
|
|
|
|
if err != nil {
|
|
|
|
return nil, fmt.Errorf("`getDesignatedByRole`: %w", err)
|
|
|
|
}
|
|
|
|
return topPublicKeysFromStack(result.Stack)
|
|
|
|
}
|
2021-03-24 10:12:33 +00:00
|
|
|
|
2021-05-14 16:38:04 +00:00
|
|
|
// NNSResolve invokes `resolve` method on a NameService contract with the specified hash.
|
2021-05-17 18:10:09 +00:00
|
|
|
func (c *Client) NNSResolve(nnsHash util.Uint160, name string, typ nns.RecordType) (string, error) {
|
|
|
|
if typ == nns.CNAME {
|
2021-03-24 10:12:33 +00:00
|
|
|
return "", errors.New("can't resolve CNAME record type")
|
|
|
|
}
|
2021-05-14 16:38:04 +00:00
|
|
|
result, err := c.InvokeFunction(nnsHash, "resolve", []smartcontract.Parameter{
|
2021-03-24 10:12:33 +00:00
|
|
|
{
|
|
|
|
Type: smartcontract.StringType,
|
|
|
|
Value: name,
|
|
|
|
},
|
|
|
|
{
|
|
|
|
Type: smartcontract.IntegerType,
|
2022-02-09 13:07:07 +00:00
|
|
|
Value: big.NewInt(int64(typ)),
|
2021-03-24 10:12:33 +00:00
|
|
|
},
|
|
|
|
}, nil)
|
|
|
|
if err != nil {
|
|
|
|
return "", err
|
|
|
|
}
|
|
|
|
err = getInvocationError(result)
|
|
|
|
if err != nil {
|
|
|
|
return "", fmt.Errorf("`resolve`: %w", err)
|
|
|
|
}
|
|
|
|
return topStringFromStack(result.Stack)
|
|
|
|
}
|
|
|
|
|
2021-05-14 16:38:04 +00:00
|
|
|
// NNSIsAvailable invokes `isAvailable` method on a NeoNameService contract with the specified hash.
|
|
|
|
func (c *Client) NNSIsAvailable(nnsHash util.Uint160, name string) (bool, error) {
|
|
|
|
result, err := c.InvokeFunction(nnsHash, "isAvailable", []smartcontract.Parameter{
|
2021-03-24 10:12:33 +00:00
|
|
|
{
|
|
|
|
Type: smartcontract.StringType,
|
|
|
|
Value: name,
|
|
|
|
},
|
|
|
|
}, nil)
|
|
|
|
if err != nil {
|
|
|
|
return false, err
|
|
|
|
}
|
|
|
|
err = getInvocationError(result)
|
|
|
|
if err != nil {
|
|
|
|
return false, fmt.Errorf("`isAvailable`: %w", err)
|
|
|
|
}
|
|
|
|
return topBoolFromStack(result.Stack)
|
|
|
|
}
|
2021-09-09 19:52:27 +00:00
|
|
|
|
|
|
|
// NNSGetAllRecords returns all records for a given name from NNS service.
|
|
|
|
func (c *Client) NNSGetAllRecords(nnsHash util.Uint160, name string) ([]nns.RecordState, error) {
|
|
|
|
result, err := c.InvokeFunction(nnsHash, "getAllRecords", []smartcontract.Parameter{
|
|
|
|
{
|
|
|
|
Type: smartcontract.StringType,
|
|
|
|
Value: name,
|
|
|
|
},
|
|
|
|
}, nil)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
err = getInvocationError(result)
|
|
|
|
if err != nil {
|
|
|
|
return nil, err
|
|
|
|
}
|
|
|
|
|
|
|
|
arr, err := topIterableFromStack(result.Stack, nns.RecordState{})
|
|
|
|
if err != nil {
|
|
|
|
return nil, fmt.Errorf("failed to get token IDs from stack: %w", err)
|
|
|
|
}
|
|
|
|
rss := make([]nns.RecordState, len(arr))
|
|
|
|
for i := range rss {
|
|
|
|
rss[i] = arr[i].(nns.RecordState)
|
|
|
|
}
|
|
|
|
return rss, nil
|
|
|
|
}
|
2022-03-01 10:10:54 +00:00
|
|
|
|
|
|
|
// GetNotaryServiceFeePerKey returns a reward per notary request key for designated
|
|
|
|
// notary nodes. It doesn't cache the result.
|
|
|
|
func (c *Client) GetNotaryServiceFeePerKey() (int64, error) {
|
|
|
|
notaryHash, err := c.GetNativeContractHash(nativenames.Notary)
|
|
|
|
if err != nil {
|
|
|
|
return 0, fmt.Errorf("failed to get native Notary hash: %w", err)
|
|
|
|
}
|
|
|
|
return c.invokeNativeGetMethod(notaryHash, "getNotaryServiceFeePerKey")
|
|
|
|
}
|