kvstore: simplified stmt exec iterator (#467)

This commit is contained in:
Jacek Sieka 2022-01-28 14:23:41 +01:00 committed by GitHub
parent 5791afccc3
commit ce4acc168c
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 50 additions and 0 deletions

View File

@ -211,6 +211,48 @@ proc exec*[Params, Res](s: SqliteStmt[Params, Res],
discard sqlite3_reset(s) # same return information as step
discard sqlite3_clear_bindings(s) # no errors possible
iterator exec*[Params, Res](s: SqliteStmt[Params, Res],
params: Params, item: var Res): KvResult[void] =
let s = RawStmtPtr s
# we use a mutable `res` variable here to avoid the code bloat that multiple
# `yield` statements cause when inlining the loop body
var res = KvResult[void].ok()
when params is tuple:
var i = 1
for param in fields(params):
if (let v = bindParam(s, i, param); v != SQLITE_OK):
res = KvResult[void].err($sqlite3_errstr(v))
break
inc i
else:
if (let v = bindParam(s, 1, params); v != SQLITE_OK):
res = KvResult[void].err($sqlite3_errstr(v))
defer:
# release implicit transaction
discard sqlite3_reset(s) # same return information as step
discard sqlite3_clear_bindings(s) # no errors possible
while res.isOk():
let v = sqlite3_step(s)
case v
of SQLITE_ROW:
item = readResult(s, Res)
yield KvResult[void].ok()
of SQLITE_DONE:
break
else:
res = KvResult[void].err($sqlite3_errstr(v))
if not res.isOk():
yield res
iterator exec*[Res](s: SqliteStmt[NoParams, Res], item: var Res): KvResult[void] =
for r in exec(s, (), item):
yield r
template exec*(s: SqliteStmt[NoParams, void]): KvResult[void] =
exec(s, ())

View File

@ -225,3 +225,11 @@ procSuite "SqStoreRef":
check:
selectRes.isOk and selectRes.get == true
abc == val
var found = false
var row: selectStmt.Result
for rowRes in selectStmt.exec(row):
rowRes.expect("working db")
check abc == row
found = true
check found