Search Apps Documentation Source Content File Folder Download Copy

README.md

3.45 Kb ยท 116 lines
  1This is a simple test realm contract that demonstrates how to use the banker.
  2
  3See [gno.land/r/demo/banktest/banktest.go](/r/demo/banktest/banktest.go) to see the original contract code.
  4
  5This article will go through each line to explain how it works.
  6
  7```go
  8package banktest
  9```
 10
 11This package is locally named "banktest" (could be anything).
 12
 13```go
 14import (
 15    "std"
 16)
 17```
 18
 19The "std" package is defined by the gno code in stdlibs/std/. </br> Self explanatory; and you'll see more usage from std later.
 20
 21```go
 22type activity struct {
 23    caller   std.Address
 24    sent     std.Coins
 25    returned std.Coins
 26    time     time.Time
 27}
 28
 29func (act *activity) String() string {
 30    return act.caller.String() + " " +
 31        act.sent.String() + " sent, " +
 32        act.returned.String() + " returned, at " +
 33        act.time.Format("2006-01-02 3:04pm MST")
 34}
 35
 36var latest [10]*activity
 37```
 38
 39This is just maintaining a list of recent activity to this contract. Notice that the "latest" variable is defined "globally" within the context of the realm with path "gno.land/r/demo/banktest".
 40
 41This means that calls to functions defined within this package are encapsulated within this "data realm", where the data is mutated based on transactions that can potentially cross many realm and non-realm package boundaries (in the call stack).
 42
 43```go
 44// Deposit will take the coins (to the realm's pkgaddr) or return them to user.
 45func Deposit(returnDenom string, returnAmount int64) string {
 46    std.AssertOriginCall()
 47    caller := std.GetOrigCaller()
 48    send := std.Coins{{returnDenom, returnAmount}}
 49```
 50
 51This is the beginning of the definition of the contract function named "Deposit". `std.AssertOriginCall() asserts that this function was called by a gno transactional Message. The caller is the user who signed off on this transactional message. Send is the amount of deposit sent along with this message.
 52
 53```go
 54    // record activity
 55    act := &activity{
 56        caller:   caller,
 57        sent:     std.GetOrigSend(),
 58        returned: send,
 59        time:     time.Now(),
 60    }
 61    for i := len(latest) - 2; i >= 0; i-- {
 62        latest[i+1] = latest[i] // shift by +1.
 63    }
 64    latest[0] = act
 65```
 66
 67Updating the "latest" array for viewing at gno.land/r/demo/banktest: (w/ trailing colon).
 68
 69```go
 70    // return if any.
 71    if returnAmount > 0 {
 72```
 73
 74If the user requested the return of coins...
 75
 76```go
 77        banker := std.GetBanker(std.BankerTypeOrigSend)
 78```
 79
 80use a std.Banker instance to return any deposited coins to the original sender.
 81
 82```go
 83        pkgaddr := std.GetOrigPkgAddr()
 84        // TODO: use std.Coins constructors, this isn't generally safe.
 85        banker.SendCoins(pkgaddr, caller, send)
 86        return "returned!"
 87```
 88
 89Notice that each realm package has an associated Cosmos address.
 90
 91Finally, the results are rendered via an ABCI query call when you visit [/r/demo/banktest:](/r/demo/banktest:).
 92
 93```go
 94func Render(path string) string {
 95    // get realm coins.
 96    banker := std.GetBanker(std.BankerTypeReadonly)
 97    coins := banker.GetCoins(std.GetOrigPkgAddr())
 98
 99    // render
100    res := ""
101    res += "## recent activity\n"
102    res += "\n"
103    for _, act := range latest {
104        if act == nil {
105            break
106        }
107        res += " * " + act.String() + "\n"
108    }
109    res += "\n"
110    res += "## total deposits\n"
111    res += coins.String()
112    return res
113}
114```
115
116You can call this contract yourself, by vistiing [/r/demo/banktest](/r/demo/banktest) and the [quickstart guide](/r/demo/boards:gnolang/4).