github.com/nspcc-dev/neo-go@v0.105.2-0.20240517133400-6be757af3eba/pkg/rpcclient/neptoken/base.go (about)

     1  /*
     2  Package neptoken contains RPC wrapper for common NEP-11 and NEP-17 methods.
     3  
     4  All of these methods are safe, read-only.
     5  */
     6  package neptoken
     7  
     8  import (
     9  	"math/big"
    10  
    11  	"github.com/nspcc-dev/neo-go/pkg/neorpc/result"
    12  	"github.com/nspcc-dev/neo-go/pkg/rpcclient/unwrap"
    13  	"github.com/nspcc-dev/neo-go/pkg/util"
    14  )
    15  
    16  const (
    17  	// MaxValidDecimals is the maximum value 'decimals' contract method can
    18  	// return to be considered as valid. It's log10(2^256), higher values
    19  	// don't make any sense on a VM with 256-bit integers. This restriction
    20  	// is not imposed by NEP-17 or NEP-11, but we do it as a sanity check
    21  	// anyway (and return plain int as a result).
    22  	MaxValidDecimals = 77
    23  )
    24  
    25  // Invoker is used by Base to call various methods.
    26  type Invoker interface {
    27  	Call(contract util.Uint160, operation string, params ...any) (*result.Invoke, error)
    28  }
    29  
    30  // Base is a reader interface for common NEP-11 and NEP-17 methods built
    31  // on top of Invoker.
    32  type Base struct {
    33  	invoker Invoker
    34  	hash    util.Uint160
    35  }
    36  
    37  // New creates an instance of Base for contract with the given hash using the
    38  // given invoker.
    39  func New(invoker Invoker, hash util.Uint160) *Base {
    40  	return &Base{invoker, hash}
    41  }
    42  
    43  // Decimals implements `decimals` NEP-17 or NEP-11 method and returns the number
    44  // of decimals used by token. For non-divisible NEP-11 tokens this method always
    45  // returns zero. Values less than 0 or more than MaxValidDecimals are considered
    46  // to be invalid (with an appropriate error) even if returned by the contract.
    47  func (b *Base) Decimals() (int, error) {
    48  	r, err := b.invoker.Call(b.hash, "decimals")
    49  	dec, err := unwrap.LimitedInt64(r, err, 0, MaxValidDecimals)
    50  	return int(dec), err
    51  }
    52  
    53  // Symbol implements `symbol` NEP-17 or NEP-11 method and returns a short token
    54  // identifier (like "NEO" or "GAS").
    55  func (b *Base) Symbol() (string, error) {
    56  	return unwrap.PrintableASCIIString(b.invoker.Call(b.hash, "symbol"))
    57  }
    58  
    59  // TotalSupply returns the total token supply currently available (the amount
    60  // of minted tokens).
    61  func (b *Base) TotalSupply() (*big.Int, error) {
    62  	return unwrap.BigInt(b.invoker.Call(b.hash, "totalSupply"))
    63  }
    64  
    65  // BalanceOf returns the token balance of the given account. For NEP-17 that's
    66  // the token balance with decimals (1 TOK with 2 decimals will lead to 100
    67  // returned from this method). For non-divisible NEP-11 that's the number of
    68  // NFTs owned by the account, for divisible NEP-11 that's the sum of the parts
    69  // of all NFTs owned by the account.
    70  func (b *Base) BalanceOf(account util.Uint160) (*big.Int, error) {
    71  	return unwrap.BigInt(b.invoker.Call(b.hash, "balanceOf", account))
    72  }