The following is Sample codes for a first look at py-mdbm
Creating and populating a database
Python 2 or higher
importmdbmimportrandomprint("[*] Creating and populating a database")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRflags=flags|mdbm.MDBM_O_CREATflags=flags|mdbm.MDBM_LARGE_OBJECTSflags=flags|mdbm.MDBM_ANY_LOCKSflags=flags|mdbm.MDBM_O_TRUNCmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
foriinrange(0, 65535):
k=str(i)
v=str(random.randrange(0, 65535))
rv=dbm.store(k, v, mdbm.MDBM_INSERT)
ifnotrv:
print("[-] failed to data store to ", path)
breakprint("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Python 3 or higher
# encoding: utf-8importmdbmimportrandomprint("[*] Creating and populating a database")
path="/tmp/test1-byte.mdbm"flags=mdbm.MDBM_O_RDWRflags=flags|mdbm.MDBM_O_CREATflags=flags|mdbm.MDBM_LARGE_OBJECTSflags=flags|mdbm.MDBM_ANY_LOCKSflags=flags|mdbm.MDBM_O_TRUNCmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
print("|--------|-------|")
print("| key | val |")
print("|--------|-------|")
# byteforiinrange(0, 10):
k=bytes(str(i), 'utf-8')
v=bytes(str(random.randrange(0, 65535)), 'utf-8')
print("|%08s|%08s|"% (k, v))
rv=dbm.store(k, v, mdbm.MDBM_INSERT|mdbm.MDBM_CACHE_MODIFY)
ifnotrv:
print("[-] failed to data store to ", path)
break# stringforiinrange(10, 20):
k=str(i)
v=str(random.randrange(0, 65535))
print("|%08s|%08s|"% (k, v))
rv=dbm.store(k, v, mdbm.MDBM_INSERT|mdbm.MDBM_CACHE_MODIFY)
ifnotrv:
print("[-] failed to data store to ", path)
breakprint("|--------|--------|")
print("[*] count of records : %d"%dbm.count_records())
print("\n")
dbm.close()
Fetching records in-place
importmdbmimportrandomprint("[*] Fetching records in-place")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
dbm.preload()
print("|-------|-------|")
print("| key | val |")
print("|-------|-------|")
foriinrange(0, 10):
k=str(random.randrange(0, 65534))
orgval=dbm.fetch(k)
ifnotorgval:
print("[-] failed to fetch value of %s in mdbm"%k)
breakprint("|%07s|%07s|"% (k, orgval))
print("|-------|-------|")
print("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Fetching and updating records in-place
importmdbmimportrandomprint("[*] Fetching and updating records in-place")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
foriinrange(0, 65535):
k=str(i)
v=str(random.randrange(0, 65535))
orgval=dbm.fetch(k)
ifnotorgval:
print("[-] failed to fetch value of %s in mdbm"%k)
breakprint("[=] key(%s) : replace val(%s) to '%s' : "% (k, orgval, v)),
rv=dbm.store(k, v, mdbm.MDBM_REPLACE)
ifnotrv:
print("FAIL")
breakprint("DONE")
print("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Deleting records in-place
importmdbmimportrandomprint("[*] Deleting records in-place")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
foriinrange(0, 10):
k=str(random.randrange(0, 65534))
rv=dbm.delete(k)
ifnotrv:
print("[-] failed to delete an record, key=%s"%k)
v=dbm.fetch(k)
ifv:
print("[-] failed to delete an record, key=%s, val=%s"% (k,v))
breakprint("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Iterating over all records
importmdbmimportrandomprint("[*] Iterating over all records")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
print("|-------|-------|")
print("| key | val |")
print("|-------|-------|")
kv=dbm.first()
print("|%07s|%07s|"%kv)
whilekv:
print("|%07s|%07s|"%kv)
kv=dbm.next()
print("|-------|-------|")
print("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Iterating over all keys
importmdbmimportrandomprint("[*] Iterating over all records")
path="/tmp/test1.mdbm"flags=mdbm.MDBM_O_RDWRmode=0o644# means 0644dbm=mdbm.open(path, flags, mode)
print("|-------|")
print("| key |")
print("|-------|")
k=dbm.firstkey()
print("|%07s|"%k)
whilek:
print("|%07s|"%k)
k=dbm.nextkey()
print("|-------|")
print("[*] count of records : %d"%dbm.count_records())
dbm.close()
print("done")
Iteration over all value by key
importmdbmimportrandomprint("[*] Creating and populating a database")
path="/tmp/test_py_dup.mdbm"flags=mdbm.MDBM_O_RDWRflags=flags|mdbm.MDBM_O_CREATflags=flags|mdbm.MDBM_LARGE_OBJECTSflags=flags|mdbm.MDBM_ANY_LOCKSflags=flags|mdbm.MDBM_O_TRUNCmode=0o644# means 0644withmdbm.open(path, flags, mode) asdbm:
forkinrange(0, 100):
key=str(k)
foriinrange(1, 12):
val=str(123*i)
rv=dbm.store(key, val, mdbm.MDBM_INSERT_DUP)
ifnotrv:
print("[-] failed to data store to ", path)
breakprint("[*] Loop through DB, looking at records with the same key.")
withmdbm.open(path, mdbm.MDBM_O_RDONLY, mode) asdbm:
print("[*] count of records : %d"%dbm.count_records())
print("|-------|-------|")
print("| key | val |")
print("|-------|-------|")
k=str(random.randrange(0, 99))
empty_iter=dbm.init_iter()
info=dbm.fetch_dup_r(k, empty_iter)
whileinfo:
print("|%07s|%07s|"% (k, info['val']))
info=dbm.fetch_dup_r(k, info['iter'])
print("|-------|-------|")
print("done")
Benchmark
The following is results of Py-mdbm vs AnyDBM vs SQLite3 vs Kyotocabinet benchmarks for simple data storing and random fetching in them.
Program terminated with signal SIGSEGV, Segmentation fault.
warning: Unexpected size of section `.reg-xstate/25978' in core file.
#0 0x000055c0c62db2a4 in visit_decref (op=0x7fb27f77d378, data=data@entry=0x0) at Modules/gcmodule.c:360
360 if (PyObject_IS_GC(op)) {
(gdb) bt
#0 0x000055c0c62db2a4 in visit_decref (op=0x7fb27f77d378, data=data@entry=0x0) at Modules/gcmodule.c:360
#1 0x000055c0c632b74b in frame_traverse (f=0x55c0c70428a0, visit=0x55c0c62db250 <visit_decref>, arg=0x0) at Objects/frameobject.c:510
#2 0x000055c0c62d9cd4 in subtract_refs (containers=<optimized out>) at Modules/gcmodule.c:385
#3 collect (generation=0) at Modules/gcmodule.c:925
#4 0x000055c0c62db8f7 in collect_generations () at Modules/gcmodule.c:1050
#5 _PyObject_GC_Malloc (basicsize=<optimized out>) at Modules/gcmodule.c:1511
#6 _PyObject_GC_New (tp=tp@entry=0x55c0c65d5da0 <PyListIter_Type>) at Modules/gcmodule.c:1521
#7 0x000055c0c61c8191 in list_iter (seq=0x7fb279aa2a70) at Objects/listobject.c:2879
#8 0x000055c0c6191254 in PyObject_GetIter (o=o@entry=0x7fb279aa2a70) at Objects/abstract.c:3097
#9 0x000055c0c6273fbc in PyEval_EvalFrameEx (f=f@entry=0x7fb279454620, throwflag=throwflag@entry=0) at Python/ceval.c:2797
#10 0x000055c0c627c93e in fast_function (nk=<optimized out>, na=<optimized out>, n=1, pp_stack=0x7fffd3835ad8, func=0x7fb27d1be320) at Python/ceval.c:4442
Hi, thank you for this package.
When trying to store byte-string: dbm.store(b"key2", b"binary vale", mdbm.MDBM_INSERT)
I get following error: mdbm.Error: Error - There was a missing parameter: key and value from here.
It would be good if byte-strings were supported too.