OSDN Git Service

test(bcrp): add unit test of saveContractView and deleteContractView (#1878)
[bytom/bytom.git] / database / contract_view_test.go
1 package database
2
3 import (
4         "bytes"
5         "encoding/hex"
6         "os"
7         "testing"
8
9         "github.com/google/uuid"
10
11         "github.com/bytom/bytom/crypto/sha3pool"
12         dbm "github.com/bytom/bytom/database/leveldb"
13         "github.com/bytom/bytom/protocol/bc"
14         "github.com/bytom/bytom/protocol/state"
15 )
16
17 var (
18         program, _ = hex.DecodeString("6a4c04626372704c01014c2820e9108d3ca8049800727f6a3505b3a2710dc579405dde03c250f16d9a7e1e6e787403ae7cac00c0")
19         hash       [32]byte
20         txID1      = &bc.Hash{V0: 1, V1: 1, V2: 1, V3: 1}
21         txID2      = &bc.Hash{V0: 2, V1: 2, V2: 2, V3: 2}
22 )
23
24 func init() {
25         sha3pool.Sum256(hash[:], program)
26 }
27
28 // register contract by transaction 1
29 func registerContract(testDB dbm.DB) {
30         contractView := state.NewContractViewpoint()
31         contractView.AttachEntries[hash] = append(txID1.Bytes(), program...)
32         if err := setContractView(testDB, contractView); err != nil {
33                 panic(err)
34         }
35 }
36
37 func setContractView(testDB dbm.DB, contractView *state.ContractViewpoint) error {
38         batch := testDB.NewBatch()
39         if err := deleteContractView(testDB, batch, contractView); err != nil {
40                 return err
41         }
42
43         if err := saveContractView(testDB, batch, contractView); err != nil {
44                 return err
45         }
46
47         batch.Write()
48         return nil
49 }
50
51 func assertDBContractData(testDB dbm.DB, txID *bc.Hash, t *testing.T) {
52         data := testDB.Get(CalcContractKey(hash))
53         if data == nil {
54                 t.Errorf("can't find the registered contract by contract hash %v", hash)
55         }
56
57         expect := append(txID.Bytes(), program...)
58         if !bytes.Equal(data, expect) {
59                 t.Errorf("got contract data: %v, expect contract data: %v", data, expect)
60         }
61 }
62
63 func TestRollback(t *testing.T) {
64         dbName := uuid.New().String()
65         testDB := dbm.NewDB(dbName, "leveldb", dbName)
66         registerContract(testDB)
67         defer os.RemoveAll(dbName)
68
69         contractView := state.NewContractViewpoint()
70         // rollback
71         contractView.DetachEntries[hash] = append(txID1.Bytes(), program...)
72         if err := setContractView(testDB, contractView); err != nil {
73                 t.Errorf("set contract view failed")
74         }
75
76         data := testDB.Get(CalcContractKey(hash))
77         if data != nil {
78                 t.Errorf("registered contract should be deleted")
79         }
80 }
81
82 func TestRollbackAndRegisterAgain(t *testing.T) {
83         dbName := uuid.New().String()
84         testDB := dbm.NewDB(dbName, "leveldb", dbName)
85         registerContract(testDB)
86         defer os.RemoveAll(dbName)
87
88         contractView := state.NewContractViewpoint()
89         // rollback
90         contractView.DetachEntries[hash] = append(txID1.Bytes(), program...)
91         // register again
92         contractView.AttachEntries[hash] = append(txID1.Bytes(), program...)
93         if err := setContractView(testDB, contractView); err != nil {
94                 t.Errorf("set contract view failed")
95         }
96
97         assertDBContractData(testDB, txID1, t)
98 }
99
100 func TestRollbackAndRegisterByAnotherTx(t *testing.T) {
101         dbName := uuid.New().String()
102         testDB := dbm.NewDB(dbName, "leveldb", dbName)
103         registerContract(testDB)
104         defer os.RemoveAll(dbName)
105
106         contractView := state.NewContractViewpoint()
107         // rollback
108         contractView.DetachEntries[hash] = append(txID1.Bytes(), program...)
109         // register by another transaction
110         contractView.AttachEntries[hash] = append(txID2.Bytes(), program...)
111         if err := setContractView(testDB, contractView); err != nil {
112                 t.Errorf("set contract view failed")
113         }
114
115         assertDBContractData(testDB, txID2, t)
116 }
117
118 func TestRepeatRegisterAndRollback(t *testing.T) {
119         dbName := uuid.New().String()
120         testDB := dbm.NewDB(dbName, "leveldb", dbName)
121         registerContract(testDB)
122         defer os.RemoveAll(dbName)
123
124         // repeat register
125         contractView := state.NewContractViewpoint()
126         contractView.AttachEntries[hash] = append(txID2.Bytes(), program...)
127         if err := setContractView(testDB, contractView); err != nil {
128                 t.Errorf("set contract view failed")
129         }
130
131         assertDBContractData(testDB, txID1, t)
132
133         // rollback by repeat register transaction
134         contractView = state.NewContractViewpoint()
135         contractView.DetachEntries[hash] = append(txID2.Bytes(), program...)
136         if err := setContractView(testDB, contractView); err != nil {
137                 t.Errorf("set contract view failed")
138         }
139
140         assertDBContractData(testDB, txID1, t)
141 }