Skip to content

Commit

Permalink
NNS wrapper extensions (#397)
Browse files Browse the repository at this point in the history
  • Loading branch information
roman-khimov authored May 6, 2024
2 parents 286b141 + 1bcacce commit e78d64e
Showing 1 changed file with 56 additions and 14 deletions.
70 changes: 56 additions & 14 deletions rpc/nns/hashes.go
Original file line number Diff line number Diff line change
Expand Up @@ -36,27 +36,69 @@ func InferHash(sg ContractStateGetter) (util.Uint160, error) {
return c.Hash, nil
}

// NewInferredReader creates an instance of [ContractReader] using hash obtained via
// [InferHash].
func NewInferredReader(sg ContractStateGetter, invoker Invoker) (*ContractReader, error) {
h, err := InferHash(sg)
if err != nil {
return nil, err
}
return NewReader(invoker, h), nil
}

// NewInferred creates an instance of [Contract] using hash obtained via [InferHash].
func NewInferred(sg ContractStateGetter, actor Actor) (*Contract, error) {
h, err := InferHash(sg)
if err != nil {
return nil, err
}
return New(actor, h), nil
}

// AddressFromRecord extracts [util.Uint160] hash from the string using one of
// the following formats:
// - hex-encoded LE (reversed) string
// - Neo address ("Nxxxx")
//
// NeoFS used both for contract hashes stored in NNS at various stages of its
// development.
//
// See also: [AddressFromRecords].
func AddressFromRecord(s string) (util.Uint160, error) {
h, err := util.Uint160DecodeStringLE(s)
if err == nil {
return h, nil
}

h, err = address.StringToUint160(s)
if err == nil {
return h, nil
}
return util.Uint160{}, errors.New("no valid address found")
}

// AddressFromRecords extracts [util.Uint160] hash from the set of given
// strings using [AddressFromRecord]. Returns the first result that can be
// interpreted as address.
func AddressFromRecords(strs []string) (util.Uint160, error) {
for i := range strs {
h, err := AddressFromRecord(strs[i])
if err == nil {
return h, nil
}
}
return util.Uint160{}, errors.New("no valid addresses are found")
}

// ResolveFSContract is a convenience method that doesn't exist in the NNS
// contract itself (it doesn't care which data is stored there). It assumes
// that contracts follow the [ContractTLD] convention, gets simple contract
// names (like "container" or "netmap") and extracts the hash for the
// respective NNS record in any of the formats (of which historically there's
// been a few).
// respective NNS record using [AddressFromRecords].
func (c *ContractReader) ResolveFSContract(name string) (util.Uint160, error) {
strs, err := c.Resolve(name+"."+ContractTLD, TXT)
if err != nil {
return util.Uint160{}, err
}
for i := range strs {
h, err := util.Uint160DecodeStringLE(strs[i])
if err == nil {
return h, nil
}

h, err = address.StringToUint160(strs[i])
if err == nil {
return h, nil
}
}
return util.Uint160{}, errors.New("no valid hashes are found")
return AddressFromRecords(strs)
}

0 comments on commit e78d64e

Please sign in to comment.