-
Notifications
You must be signed in to change notification settings - Fork 30
/
proxy.go
89 lines (78 loc) · 2.68 KB
/
proxy.go
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
package keeper
import (
sdk "github.com/line/lbm-sdk/types"
sdkerrors "github.com/line/lbm-sdk/types/errors"
"github.com/line/lbm-sdk/x/token/internal/types"
)
var (
ApprovedValue = []byte{0x01}
)
type ProxyKeeper interface {
IsApproved(ctx sdk.Context, proxy sdk.AccAddress, approver sdk.AccAddress) bool
SetApproved(ctx sdk.Context, proxy sdk.AccAddress, approver sdk.AccAddress) error
DeleteApproved(ctx sdk.Context, proxy sdk.AccAddress, approver sdk.AccAddress) error
}
func (k Keeper) IsApproved(ctx sdk.Context, proxy sdk.AccAddress, approver sdk.AccAddress) bool {
store := ctx.KVStore(k.storeKey)
approvedKey := types.TokenApprovedKey(k.getContractID(ctx), proxy, approver)
return store.Has(approvedKey)
}
func (k Keeper) SetApproved(ctx sdk.Context, proxy sdk.AccAddress, approver sdk.AccAddress) error {
store := ctx.KVStore(k.storeKey)
if !store.Has(types.TokenKey(k.getContractID(ctx))) {
return sdkerrors.Wrapf(types.ErrTokenNotExist, "ContractID: %s", k.getContractID(ctx))
}
approvedKey := types.TokenApprovedKey(k.getContractID(ctx), proxy, approver)
if store.Has(approvedKey) {
return sdkerrors.Wrapf(types.ErrTokenAlreadyApproved, "Proxy: %s, Approver: %s, ContractID: %s", proxy.String(), approver.String(), k.getContractID(ctx))
}
store.Set(approvedKey, ApprovedValue)
// Set Account if not exists yet
account := k.accountKeeper.GetAccount(ctx, proxy)
if account == nil {
account = k.accountKeeper.NewAccountWithAddress(ctx, proxy)
k.accountKeeper.SetAccount(ctx, account)
}
ctx.EventManager().EmitEvents(sdk.Events{
sdk.NewEvent(
types.EventTypeApproveToken,
sdk.NewAttribute(types.AttributeKeyContractID, k.getContractID(ctx)),
sdk.NewAttribute(types.AttributeKeyProxy, proxy.String()),
sdk.NewAttribute(types.AttributeKeyApprover, approver.String()),
),
})
return nil
}
func (k Keeper) GetApprovers(ctx sdk.Context, proxy sdk.AccAddress) (accAds []sdk.AccAddress, err error) {
_, err = k.GetToken(ctx)
if err != nil {
return nil, err
}
k.iterateApprovers(ctx, proxy, false, func(address sdk.AccAddress) bool {
accAds = append(accAds, address)
return false
})
return accAds, nil
}
func (k Keeper) iterateApprovers(ctx sdk.Context, prefix sdk.AccAddress, reverse bool, process func(accAd sdk.AccAddress) bool) {
store := ctx.KVStore(k.storeKey)
prefixKey := types.TokenApproversKey(k.getContractID(ctx), prefix)
var iter sdk.Iterator
if reverse {
iter = sdk.KVStoreReversePrefixIterator(store, prefixKey)
} else {
iter = sdk.KVStorePrefixIterator(store, prefixKey)
}
defer iter.Close()
for {
if !iter.Valid() {
return
}
bz := iter.Key()
approver := bz[len(prefixKey):]
if process(approver) {
return
}
iter.Next()
}
}