github.com/onflow/flow-go@v0.35.7-crescendo-preview.23-atree-inlining/module/blobs/blob_store.go (about) 1 package blobs 2 3 import ( 4 "context" 5 "errors" 6 7 "github.com/ipfs/boxo/blockstore" 8 "github.com/ipfs/go-cid" 9 "github.com/ipfs/go-datastore" 10 ipld "github.com/ipfs/go-ipld-format" 11 ) 12 13 type Blobstore interface { 14 DeleteBlob(context.Context, cid.Cid) error 15 Has(context.Context, cid.Cid) (bool, error) 16 Get(context.Context, cid.Cid) (Blob, error) 17 18 // GetSize returns the CIDs mapped BlobSize 19 GetSize(context.Context, cid.Cid) (int, error) 20 21 // Put puts a given blob to the underlying datastore 22 Put(context.Context, Blob) error 23 24 // PutMany puts a slice of blobs at the same time using batching 25 // capabilities of the underlying datastore whenever possible. 26 PutMany(context.Context, []Blob) error 27 28 // AllKeysChan returns a channel from which 29 // the CIDs in the Blobstore can be read. It should respect 30 // the given context, closing the channel if it becomes Done. 31 AllKeysChan(ctx context.Context) (<-chan cid.Cid, error) 32 33 // HashOnRead specifies if every read blob should be 34 // rehashed to make sure it matches its CID. 35 HashOnRead(enabled bool) 36 } 37 38 var ErrNotFound = errors.New("blobstore: blob not found") 39 40 type blobstoreImpl struct { 41 bs blockstore.Blockstore 42 } 43 44 func NewBlobstore(ds datastore.Batching) *blobstoreImpl { 45 return &blobstoreImpl{bs: blockstore.NewBlockstore(ds)} 46 } 47 48 func (bs *blobstoreImpl) DeleteBlob(ctx context.Context, c cid.Cid) error { 49 return bs.bs.DeleteBlock(ctx, c) 50 } 51 52 func (bs *blobstoreImpl) Has(ctx context.Context, c cid.Cid) (bool, error) { 53 return bs.bs.Has(ctx, c) 54 } 55 56 func (bs *blobstoreImpl) Get(ctx context.Context, c cid.Cid) (Blob, error) { 57 blob, err := bs.bs.Get(ctx, c) 58 if ipld.IsNotFound(err) { 59 return nil, ErrNotFound 60 } 61 62 return blob, err 63 } 64 65 func (bs *blobstoreImpl) GetSize(ctx context.Context, c cid.Cid) (int, error) { 66 return bs.bs.GetSize(ctx, c) 67 } 68 69 func (bs *blobstoreImpl) Put(ctx context.Context, blob Blob) error { 70 return bs.bs.Put(ctx, blob) 71 } 72 73 func (bs *blobstoreImpl) PutMany(ctx context.Context, blobs []Blob) error { 74 return bs.bs.PutMany(ctx, blobs) 75 } 76 77 func (bs *blobstoreImpl) AllKeysChan(ctx context.Context) (<-chan cid.Cid, error) { 78 return bs.bs.AllKeysChan(ctx) 79 } 80 81 func (bs *blobstoreImpl) HashOnRead(enabled bool) { 82 bs.bs.HashOnRead(enabled) 83 } 84 85 // NoopBlobstore is a Blobstore that does nothing, which is useful for calculating 86 // BlockExecutionData IDs without storing the data. 87 type NoopBlobstore struct{} 88 89 func NewNoopBlobstore() *NoopBlobstore { 90 return &NoopBlobstore{} 91 } 92 93 func (n *NoopBlobstore) DeleteBlob(context.Context, cid.Cid) error { 94 return nil 95 } 96 97 func (n *NoopBlobstore) Has(context.Context, cid.Cid) (bool, error) { 98 return false, nil 99 } 100 101 func (n *NoopBlobstore) Get(context.Context, cid.Cid) (Blob, error) { 102 return nil, nil 103 } 104 105 func (n *NoopBlobstore) GetSize(context.Context, cid.Cid) (int, error) { 106 return 0, nil 107 } 108 109 func (n *NoopBlobstore) Put(context.Context, Blob) error { 110 return nil 111 } 112 113 func (n *NoopBlobstore) PutMany(context.Context, []Blob) error { 114 return nil 115 } 116 117 func (n *NoopBlobstore) AllKeysChan(ctx context.Context) (<-chan cid.Cid, error) { 118 return nil, nil 119 } 120 121 func (n *NoopBlobstore) HashOnRead(enabled bool) {}