github.com/sixexorg/magnetic-ring@v0.0.0-20191119090307-31705a21e419/store/orgchain/storages/vote_store.go (about) 1 package storages 2 3 import ( 4 "bytes" 5 "encoding/binary" 6 7 "fmt" 8 9 "github.com/sixexorg/magnetic-ring/common" 10 "github.com/sixexorg/magnetic-ring/errors" 11 "github.com/sixexorg/magnetic-ring/store/db" 12 "github.com/sixexorg/magnetic-ring/store/storelaw" 13 ) 14 15 // write to db by height 16 type VoteStore struct { 17 dbDir string 18 store *db.LevelDBStore 19 votePrefix byte 20 recordPrefix byte 21 } 22 23 func NewVoteStore(dbDir string, votePrefix, recordPrefix byte) (*VoteStore, error) { 24 var err error 25 store, err := db.NewLevelDBStore(dbDir) 26 if err != nil { 27 return nil, err 28 } 29 voteStore := &VoteStore{ 30 dbDir: dbDir, 31 store: store, 32 votePrefix: votePrefix, 33 recordPrefix: recordPrefix, 34 } 35 return voteStore, nil 36 } 37 38 func (this *VoteStore) NewBatch() { 39 this.store.NewBatch() 40 } 41 func (this *VoteStore) CommitTo() error { 42 return this.store.BatchCommit() 43 } 44 45 func (this *VoteStore) GetVoteState(voteId common.Hash, height uint64) (*storelaw.VoteState, error) { 46 fmt.Printf("⭕️ vote store get voteId:%s height:%d\n", voteId.String(), height) 47 key := this.getKey(voteId, height) 48 iter := this.store.NewIterator(nil) 49 flag := true 50 buff := bytes.NewBuffer(nil) 51 if iter.Seek(key) { 52 if bytes.Compare(iter.Key(), key) == 0 { 53 buff.Write(iter.Key()[1:]) 54 buff.Write(iter.Value()) 55 flag = false 56 } 57 } 58 if flag && iter.Prev() { 59 buff.Write(iter.Key()[1:]) 60 buff.Write(iter.Value()) 61 } 62 iter.Release() 63 err := iter.Error() 64 if err != nil { 65 return nil, err 66 } 67 vs := &storelaw.VoteState{} 68 err = vs.Deserialize(buff) 69 if err != nil { 70 return nil, err 71 } 72 if bytes.Equal(vs.VoteId[:], voteId[:]) { 73 return vs, nil 74 } 75 return nil, errors.ERR_DB_NOT_FOUND 76 } 77 78 func (this *VoteStore) SaveVotes(vs []*storelaw.VoteState) { 79 for _, v := range vs { 80 fmt.Printf("⭕️ vote store save voteId:%s height:%d\n", v.VoteId.String(), v.Height) 81 key := this.getKey(v.VoteId, v.Height) 82 val := v.GetVal() 83 this.store.BatchPut(key, val) 84 } 85 } 86 87 func (this *VoteStore) AlreadyVoted(voteId common.Hash, account common.Address) bool { 88 key := this.getAccountKey(voteId, account) 89 _, err := this.store.Get(key) 90 if err != nil { 91 return false 92 } 93 return true 94 } 95 func (this *VoteStore) SaveAccountVoted(avs []*storelaw.AccountVoted, height uint64) { 96 for _, v := range avs { 97 for _, vi := range v.Accounts { 98 key := this.getAccountKey(v.VoteId, vi) 99 100 val := make([]byte, 8) 101 binary.LittleEndian.PutUint64(val, height) 102 this.store.BatchPut(key, val) 103 } 104 } 105 } 106 107 func (this *VoteStore) getKey(voteId common.Hash, height uint64) []byte { 108 buff := make([]byte, 1+common.HashLength+8) 109 buff[0] = this.votePrefix 110 copy(buff[1:common.HashLength+1], voteId[:]) 111 binary.LittleEndian.PutUint64(buff[common.HashLength+1:], height) 112 return buff 113 } 114 func (this *VoteStore) getAccountKey(voteId common.Hash, account common.Address) []byte { 115 buff := make([]byte, 1+common.HashLength+common.AddrLength) 116 buff[0] = this.recordPrefix 117 copy(buff[1:common.HashLength+1], voteId[:]) 118 copy(buff[common.HashLength+1:], account[:]) 119 return buff 120 }