github.com/onflow/flow-go@v0.35.7-crescendo-preview.23-atree-inlining/storage/badger/qcs.go (about) 1 package badger 2 3 import ( 4 "github.com/dgraph-io/badger/v2" 5 6 "github.com/onflow/flow-go/model/flow" 7 "github.com/onflow/flow-go/module" 8 "github.com/onflow/flow-go/module/metrics" 9 "github.com/onflow/flow-go/storage" 10 "github.com/onflow/flow-go/storage/badger/operation" 11 "github.com/onflow/flow-go/storage/badger/transaction" 12 ) 13 14 // QuorumCertificates implements persistent storage for quorum certificates. 15 type QuorumCertificates struct { 16 db *badger.DB 17 cache *Cache[flow.Identifier, *flow.QuorumCertificate] 18 } 19 20 var _ storage.QuorumCertificates = (*QuorumCertificates)(nil) 21 22 // NewQuorumCertificates Creates QuorumCertificates instance which is a database of quorum certificates 23 // which supports storing, caching and retrieving by block ID. 24 func NewQuorumCertificates(collector module.CacheMetrics, db *badger.DB, cacheSize uint) *QuorumCertificates { 25 store := func(_ flow.Identifier, qc *flow.QuorumCertificate) func(*transaction.Tx) error { 26 return transaction.WithTx(operation.InsertQuorumCertificate(qc)) 27 } 28 29 retrieve := func(blockID flow.Identifier) func(tx *badger.Txn) (*flow.QuorumCertificate, error) { 30 return func(tx *badger.Txn) (*flow.QuorumCertificate, error) { 31 var qc flow.QuorumCertificate 32 err := operation.RetrieveQuorumCertificate(blockID, &qc)(tx) 33 return &qc, err 34 } 35 } 36 37 return &QuorumCertificates{ 38 db: db, 39 cache: newCache[flow.Identifier, *flow.QuorumCertificate](collector, metrics.ResourceQC, 40 withLimit[flow.Identifier, *flow.QuorumCertificate](cacheSize), 41 withStore(store), 42 withRetrieve(retrieve)), 43 } 44 } 45 46 func (q *QuorumCertificates) StoreTx(qc *flow.QuorumCertificate) func(*transaction.Tx) error { 47 return q.cache.PutTx(qc.BlockID, qc) 48 } 49 50 func (q *QuorumCertificates) ByBlockID(blockID flow.Identifier) (*flow.QuorumCertificate, error) { 51 tx := q.db.NewTransaction(false) 52 defer tx.Discard() 53 return q.retrieveTx(blockID)(tx) 54 } 55 56 func (q *QuorumCertificates) retrieveTx(blockID flow.Identifier) func(*badger.Txn) (*flow.QuorumCertificate, error) { 57 return func(tx *badger.Txn) (*flow.QuorumCertificate, error) { 58 val, err := q.cache.Get(blockID)(tx) 59 if err != nil { 60 return nil, err 61 } 62 return val, nil 63 } 64 }