Fix review comments

This commit is contained in:
Tomasz Bekas 2024-01-10 16:54:14 +01:00
parent 0d1ca4b2cd
commit 3c4daf4198
5 changed files with 28 additions and 12 deletions

View File

@ -13,7 +13,7 @@ jobs:
fail-fast: false fail-fast: false
matrix: matrix:
cache_nonce: [ 1 ] cache_nonce: [ 1 ]
nim_version: [ 1.6.16 ] nim_version: [ 1.6.18 ]
platform: platform:
- { - {
icon: 🐧, icon: 🐧,

View File

@ -13,7 +13,7 @@ push: {.upraises: [].}
type type
BatchEntry* = tuple[key: Key, data: seq[byte]] BatchEntry* = tuple[key: Key, data: seq[byte]]
Function*[T, U] = proc(value: T): U {.upraises: [CatchableError], gcsafe, closure.} Function*[T, U] = proc(value: T): U {.raises: [CatchableError], gcsafe, closure.}
Modify* = Function[?seq[byte], Future[?seq[byte]]] Modify* = Function[?seq[byte], Future[?seq[byte]]]
ModifyGet* = Function[?seq[byte], Future[(?seq[byte], seq[byte])]] ModifyGet* = Function[?seq[byte], Future[(?seq[byte], seq[byte])]]

View File

@ -46,7 +46,7 @@ proc defaultModifyGetImpl*(
finally: finally:
lock.release() lock.release()
method defaultModifyImpl*( proc defaultModifyImpl*(
self: Datastore, self: Datastore,
lock: AsyncLock, lock: AsyncLock,
key: Key, key: Key,

View File

@ -1,5 +1,6 @@
import std/os import std/os
import std/options import std/options
import std/tables
import std/strutils import std/strutils
import pkg/chronos import pkg/chronos
@ -20,7 +21,7 @@ type
root*: string root*: string
ignoreProtected: bool ignoreProtected: bool
depth: int depth: int
lock: AsyncLock locks: TableRef[Key, AsyncLock]
proc validDepth*(self: FSDatastore, key: Key): bool = proc validDepth*(self: FSDatastore, key: Key): bool =
key.len <= self.depth key.len <= self.depth
@ -222,14 +223,26 @@ method query*(
method modifyGet*( method modifyGet*(
self: FSDatastore, self: FSDatastore,
key: Key, key: Key,
fn: ModifyGet): Future[?!seq[byte]] = fn: ModifyGet): Future[?!seq[byte]] {.async.} =
defaultModifyGetImpl(self, self.lock, key, fn) var lock: AsyncLock
try:
lock = self.locks.mgetOrPut(key, newAsyncLock())
return await defaultModifyGetImpl(self, lock, key, fn)
finally:
if not lock.locked:
self.locks.del(key)
method modify*( method modify*(
self: FSDatastore, self: FSDatastore,
key: Key, key: Key,
fn: Modify): Future[?!void] = fn: Modify): Future[?!void] {.async.} =
defaultModifyImpl(self, self.lock, key, fn) var lock: AsyncLock
try:
lock = self.locks.mgetOrPut(key, newAsyncLock())
return await defaultModifyImpl(self, lock, key, fn)
finally:
if not lock.locked:
self.locks.del(key)
proc new*( proc new*(
T: type FSDatastore, T: type FSDatastore,
@ -250,4 +263,5 @@ proc new*(
root: root, root: root,
ignoreProtected: ignoreProtected, ignoreProtected: ignoreProtected,
depth: depth, depth: depth,
lock: newAsyncLock()) locks: newTable[Key, AsyncLock]()
)

View File

@ -19,7 +19,9 @@ proc modifyTests*(
randomize() randomize()
let processCount = 100 let
processCount = 100
timeout = (1 + processCount div 10).seconds
proc withRandDelay(op: Future[?!void]): Future[void] {.async: (raises: [Exception]).} = proc withRandDelay(op: Future[?!void]): Future[void] {.async: (raises: [Exception]).} =
await sleepAsync(rand(processCount).millis) await sleepAsync(rand(processCount).millis)
@ -53,7 +55,7 @@ proc modifyTests*(
return success() return success()
let futs = newSeqWith(processCount, withRandDelay(getIncAndPut())) let futs = newSeqWith(processCount, withRandDelay(getIncAndPut()))
await allFutures(futs).wait(10.seconds) await allFutures(futs).wait(timeout)
let finalValue = uint64.fromBytes((await ds.get(key)).tryGet) let finalValue = uint64.fromBytes((await ds.get(key)).tryGet)
@ -63,7 +65,7 @@ proc modifyTests*(
(await ds.put(key, @(0.uint64.toBytes))).tryGet (await ds.put(key, @(0.uint64.toBytes))).tryGet
let futs = newSeqWith(processCount, withRandDelay(ds.modify(key, incAsyncFn))) let futs = newSeqWith(processCount, withRandDelay(ds.modify(key, incAsyncFn)))
await allFutures(futs).wait(10.seconds) await allFutures(futs).wait(timeout)
let finalValue = uint64.fromBytes((await ds.get(key)).tryGet) let finalValue = uint64.fromBytes((await ds.get(key)).tryGet)