From f63abb769a5ef820381b09da59a6c024ef2f31a7 Mon Sep 17 00:00:00 2001 From: Xie Yanbo Date: Sat, 16 Nov 2019 17:42:40 +0800 Subject: [PATCH 1/3] Iterates with the prefix of keys --- src/leveldb.nim | 7 ++++++- tests/test.nim | 5 +++++ 2 files changed, 11 insertions(+), 1 deletion(-) diff --git a/src/leveldb.nim b/src/leveldb.nim index e50eddd..508ad3d 100644 --- a/src/leveldb.nim +++ b/src/leveldb.nim @@ -1,4 +1,4 @@ -import options, leveldb/raw +import options, strutils, leveldb/raw type LevelDb* = ref object @@ -122,6 +122,11 @@ iterator iter*(self: LevelDb, seek: string = "", reverse: bool = false): ( else: leveldb_iter_next(iterPtr) +iterator iterPrefix*(self: LevelDb, prefix: string = ""): (string, string) = + for (key, value) in iter(self, prefix): + if key.startsWith(prefix): + yield (key, value) + proc removeDb*(name: string) = var err: cstring = nil let options = leveldb_options_create() diff --git a/tests/test.nim b/tests/test.nim index 8bb8f3d..5d587cb 100644 --- a/tests/test.nim +++ b/tests/test.nim @@ -52,3 +52,8 @@ suite "leveldb": initData(db) check(toSeq(db.iter(seek = "ab", reverse = true)) == @[("ba", "2"), ("aa", "1")]) + + test "iter prefix": + initData(db) + check(toSeq(db.iterPrefix(prefix = "b")) == + @[("ba", "2"), ("bb", "3")]) From 177190b3118a9eb6fcd2f331877949b03e1a47cc Mon Sep 17 00:00:00 2001 From: Xie Yanbo Date: Sat, 16 Nov 2019 17:42:48 +0800 Subject: [PATCH 2/3] Iterates with range of keys --- src/leveldb.nim | 15 +++++++++++++-- tests/test.nim | 10 ++++++++++ 2 files changed, 23 insertions(+), 2 deletions(-) diff --git a/src/leveldb.nim b/src/leveldb.nim index 508ad3d..fe1b4ea 100644 --- a/src/leveldb.nim +++ b/src/leveldb.nim @@ -122,11 +122,22 @@ iterator iter*(self: LevelDb, seek: string = "", reverse: bool = false): ( else: leveldb_iter_next(iterPtr) -iterator iterPrefix*(self: LevelDb, prefix: string = ""): (string, string) = - for (key, value) in iter(self, prefix): +iterator iterPrefix*(self: LevelDb, prefix: string): (string, string) = + for (key, value) in iter(self, prefix, reverse = false): if key.startsWith(prefix): yield (key, value) +iterator iterRange*(self: LevelDb, start, limit: string): (string, string) = + let reverse: bool = limit < start + for (key, value) in iter(self, start, reverse = reverse): + if reverse: + if key < limit: + break + else: + if key > limit: + break + yield (key, value) + proc removeDb*(name: string) = var err: cstring = nil let options = leveldb_options_create() diff --git a/tests/test.nim b/tests/test.nim index 5d587cb..6b614b1 100644 --- a/tests/test.nim +++ b/tests/test.nim @@ -57,3 +57,13 @@ suite "leveldb": initData(db) check(toSeq(db.iterPrefix(prefix = "b")) == @[("ba", "2"), ("bb", "3")]) + + test "iter range": + initData(db) + check(toSeq(db.iterRange(start = "a", limit = "ba")) == + @[("aa", "1"), ("ba", "2")]) + + test "iter range reverse": + initData(db) + check(toSeq(db.iterRange(start = "bb", limit = "b")) == + @[("bb", "3"), ("ba", "2")]) From 9d67cd79c8bc87ad890befc76e9bc40cded880cb Mon Sep 17 00:00:00 2001 From: Xie Yanbo Date: Sat, 16 Nov 2019 19:35:02 +0800 Subject: [PATCH 3/3] fix: stop iter if prefix not matched --- src/leveldb.nim | 2 ++ 1 file changed, 2 insertions(+) diff --git a/src/leveldb.nim b/src/leveldb.nim index fe1b4ea..c82618b 100644 --- a/src/leveldb.nim +++ b/src/leveldb.nim @@ -126,6 +126,8 @@ iterator iterPrefix*(self: LevelDb, prefix: string): (string, string) = for (key, value) in iter(self, prefix, reverse = false): if key.startsWith(prefix): yield (key, value) + else: + break iterator iterRange*(self: LevelDb, start, limit: string): (string, string) = let reverse: bool = limit < start