From 6113019f158f99fd6b3cebffb0a2c343a9da3691 Mon Sep 17 00:00:00 2001 From: Emery Hemingway Date: Mon, 18 Mar 2019 21:50:58 +0100 Subject: [PATCH] Add "contains" to store interface --- src/blobsets.nim | 22 ++++++++++++---------- src/blobsets/filestores.nim | 11 +++++++++++ src/blobsets/httpstores.nim | 12 ++++++++++++ 3 files changed, 35 insertions(+), 10 deletions(-) diff --git a/src/blobsets.nim b/src/blobsets.nim index c010fbf..2d57c32 100644 --- a/src/blobsets.nim +++ b/src/blobsets.nim @@ -264,6 +264,7 @@ func toCbor*(x: BlobSet): CborNode = assert(bitmap.getInt.uint64 == x.bitmap, $bitmap.getInt.uint64 & " != " & $x.bitmap) array.add bitmap for y in x.table: + assert(not y.isNil) array.add y.toCbor newCborTag(nodeTag, array) of coldNode: @@ -624,20 +625,21 @@ proc commit*(store: BlobStore; bs: BlobSet): Future[BlobSet] {.async.} = if bs.isCold: return bs let tmp = BlobSet(kind: hotNode, bitmap: bs.bitmap, table: bs.table) for e in tmp.table.mitems: - if e.isHot: e = await store.commit e + if e.isHot: + let cold = await store.commit e + assert(not cold.isNil) + e = cold var buf = encode tmp.toCbor - #let - # localId = blobHash(buf) - #echo "check if store has ", localId.toHex - #let - # present = await store.contains(localId, metaBlob) - #echo "check returned ", present - #if not present: - block: + let + localId = blobHash(buf) + present = await store.contains(localId, metaBlob) + if present: + return BlobSet(kind: coldNode, setId: localId) + else: let stream = store.openIngestStream(size=buf.len, kind=metaBlob) await stream.ingest(buf) let (storeId, _) = await finish(stream) - #assert(localId == storeId) + assert(localId == storeId) return BlobSet(kind: coldNode, setId: storeId) # diff --git a/src/blobsets/filestores.nim b/src/blobsets/filestores.nim index e209e3c..0b35b82 100644 --- a/src/blobsets/filestores.nim +++ b/src/blobsets/filestores.nim @@ -129,6 +129,16 @@ proc fsOpenIngestStream(s: BlobStore; size: BiggestInt; kind: BlobKind): IngestS stream.leaves = newSeq[BlobId]() stream +proc fsContains(s: BlobStore; id: BlobId; kind: BlobKind): Future[bool] = + var fs = FileStore(s) + result = newFuture[bool]("blobsets.filestores.fsContains") + let path = fs.root / $kind / id.toHex + try: + close(openAsync(path, fmRead)) + result.complete(true) + except: + result.complete(false) + proc newFileStore*(root: string): BlobStore = ## Create a new store object backed by a file-system. try: @@ -136,6 +146,7 @@ proc newFileStore*(root: string): BlobStore = createDir(root / $metaBlob) except: discard FileStore( + containsImpl: fsContains, openBlobStreamImpl: fsOpenBlobStream, openIngestStreamImpl: fsOpenIngestStream, root: root, diff --git a/src/blobsets/httpstores.nim b/src/blobsets/httpstores.nim index dc09a97..b860d7c 100644 --- a/src/blobsets/httpstores.nim +++ b/src/blobsets/httpstores.nim @@ -113,9 +113,21 @@ proc httpCloseStore(s: BlobStore) = var s = HttpStore(s) close s.client +proc httpContains(s: BlobStore; id: BlobId; kind: BlobKind): Future[bool] {.async.} = + var s = HttpStore(s) + try: + let + url = $((s.url / $kind) / id.toHex) + resp = await s.client.request(url, HttpHEAD) + return (resp.code in {Http200, Http204}) + except: + close s.client + return false + proc newHttpStore*(url: string): HttpStore = HttpStore( closeImpl: httpCloseStore, + containsImpl: httpContains, openBlobStreamImpl: httpOpenBlobStream, openIngestStreamImpl: httpOpenIngestStream, client: newAsyncHttpClient(),