grc20reg.gno

1.79 Kb ยท 78 lines
 1package grc20reg
 2
 3import (
 4	"std"
 5
 6	"gno.land/p/demo/avl"
 7	"gno.land/p/demo/avl/rotree"
 8	"gno.land/p/demo/fqname"
 9	"gno.land/p/demo/grc/grc20"
10	"gno.land/p/demo/ufmt"
11)
12
13var registry = avl.NewTree() // rlmPath[.slug] -> *Token (slug is optional)
14func Register(cur realm, token *grc20.Token, slug string) {
15	rlmPath := std.PreviousRealm().PkgPath()
16	key := fqname.Construct(rlmPath, slug)
17	registry.Set(key, token)
18	std.Emit(
19		registerEvent,
20		"pkgpath", rlmPath,
21		"slug", slug,
22	)
23}
24
25func Get(key string) *grc20.Token {
26	token, ok := registry.Get(key)
27	if !ok {
28		return nil
29	}
30	return token.(*grc20.Token)
31}
32
33func MustGet(key string) *grc20.Token {
34	token := Get(key)
35	if token == nil {
36		panic("unknown token: " + key)
37	}
38	return token
39}
40
41func Render(path string) string {
42	switch {
43	case path == "": // home
44		// TODO: add pagination
45		s := ""
46		count := 0
47		registry.Iterate("", "", func(key string, tokenI any) bool {
48			count++
49			token := tokenI.(*grc20.Token)
50			rlmPath, slug := fqname.Parse(key)
51			rlmLink := fqname.RenderLink(rlmPath, slug)
52			infoLink := "/r/demo/grc20reg:" + key
53			s += ufmt.Sprintf("- **%s** - %s - [info](%s)\n", token.GetName(), rlmLink, infoLink)
54			return false
55		})
56		if count == 0 {
57			return "No registered token."
58		}
59		return s
60	default: // specific token
61		key := path
62		token := MustGet(key)
63		rlmPath, slug := fqname.Parse(key)
64		rlmLink := fqname.RenderLink(rlmPath, slug)
65		s := ufmt.Sprintf("# %s\n", token.GetName())
66		s += ufmt.Sprintf("- symbol: **%s**\n", token.GetSymbol())
67		s += ufmt.Sprintf("- realm: %s\n", rlmLink)
68		s += ufmt.Sprintf("- decimals: %d\n", token.GetDecimals())
69		s += ufmt.Sprintf("- total supply: %d\n", token.TotalSupply())
70		return s
71	}
72}
73
74const registerEvent = "register"
75
76func GetRegistry() *rotree.ReadOnlyTree {
77	return rotree.Wrap(registry, nil)
78}