7 dbm "github.com/bytom/bytom/database/leveldb"
8 chainjson "github.com/bytom/bytom/encoding/json"
9 "github.com/bytom/bytom/errors"
13 userContractPrefix = []byte("UC:")
16 // pre-define errors for supporting bytom errorFormatter
18 ErrContractDuplicated = errors.New("contract is duplicated")
19 ErrContractNotFound = errors.New("contract not found")
22 // userContractKey return user contract key
23 func userContractKey(hash chainjson.HexBytes) []byte {
24 return append(userContractPrefix, hash[:]...)
27 // Registry tracks and stores all user contract.
28 type Registry struct {
33 //NewRegistry create new registry
34 func NewRegistry(db dbm.DB) *Registry {
40 //Contract describe user contract
41 type Contract struct {
42 Hash chainjson.HexBytes `json:"id"`
43 Alias string `json:"alias"`
44 Contract chainjson.HexBytes `json:"contract"`
45 CallProgram chainjson.HexBytes `json:"call_program"`
46 RegisterProgram chainjson.HexBytes `json:"register_program"`
49 // SaveContract save user contract
50 func (reg *Registry) SaveContract(contract *Contract) error {
52 defer reg.contractMu.Unlock()
54 contractKey := userContractKey(contract.Hash)
55 if existContract := reg.db.Get(contractKey); existContract != nil {
56 return ErrContractDuplicated
59 rawContract, err := json.Marshal(contract)
64 reg.db.Set(contractKey, rawContract)
68 //UpdateContract updates user contract alias
69 func (reg *Registry) UpdateContract(hash chainjson.HexBytes, alias string) error {
71 defer reg.contractMu.Unlock()
73 contract, err := reg.GetContract(hash)
78 contract.Alias = alias
79 rawContract, err := json.Marshal(contract)
84 reg.db.Set(userContractKey(hash), rawContract)
88 // GetContract get user contract
89 func (reg *Registry) GetContract(hash chainjson.HexBytes) (*Contract, error) {
90 contract := &Contract{}
91 if rawContract := reg.db.Get(userContractKey(hash)); rawContract != nil {
92 return contract, json.Unmarshal(rawContract, contract)
94 return nil, ErrContractNotFound
97 // ListContracts returns user contracts
98 func (reg *Registry) ListContracts() ([]*Contract, error) {
99 contracts := []*Contract{}
100 contractIter := reg.db.IteratorPrefix(userContractPrefix)
101 defer contractIter.Release()
103 for contractIter.Next() {
104 contract := &Contract{}
105 if err := json.Unmarshal(contractIter.Value(), contract); err != nil {
109 contracts = append(contracts, contract)
111 return contracts, nil