mdbxmou 0.1.26
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/.github/workflows/ci.yml +32 -0
- package/.github/workflows/publish.yml +27 -0
- package/.gitmodules +3 -0
- package/CMakeLists.txt +53 -0
- package/LICENSE +201 -0
- package/README.md +639 -0
- package/build.js +11 -0
- package/deps/libmdbx/.clang-format +3 -0
- package/deps/libmdbx/.cmake-format.yaml +3 -0
- package/deps/libmdbx/.le.ini +40 -0
- package/deps/libmdbx/CMakeLists.txt +1269 -0
- package/deps/libmdbx/COPYRIGHT +159 -0
- package/deps/libmdbx/ChangeLog.md +2786 -0
- package/deps/libmdbx/GNUmakefile +950 -0
- package/deps/libmdbx/LICENSE +177 -0
- package/deps/libmdbx/Makefile +16 -0
- package/deps/libmdbx/NOTICE +39 -0
- package/deps/libmdbx/README.md +863 -0
- package/deps/libmdbx/TODO.md +43 -0
- package/deps/libmdbx/cmake/compiler.cmake +1221 -0
- package/deps/libmdbx/cmake/profile.cmake +58 -0
- package/deps/libmdbx/cmake/utils.cmake +524 -0
- package/deps/libmdbx/conanfile.py +323 -0
- package/deps/libmdbx/docs/Doxyfile.in +2734 -0
- package/deps/libmdbx/docs/_preface.md +47 -0
- package/deps/libmdbx/docs/_restrictions.md +248 -0
- package/deps/libmdbx/docs/_starting.md +245 -0
- package/deps/libmdbx/docs/_toc.md +34 -0
- package/deps/libmdbx/docs/header.html +96 -0
- package/deps/libmdbx/example/CMakeLists.txt +6 -0
- package/deps/libmdbx/example/README.md +1 -0
- package/deps/libmdbx/example/example-mdbx.c +154 -0
- package/deps/libmdbx/example/sample-bdb.txt +77 -0
- package/deps/libmdbx/mdbx.h +6655 -0
- package/deps/libmdbx/mdbx.h++ +6428 -0
- package/deps/libmdbx/packages/buildroot/0001-package-libmdbx-new-package-library-database.patch +173 -0
- package/deps/libmdbx/src/alloy.c +54 -0
- package/deps/libmdbx/src/api-cold.c +543 -0
- package/deps/libmdbx/src/api-copy.c +912 -0
- package/deps/libmdbx/src/api-cursor.c +754 -0
- package/deps/libmdbx/src/api-dbi.c +315 -0
- package/deps/libmdbx/src/api-env.c +1434 -0
- package/deps/libmdbx/src/api-extra.c +165 -0
- package/deps/libmdbx/src/api-key-transform.c +197 -0
- package/deps/libmdbx/src/api-misc.c +286 -0
- package/deps/libmdbx/src/api-opts.c +575 -0
- package/deps/libmdbx/src/api-range-estimate.c +365 -0
- package/deps/libmdbx/src/api-txn-data.c +454 -0
- package/deps/libmdbx/src/api-txn.c +921 -0
- package/deps/libmdbx/src/atomics-ops.h +364 -0
- package/deps/libmdbx/src/atomics-types.h +97 -0
- package/deps/libmdbx/src/audit.c +109 -0
- package/deps/libmdbx/src/bits.md +34 -0
- package/deps/libmdbx/src/chk.c +1796 -0
- package/deps/libmdbx/src/cogs.c +309 -0
- package/deps/libmdbx/src/cogs.h +506 -0
- package/deps/libmdbx/src/coherency.c +170 -0
- package/deps/libmdbx/src/config.h.in +88 -0
- package/deps/libmdbx/src/cursor.c +2396 -0
- package/deps/libmdbx/src/cursor.h +391 -0
- package/deps/libmdbx/src/dbi.c +717 -0
- package/deps/libmdbx/src/dbi.h +142 -0
- package/deps/libmdbx/src/debug_begin.h +36 -0
- package/deps/libmdbx/src/debug_end.h +15 -0
- package/deps/libmdbx/src/dpl.c +486 -0
- package/deps/libmdbx/src/dpl.h +134 -0
- package/deps/libmdbx/src/dxb.c +1335 -0
- package/deps/libmdbx/src/env.c +607 -0
- package/deps/libmdbx/src/essentials.h +125 -0
- package/deps/libmdbx/src/gc-get.c +1345 -0
- package/deps/libmdbx/src/gc-put.c +970 -0
- package/deps/libmdbx/src/gc.h +40 -0
- package/deps/libmdbx/src/global.c +474 -0
- package/deps/libmdbx/src/internals.h +585 -0
- package/deps/libmdbx/src/layout-dxb.h +288 -0
- package/deps/libmdbx/src/layout-lck.h +289 -0
- package/deps/libmdbx/src/lck-posix.c +859 -0
- package/deps/libmdbx/src/lck-windows.c +607 -0
- package/deps/libmdbx/src/lck.c +174 -0
- package/deps/libmdbx/src/lck.h +110 -0
- package/deps/libmdbx/src/logging_and_debug.c +250 -0
- package/deps/libmdbx/src/logging_and_debug.h +159 -0
- package/deps/libmdbx/src/man1/mdbx_chk.1 +106 -0
- package/deps/libmdbx/src/man1/mdbx_copy.1 +95 -0
- package/deps/libmdbx/src/man1/mdbx_drop.1 +48 -0
- package/deps/libmdbx/src/man1/mdbx_dump.1 +101 -0
- package/deps/libmdbx/src/man1/mdbx_load.1 +105 -0
- package/deps/libmdbx/src/man1/mdbx_stat.1 +86 -0
- package/deps/libmdbx/src/mdbx.c++ +1837 -0
- package/deps/libmdbx/src/meta.c +656 -0
- package/deps/libmdbx/src/meta.h +168 -0
- package/deps/libmdbx/src/mvcc-readers.c +414 -0
- package/deps/libmdbx/src/node.c +365 -0
- package/deps/libmdbx/src/node.h +102 -0
- package/deps/libmdbx/src/ntdll.def +1246 -0
- package/deps/libmdbx/src/options.h +534 -0
- package/deps/libmdbx/src/osal.c +3485 -0
- package/deps/libmdbx/src/osal.h +587 -0
- package/deps/libmdbx/src/page-get.c +483 -0
- package/deps/libmdbx/src/page-iov.c +185 -0
- package/deps/libmdbx/src/page-iov.h +34 -0
- package/deps/libmdbx/src/page-ops.c +744 -0
- package/deps/libmdbx/src/page-ops.h +142 -0
- package/deps/libmdbx/src/pnl.c +236 -0
- package/deps/libmdbx/src/pnl.h +146 -0
- package/deps/libmdbx/src/preface.h +990 -0
- package/deps/libmdbx/src/proto.h +105 -0
- package/deps/libmdbx/src/refund.c +212 -0
- package/deps/libmdbx/src/sort.h +484 -0
- package/deps/libmdbx/src/spill.c +431 -0
- package/deps/libmdbx/src/spill.h +74 -0
- package/deps/libmdbx/src/table.c +107 -0
- package/deps/libmdbx/src/tls.c +551 -0
- package/deps/libmdbx/src/tls.h +43 -0
- package/deps/libmdbx/src/tools/chk.c +673 -0
- package/deps/libmdbx/src/tools/copy.c +166 -0
- package/deps/libmdbx/src/tools/drop.c +199 -0
- package/deps/libmdbx/src/tools/dump.c +515 -0
- package/deps/libmdbx/src/tools/load.c +831 -0
- package/deps/libmdbx/src/tools/stat.c +516 -0
- package/deps/libmdbx/src/tools/wingetopt.c +87 -0
- package/deps/libmdbx/src/tools/wingetopt.h +30 -0
- package/deps/libmdbx/src/tree-ops.c +1554 -0
- package/deps/libmdbx/src/tree-search.c +140 -0
- package/deps/libmdbx/src/txl.c +99 -0
- package/deps/libmdbx/src/txl.h +26 -0
- package/deps/libmdbx/src/txn.c +1083 -0
- package/deps/libmdbx/src/unaligned.h +205 -0
- package/deps/libmdbx/src/utils.c +32 -0
- package/deps/libmdbx/src/utils.h +76 -0
- package/deps/libmdbx/src/version.c.in +44 -0
- package/deps/libmdbx/src/walk.c +290 -0
- package/deps/libmdbx/src/walk.h +20 -0
- package/deps/libmdbx/src/windows-import.c +152 -0
- package/deps/libmdbx/src/windows-import.h +128 -0
- package/deps/libmdbx/test/CMakeLists.txt +317 -0
- package/deps/libmdbx/test/append.c++ +237 -0
- package/deps/libmdbx/test/base.h++ +92 -0
- package/deps/libmdbx/test/battery-tmux.sh +64 -0
- package/deps/libmdbx/test/cases.c++ +118 -0
- package/deps/libmdbx/test/chrono.c++ +134 -0
- package/deps/libmdbx/test/chrono.h++ +85 -0
- package/deps/libmdbx/test/config.c++ +643 -0
- package/deps/libmdbx/test/config.h++ +334 -0
- package/deps/libmdbx/test/copy.c++ +62 -0
- package/deps/libmdbx/test/dead.c++ +39 -0
- package/deps/libmdbx/test/dump-load.sh +40 -0
- package/deps/libmdbx/test/extra/crunched_delete.c++ +409 -0
- package/deps/libmdbx/test/extra/cursor_closing.c++ +410 -0
- package/deps/libmdbx/test/extra/dbi.c++ +229 -0
- package/deps/libmdbx/test/extra/doubtless_positioning.c++ +253 -0
- package/deps/libmdbx/test/extra/dupfix_addodd.c +94 -0
- package/deps/libmdbx/test/extra/dupfix_multiple.c++ +311 -0
- package/deps/libmdbx/test/extra/early_close_dbi.c++ +137 -0
- package/deps/libmdbx/test/extra/hex_base64_base58.c++ +118 -0
- package/deps/libmdbx/test/extra/maindb_ordinal.c++ +61 -0
- package/deps/libmdbx/test/extra/open.c++ +96 -0
- package/deps/libmdbx/test/extra/pcrf/README.md +2 -0
- package/deps/libmdbx/test/extra/pcrf/pcrf_test.c +380 -0
- package/deps/libmdbx/test/extra/probe.c++ +10 -0
- package/deps/libmdbx/test/extra/txn.c++ +407 -0
- package/deps/libmdbx/test/extra/upsert_alldups.c +193 -0
- package/deps/libmdbx/test/fork.c++ +263 -0
- package/deps/libmdbx/test/hill.c++ +447 -0
- package/deps/libmdbx/test/jitter.c++ +197 -0
- package/deps/libmdbx/test/keygen.c++ +393 -0
- package/deps/libmdbx/test/keygen.h++ +130 -0
- package/deps/libmdbx/test/log.c++ +358 -0
- package/deps/libmdbx/test/log.h++ +91 -0
- package/deps/libmdbx/test/main.c++ +706 -0
- package/deps/libmdbx/test/nested.c++ +318 -0
- package/deps/libmdbx/test/osal-unix.c++ +647 -0
- package/deps/libmdbx/test/osal-windows.c++ +440 -0
- package/deps/libmdbx/test/osal.h++ +41 -0
- package/deps/libmdbx/test/stochastic.sh +690 -0
- package/deps/libmdbx/test/stub/LICENSE +24 -0
- package/deps/libmdbx/test/stub/README.md +8 -0
- package/deps/libmdbx/test/stub/pthread_barrier.c +104 -0
- package/deps/libmdbx/test/stub/pthread_barrier.h +77 -0
- package/deps/libmdbx/test/test.c++ +1551 -0
- package/deps/libmdbx/test/test.h++ +298 -0
- package/deps/libmdbx/test/tmux.conf +3 -0
- package/deps/libmdbx/test/try.c++ +30 -0
- package/deps/libmdbx/test/ttl.c++ +240 -0
- package/deps/libmdbx/test/utils.c++ +203 -0
- package/deps/libmdbx/test/utils.h++ +326 -0
- package/deps/libmdbx/test/valgrind_suppress.txt +536 -0
- package/lib/mdbx_evn_async.js +211 -0
- package/lib/mdbx_worker.js +195 -0
- package/lib/nativemou.js +6 -0
- package/package.json +38 -0
- package/src/async/envmou_close.cpp +34 -0
- package/src/async/envmou_close.hpp +32 -0
- package/src/async/envmou_copy_to.cpp +29 -0
- package/src/async/envmou_copy_to.hpp +38 -0
- package/src/async/envmou_keys.cpp +201 -0
- package/src/async/envmou_keys.hpp +50 -0
- package/src/async/envmou_open.cpp +38 -0
- package/src/async/envmou_open.hpp +33 -0
- package/src/async/envmou_query.cpp +167 -0
- package/src/async/envmou_query.hpp +53 -0
- package/src/dbimou.cpp +522 -0
- package/src/dbimou.hpp +82 -0
- package/src/env_arg0.hpp +24 -0
- package/src/envmou.cpp +445 -0
- package/src/envmou.hpp +116 -0
- package/src/modulemou.cpp +113 -0
- package/src/querymou.cpp +177 -0
- package/src/querymou.hpp +93 -0
- package/src/txnmou.cpp +254 -0
- package/src/txnmou.hpp +122 -0
- package/src/typemou.hpp +239 -0
- package/src/valuemou.hpp +194 -0
- package/test/async.js +67 -0
- package/test/e3.js +38 -0
- package/test/e4.js +89 -0
- package/test/e5.js +162 -0
- package/test/test-batch-ops.js +243 -0
- package/test/test-cursor-mode.js +84 -0
- package/test/test-multi-mode.js +87 -0
package/test/e5.js
ADDED
|
@@ -0,0 +1,162 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
const fs = require('fs');
|
|
4
|
+
const MDBX = require('../lib/nativemou.js');
|
|
5
|
+
const { MDBX_Env, MDBX_Param } = MDBX;
|
|
6
|
+
|
|
7
|
+
const test = async () => {
|
|
8
|
+
const path = 'e5';
|
|
9
|
+
|
|
10
|
+
await Promise.all([
|
|
11
|
+
fs.promises.rm(path, { recursive: true, force: true })
|
|
12
|
+
]);
|
|
13
|
+
|
|
14
|
+
console.log("MDBX_Param:", MDBX_Param);
|
|
15
|
+
// получаем константы
|
|
16
|
+
const { keyMode, keyFlag, queryMode, valueFlag } = MDBX_Param;
|
|
17
|
+
|
|
18
|
+
const db = new MDBX_Env();
|
|
19
|
+
|
|
20
|
+
console.log('Opening database...');
|
|
21
|
+
const rc = await db.open({
|
|
22
|
+
path: path,
|
|
23
|
+
valueFlag: valueFlag.string
|
|
24
|
+
});
|
|
25
|
+
|
|
26
|
+
const count = 2;
|
|
27
|
+
console.log('Start write');
|
|
28
|
+
const txn = db.startWrite();
|
|
29
|
+
// будем использовать ordinal ключи
|
|
30
|
+
const dbi = txn.createMap(keyMode.ordinal);
|
|
31
|
+
for (let i = 0; i < count; i++) {
|
|
32
|
+
dbi.put(i, `val-${i}`, 0);
|
|
33
|
+
}
|
|
34
|
+
txn.commit();
|
|
35
|
+
console.log('Write finish');
|
|
36
|
+
|
|
37
|
+
// вычитаем key = 1 - асинхронно
|
|
38
|
+
// запишем при этом key = 2
|
|
39
|
+
// по умолчаниюю query выполняется в режиме wr
|
|
40
|
+
const out = await db.query([
|
|
41
|
+
{
|
|
42
|
+
mode: queryMode.get,
|
|
43
|
+
keyMode: keyMode.ordinal,
|
|
44
|
+
keyFlag: keyFlag.number,
|
|
45
|
+
item: [{ "key": 1 }, { "key": 42 }]
|
|
46
|
+
},
|
|
47
|
+
{
|
|
48
|
+
mode: queryMode.insertUnique,
|
|
49
|
+
keyMode: keyMode.ordinal,
|
|
50
|
+
keyFlag: keyFlag.number,
|
|
51
|
+
item: [{ "key": 2, "value":"val-2" }]
|
|
52
|
+
}
|
|
53
|
+
]);
|
|
54
|
+
console.log('q1', JSON.stringify(out));
|
|
55
|
+
|
|
56
|
+
// вычитаем key = 2 - синхронно
|
|
57
|
+
const r = db.startRead();
|
|
58
|
+
const rdbi = r.openMap(keyMode.ordinal);
|
|
59
|
+
const keys = rdbi.keys();
|
|
60
|
+
const val = rdbi.get(2);
|
|
61
|
+
console.log("keys", keys);
|
|
62
|
+
console.log("read 2", val);
|
|
63
|
+
|
|
64
|
+
console.log("forEach");
|
|
65
|
+
rdbi.forEach((key, value, index) => {
|
|
66
|
+
console.log(`[${index}]`, key, value);
|
|
67
|
+
});
|
|
68
|
+
|
|
69
|
+
console.log("forEach from key 1");
|
|
70
|
+
rdbi.forEach(1, (key, value, index) => {
|
|
71
|
+
console.log(`[${index}]`, key, value);
|
|
72
|
+
});
|
|
73
|
+
|
|
74
|
+
{
|
|
75
|
+
const out = rdbi.keysFrom(1);
|
|
76
|
+
console.log("keysFrom()", out);
|
|
77
|
+
}
|
|
78
|
+
|
|
79
|
+
r.commit();
|
|
80
|
+
|
|
81
|
+
{
|
|
82
|
+
// почитаем асинхронно в упрощенном режиме
|
|
83
|
+
console.log("Read key = 2 in simple async mode to out2");
|
|
84
|
+
const out2 = await db.query({
|
|
85
|
+
keyMode: keyMode.ordinal,
|
|
86
|
+
item: [{ "key": 2 }, { "key": 42 }]
|
|
87
|
+
});
|
|
88
|
+
console.log("out2", JSON.stringify(out2));
|
|
89
|
+
}
|
|
90
|
+
|
|
91
|
+
{
|
|
92
|
+
// почитаем асинхронно в упрощенном режиме
|
|
93
|
+
const out = await db.keys({
|
|
94
|
+
keyMode: BigInt(keyMode.ordinal),
|
|
95
|
+
});
|
|
96
|
+
console.log("await keys()", out);
|
|
97
|
+
}
|
|
98
|
+
|
|
99
|
+
// добавим не существующий ключ
|
|
100
|
+
keys.push(42);
|
|
101
|
+
// удалим все ключи
|
|
102
|
+
const rm = await db.query([
|
|
103
|
+
{
|
|
104
|
+
mode: queryMode.del,
|
|
105
|
+
keyMode: keyMode.ordinal,
|
|
106
|
+
item: keys.map(key => ({ "key": key }))
|
|
107
|
+
}
|
|
108
|
+
]);
|
|
109
|
+
console.log("rm keys", JSON.stringify(rm));
|
|
110
|
+
|
|
111
|
+
// Тестируем forEach с cursorMode
|
|
112
|
+
{
|
|
113
|
+
console.log("=== Testing forEach with cursorMode ===");
|
|
114
|
+
|
|
115
|
+
// добавим тестовые данные
|
|
116
|
+
const w = db.startWrite();
|
|
117
|
+
const wdbi = w.createMap(keyMode.ordinal);
|
|
118
|
+
for (let i = 1; i <= 10; i++) {
|
|
119
|
+
wdbi.put(i, `value${i}`);
|
|
120
|
+
}
|
|
121
|
+
w.commit();
|
|
122
|
+
|
|
123
|
+
// читаем заново
|
|
124
|
+
const r = db.startRead();
|
|
125
|
+
const dbi = r.openMap(keyMode.ordinal);
|
|
126
|
+
|
|
127
|
+
// forEach(fn) - обычный вызов
|
|
128
|
+
console.log("forEach(fn):");
|
|
129
|
+
dbi.forEach((k, v, i) => {
|
|
130
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
131
|
+
return i >= 2; // останавливаем после 3 элементов
|
|
132
|
+
});
|
|
133
|
+
|
|
134
|
+
// forEach(fromKey, fn) - с начального ключа
|
|
135
|
+
console.log("forEach(fromKey=5, fn):");
|
|
136
|
+
dbi.forEach(5, (k, v, i) => {
|
|
137
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
138
|
+
return i >= 2; // останавливаем после 3 элементов
|
|
139
|
+
});
|
|
140
|
+
|
|
141
|
+
// forEach(fromKey, cursorMode, fn) - с cursorMode
|
|
142
|
+
console.log("forEach(fromKey=7, cursorMode=keyGreater, fn):");
|
|
143
|
+
dbi.forEach(7, 'keyGreater', (k, v, i) => {
|
|
144
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
145
|
+
return i >= 1; // останавливаем после 2 элементов
|
|
146
|
+
});
|
|
147
|
+
|
|
148
|
+
r.commit();
|
|
149
|
+
}
|
|
150
|
+
|
|
151
|
+
// вычитаем все ключи
|
|
152
|
+
{
|
|
153
|
+
// вычитаем key = 2 - синхронно
|
|
154
|
+
const r = db.startRead();
|
|
155
|
+
const dbi = r.openMap(keyMode.ordinal);
|
|
156
|
+
console.log("keys", dbi.keys());
|
|
157
|
+
r.commit();
|
|
158
|
+
}
|
|
159
|
+
await db.close();
|
|
160
|
+
}
|
|
161
|
+
|
|
162
|
+
test().catch(console.error);
|
|
@@ -0,0 +1,243 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
const fs = require("fs");
|
|
3
|
+
const { MDBX_Async_Env } = require("../lib/mdbx_evn_async.js");
|
|
4
|
+
const MDBX = require("../lib/nativemou.js");
|
|
5
|
+
const { MDBX_Param } = MDBX;
|
|
6
|
+
|
|
7
|
+
(async () => {
|
|
8
|
+
const testPath = "batch-ops-db";
|
|
9
|
+
await fs.promises.rm(testPath, { recursive: true, force: true }).catch(() => {});
|
|
10
|
+
|
|
11
|
+
const env = new MDBX_Async_Env();
|
|
12
|
+
|
|
13
|
+
try {
|
|
14
|
+
await env.open({ path: testPath });
|
|
15
|
+
const { keyMode } = MDBX_Param;
|
|
16
|
+
|
|
17
|
+
console.log("=== Тест групповых операций ===");
|
|
18
|
+
|
|
19
|
+
// 1. Создаем транзакцию
|
|
20
|
+
console.log("1. Создаем транзакцию записи...");
|
|
21
|
+
const w = await env.startWrite();
|
|
22
|
+
const dbi = await w.openMap({ keyMode: keyMode.ordinal, create: true });
|
|
23
|
+
|
|
24
|
+
// 2. Групповая запись множества ключей
|
|
25
|
+
console.log("2. Групповая запись 5 ключей...");
|
|
26
|
+
const itemsToWrite = [
|
|
27
|
+
{ key: 1n, value: "value1" },
|
|
28
|
+
{ key: 2n, value: "value2" },
|
|
29
|
+
{ key: 3n, value: "value3" },
|
|
30
|
+
{ key: 4n, value: "value4" },
|
|
31
|
+
{ key: 5n, value: "value5" }
|
|
32
|
+
];
|
|
33
|
+
|
|
34
|
+
const writeResults = await dbi.putBatch(itemsToWrite);
|
|
35
|
+
console.log("Результат записи:", writeResults);
|
|
36
|
+
|
|
37
|
+
// 3. Коммитим транзакцию
|
|
38
|
+
console.log("3. Коммитим транзакцию...");
|
|
39
|
+
await w.commit();
|
|
40
|
+
|
|
41
|
+
// 4. Создаем транзакцию чтения
|
|
42
|
+
console.log("4. Создаем транзакцию чтения...");
|
|
43
|
+
const r = await env.startRead();
|
|
44
|
+
const readDbi = await r.openMap({ keyMode: keyMode.ordinal });
|
|
45
|
+
|
|
46
|
+
// 5. Групповое чтение множества ключей
|
|
47
|
+
console.log("5. Групповое чтение ключей...");
|
|
48
|
+
const keysToRead = [1n, 2n, 3n, 42n, 5n]; // 42n не существует
|
|
49
|
+
const readResults = await readDbi.getBatch(keysToRead);
|
|
50
|
+
console.log("Результат чтения:");
|
|
51
|
+
readResults.forEach(r => {
|
|
52
|
+
console.log(` Ключ ${r.key}: ${r.found ? r.value : 'НЕ НАЙДЕН'}`);
|
|
53
|
+
});
|
|
54
|
+
|
|
55
|
+
await r.commit();
|
|
56
|
+
|
|
57
|
+
// 6. Создаем транзакцию для удаления
|
|
58
|
+
console.log("6. Создаем транзакцию для удаления...");
|
|
59
|
+
const d = await env.startWrite();
|
|
60
|
+
const delDbi = await d.openMap({ keyMode: keyMode.ordinal });
|
|
61
|
+
|
|
62
|
+
// 7. Групповое удаление ключей
|
|
63
|
+
console.log("7. Групповое удаление ключей...");
|
|
64
|
+
const keysToDelete = [2n, 4n, 42n]; // 42n не существует
|
|
65
|
+
const deleteResults = await delDbi.delBatch(keysToDelete);
|
|
66
|
+
console.log("Результат удаления:");
|
|
67
|
+
deleteResults.forEach(r => {
|
|
68
|
+
console.log(` Ключ ${r.key}: ${r.deleted ? 'УДАЛЕН' : 'НЕ НАЙДЕН'}`);
|
|
69
|
+
});
|
|
70
|
+
|
|
71
|
+
await d.commit();
|
|
72
|
+
|
|
73
|
+
// 8. Проверяем финальное состояние
|
|
74
|
+
console.log("8. Проверяем финальное состояние...");
|
|
75
|
+
const final = await env.startRead();
|
|
76
|
+
const finalDbi = await final.openMap({ keyMode: keyMode.ordinal });
|
|
77
|
+
|
|
78
|
+
const allKeys = [1n, 2n, 3n, 4n, 5n];
|
|
79
|
+
const finalResults = await finalDbi.getBatch(allKeys);
|
|
80
|
+
console.log("Финальное состояние:");
|
|
81
|
+
finalResults.forEach(r => {
|
|
82
|
+
console.log(` Ключ ${r.key}: ${r.found ? r.value : 'ОТСУТСТВУЕТ'}`);
|
|
83
|
+
});
|
|
84
|
+
|
|
85
|
+
await final.commit();
|
|
86
|
+
|
|
87
|
+
await env.close();
|
|
88
|
+
console.log("Тест завершен успешно!");
|
|
89
|
+
|
|
90
|
+
console.log("\n=== Тест с двумя базами данных ===");
|
|
91
|
+
|
|
92
|
+
// Открываем заново для multi-database теста
|
|
93
|
+
await env.open({ path: testPath });
|
|
94
|
+
|
|
95
|
+
// 1. Создаем транзакцию и две базы данных
|
|
96
|
+
console.log("1. Создаем транзакцию и две базы...");
|
|
97
|
+
const multiW = await env.startWrite();
|
|
98
|
+
const oddDbi = await multiW.openMap({
|
|
99
|
+
name: "odd_numbers",
|
|
100
|
+
keyMode: keyMode.ordinal,
|
|
101
|
+
create: true
|
|
102
|
+
});
|
|
103
|
+
const evenDbi = await multiW.openMap({
|
|
104
|
+
name: "even_numbers",
|
|
105
|
+
keyMode: keyMode.ordinal,
|
|
106
|
+
create: true
|
|
107
|
+
});
|
|
108
|
+
|
|
109
|
+
// 2. Заполняем начальными данными
|
|
110
|
+
console.log("2. Заполняем начальными данными...");
|
|
111
|
+
const oddInitial = [
|
|
112
|
+
{ key: 1n, value: "один" },
|
|
113
|
+
{ key: 3n, value: "три" },
|
|
114
|
+
{ key: 5n, value: "пять" }
|
|
115
|
+
];
|
|
116
|
+
const evenInitial = [
|
|
117
|
+
{ key: 2n, value: "два" },
|
|
118
|
+
{ key: 4n, value: "четыре" }
|
|
119
|
+
];
|
|
120
|
+
|
|
121
|
+
const oddResults = await oddDbi.putBatch(oddInitial);
|
|
122
|
+
const evenResults = await evenDbi.putBatch(evenInitial);
|
|
123
|
+
|
|
124
|
+
console.log("Нечетные числа записаны:", oddResults.every(r => r.success));
|
|
125
|
+
console.log("Четные числа записаны:", evenResults.every(r => r.success));
|
|
126
|
+
|
|
127
|
+
// 3. Добавляем дополнительные данные в ту же транзакцию
|
|
128
|
+
console.log("3. Добавляем дополнительные числа...");
|
|
129
|
+
const oddAdditional = [
|
|
130
|
+
{ key: 7n, value: "семь" },
|
|
131
|
+
{ key: 9n, value: "девять" }
|
|
132
|
+
];
|
|
133
|
+
const evenAdditional = [
|
|
134
|
+
{ key: 6n, value: "шесть" },
|
|
135
|
+
{ key: 8n, value: "восемь" }
|
|
136
|
+
];
|
|
137
|
+
|
|
138
|
+
await oddDbi.putBatch(oddAdditional);
|
|
139
|
+
await evenDbi.putBatch(evenAdditional);
|
|
140
|
+
|
|
141
|
+
console.log("Дополнительные числа добавлены");
|
|
142
|
+
|
|
143
|
+
// 4. Коммитим всё одной транзакцией
|
|
144
|
+
console.log("4. Коммитим обе базы одной транзакцией...");
|
|
145
|
+
await multiW.commit();
|
|
146
|
+
|
|
147
|
+
// 5. Проверяем результаты в обеих базах
|
|
148
|
+
console.log("5. Проверяем результаты...");
|
|
149
|
+
const checkR = await env.startRead();
|
|
150
|
+
const checkOddDbi = await checkR.openMap({
|
|
151
|
+
name: "odd_numbers",
|
|
152
|
+
keyMode: keyMode.ordinal
|
|
153
|
+
});
|
|
154
|
+
const checkEvenDbi = await checkR.openMap({
|
|
155
|
+
name: "even_numbers",
|
|
156
|
+
keyMode: keyMode.ordinal
|
|
157
|
+
});
|
|
158
|
+
|
|
159
|
+
// Читаем все нечетные числа
|
|
160
|
+
const oddKeys = [1n, 3n, 5n, 7n, 9n];
|
|
161
|
+
const oddFinalResults = await checkOddDbi.getBatch(oddKeys);
|
|
162
|
+
console.log("База нечетных чисел:");
|
|
163
|
+
oddFinalResults.forEach(r => {
|
|
164
|
+
console.log(` ${r.key}: ${r.found ? r.value : 'ОТСУТСТВУЕТ'}`);
|
|
165
|
+
});
|
|
166
|
+
|
|
167
|
+
// Читаем все четные числа
|
|
168
|
+
const evenKeys = [2n, 4n, 6n, 8n];
|
|
169
|
+
const evenFinalResults = await checkEvenDbi.getBatch(evenKeys);
|
|
170
|
+
console.log("База четных чисел:");
|
|
171
|
+
evenFinalResults.forEach(r => {
|
|
172
|
+
console.log(` ${r.key}: ${r.found ? r.value : 'ОТСУТСТВУЕТ'}`);
|
|
173
|
+
});
|
|
174
|
+
|
|
175
|
+
await checkR.commit();
|
|
176
|
+
|
|
177
|
+
// 6. Тест межбазовых операций в одной транзакции
|
|
178
|
+
console.log("6. Тест межбазовых операций...");
|
|
179
|
+
const crossW = await env.startWrite();
|
|
180
|
+
const crossOddDbi = await crossW.openMap({
|
|
181
|
+
name: "odd_numbers",
|
|
182
|
+
keyMode: keyMode.ordinal
|
|
183
|
+
});
|
|
184
|
+
const crossEvenDbi = await crossW.openMap({
|
|
185
|
+
name: "even_numbers",
|
|
186
|
+
keyMode: keyMode.ordinal
|
|
187
|
+
});
|
|
188
|
+
|
|
189
|
+
// Удаляем некоторые числа из обеих баз
|
|
190
|
+
console.log("Удаляем 5 из нечетных и 4 из четных...");
|
|
191
|
+
await crossOddDbi.delBatch([5n]);
|
|
192
|
+
await crossEvenDbi.delBatch([4n]);
|
|
193
|
+
|
|
194
|
+
// Добавляем новые числа
|
|
195
|
+
console.log("Добавляем 11 в нечетные и 10 в четные...");
|
|
196
|
+
await crossOddDbi.putBatch([{ key: 11n, value: "одиннадцать" }]);
|
|
197
|
+
await crossEvenDbi.putBatch([{ key: 10n, value: "десять" }]);
|
|
198
|
+
|
|
199
|
+
await crossW.commit();
|
|
200
|
+
|
|
201
|
+
// 7. Финальная проверка
|
|
202
|
+
console.log("7. Финальная проверка всех баз...");
|
|
203
|
+
const finalCheckR = await env.startRead();
|
|
204
|
+
const finalOddDbi = await finalCheckR.openMap({
|
|
205
|
+
name: "odd_numbers",
|
|
206
|
+
keyMode: keyMode.ordinal
|
|
207
|
+
});
|
|
208
|
+
const finalEvenDbi = await finalCheckR.openMap({
|
|
209
|
+
name: "even_numbers",
|
|
210
|
+
keyMode: keyMode.ordinal
|
|
211
|
+
});
|
|
212
|
+
|
|
213
|
+
const allOddKeys = [1n, 3n, 5n, 7n, 9n, 11n];
|
|
214
|
+
const allEvenKeys = [2n, 4n, 6n, 8n, 10n];
|
|
215
|
+
|
|
216
|
+
const finalOddResults = await finalOddDbi.getBatch(allOddKeys);
|
|
217
|
+
const finalEvenResults = await finalEvenDbi.getBatch(allEvenKeys);
|
|
218
|
+
|
|
219
|
+
console.log("Финальное состояние нечетных:");
|
|
220
|
+
finalOddResults.forEach(r => {
|
|
221
|
+
console.log(` ${r.key}: ${r.found ? r.value : 'УДАЛЕНО'}`);
|
|
222
|
+
});
|
|
223
|
+
|
|
224
|
+
console.log("Финальное состояние четных:");
|
|
225
|
+
finalEvenResults.forEach(r => {
|
|
226
|
+
console.log(` ${r.key}: ${r.found ? r.value : 'УДАЛЕНО'}`);
|
|
227
|
+
});
|
|
228
|
+
|
|
229
|
+
await finalCheckR.commit();
|
|
230
|
+
|
|
231
|
+
await env.close();
|
|
232
|
+
console.log("Тест с двумя базами завершен успешно!");
|
|
233
|
+
|
|
234
|
+
} catch (error) {
|
|
235
|
+
console.error("Ошибка теста:", error);
|
|
236
|
+
} finally {
|
|
237
|
+
try {
|
|
238
|
+
await env.terminate();
|
|
239
|
+
} catch (e) {
|
|
240
|
+
console.error("Ошибка при завершении:", e.message);
|
|
241
|
+
}
|
|
242
|
+
}
|
|
243
|
+
})();
|
|
@@ -0,0 +1,84 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
const fs = require('fs');
|
|
4
|
+
const MDBX = require('../lib/nativemou.js');
|
|
5
|
+
const { MDBX_Env, MDBX_Param } = MDBX;
|
|
6
|
+
|
|
7
|
+
const testCursorMode = async () => {
|
|
8
|
+
const path = 'test-cursor-mode';
|
|
9
|
+
|
|
10
|
+
await Promise.all([
|
|
11
|
+
fs.promises.rm(path, { recursive: true, force: true })
|
|
12
|
+
]);
|
|
13
|
+
|
|
14
|
+
const { keyMode, cursorMode } = MDBX_Param;
|
|
15
|
+
|
|
16
|
+
const db = new MDBX_Env();
|
|
17
|
+
|
|
18
|
+
console.log('Opening database...');
|
|
19
|
+
await db.open({
|
|
20
|
+
path: path,
|
|
21
|
+
valueFlag: MDBX_Param.valueFlag.string
|
|
22
|
+
});
|
|
23
|
+
|
|
24
|
+
// добавим тестовые данные
|
|
25
|
+
const w = db.startWrite();
|
|
26
|
+
const wdbi = w.createMap(keyMode.ordinal);
|
|
27
|
+
for (let i = 1; i <= 10; i++) {
|
|
28
|
+
wdbi.put(i, `value${i}`);
|
|
29
|
+
}
|
|
30
|
+
w.commit();
|
|
31
|
+
|
|
32
|
+
// читаем данные
|
|
33
|
+
const r = db.startRead();
|
|
34
|
+
const dbi = r.openMap(keyMode.ordinal);
|
|
35
|
+
|
|
36
|
+
console.log('=== Testing forEach variants ===');
|
|
37
|
+
|
|
38
|
+
// 1. forEach(fn)
|
|
39
|
+
console.log('\n1. forEach(fn):');
|
|
40
|
+
let count = dbi.forEach((k, v, i) => {
|
|
41
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
42
|
+
return i >= 2; // останавливаем после 3 элементов
|
|
43
|
+
});
|
|
44
|
+
console.log(`Processed ${count} items`);
|
|
45
|
+
|
|
46
|
+
// 2. forEach(fromKey, fn)
|
|
47
|
+
console.log('\n2. forEach(fromKey=5, fn):');
|
|
48
|
+
count = dbi.forEach(5, (k, v, i) => {
|
|
49
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
50
|
+
return i >= 2; // останавливаем после 3 элементов
|
|
51
|
+
});
|
|
52
|
+
console.log(`Processed ${count} items`);
|
|
53
|
+
|
|
54
|
+
// 3. forEach(fromKey, cursorMode, fn) - строковый режим
|
|
55
|
+
console.log('\n3. forEach(fromKey=7, "keyGreater", fn):');
|
|
56
|
+
count = dbi.forEach(7, 'keyGreater', (k, v, i) => {
|
|
57
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
58
|
+
return i >= 1; // останавливаем после 2 элементов
|
|
59
|
+
});
|
|
60
|
+
console.log(`Processed ${count} items`);
|
|
61
|
+
|
|
62
|
+
// 4. forEach(fromKey, cursorMode, fn) - числовой режим key_lesser_or_equal (обратное сканирование)
|
|
63
|
+
console.log('\n4. forEach(fromKey=7, cursorMode.key_lesser_or_equal, fn):');
|
|
64
|
+
count = dbi.forEach(7, cursorMode.key_lesser_or_equal, (k, v, i) => {
|
|
65
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
66
|
+
return i >= 2; // останавливаем после 3 элементов
|
|
67
|
+
});
|
|
68
|
+
console.log(`Processed ${count} items`);
|
|
69
|
+
|
|
70
|
+
// 5. forEach(fromKey, cursorMode, fn) - keyEqual
|
|
71
|
+
console.log('\n5. forEach(fromKey=5, "keyEqual", fn):');
|
|
72
|
+
count = dbi.forEach(5, 'keyEqual', (k, v, i) => {
|
|
73
|
+
console.log(` ${i}: ${k} = ${v}`);
|
|
74
|
+
return i >= 0; // останавливаем после первого элемента для демонстрации
|
|
75
|
+
});
|
|
76
|
+
console.log(`Processed ${count} items`);
|
|
77
|
+
|
|
78
|
+
r.commit();
|
|
79
|
+
await db.close();
|
|
80
|
+
|
|
81
|
+
console.log('\n=== Test completed successfully ===');
|
|
82
|
+
}
|
|
83
|
+
|
|
84
|
+
testCursorMode().catch(console.error);
|
|
@@ -0,0 +1,87 @@
|
|
|
1
|
+
"use strict";
|
|
2
|
+
|
|
3
|
+
const fs = require('fs');
|
|
4
|
+
const MDBX = require('../lib/nativemou.js');
|
|
5
|
+
const { MDBX_Env, MDBX_Param } = MDBX;
|
|
6
|
+
|
|
7
|
+
const testMultiMode = async () => {
|
|
8
|
+
const path = 'test-multi-mode';
|
|
9
|
+
|
|
10
|
+
await Promise.all([
|
|
11
|
+
fs.promises.rm(path, { recursive: true, force: true })
|
|
12
|
+
]);
|
|
13
|
+
|
|
14
|
+
const { keyMode, valueMode, cursorMode } = MDBX_Param;
|
|
15
|
+
|
|
16
|
+
const db = new MDBX_Env();
|
|
17
|
+
|
|
18
|
+
console.log('Opening database with multi value mode...');
|
|
19
|
+
await db.open({
|
|
20
|
+
path: path,
|
|
21
|
+
valueFlag: MDBX_Param.valueFlag.string
|
|
22
|
+
});
|
|
23
|
+
|
|
24
|
+
// добавим тестовые данные в multi режиме
|
|
25
|
+
const w = db.startWrite();
|
|
26
|
+
const wdbi = w.createMap(keyMode.ordinal, valueMode.multi);
|
|
27
|
+
|
|
28
|
+
// Добавляем несколько значений для одного ключа
|
|
29
|
+
wdbi.put(5, 'value5_1');
|
|
30
|
+
wdbi.put(5, 'value5_2');
|
|
31
|
+
wdbi.put(5, 'value5_3');
|
|
32
|
+
|
|
33
|
+
// Добавляем данные для других ключей
|
|
34
|
+
for (let i = 1; i <= 10; i++) {
|
|
35
|
+
if (i !== 5) {
|
|
36
|
+
wdbi.put(i, `value${i}`);
|
|
37
|
+
}
|
|
38
|
+
}
|
|
39
|
+
|
|
40
|
+
w.commit();
|
|
41
|
+
|
|
42
|
+
// читаем данные
|
|
43
|
+
const r = db.startRead();
|
|
44
|
+
const dbi = r.openMap(keyMode.ordinal, valueMode.multi);
|
|
45
|
+
|
|
46
|
+
console.log('=== Testing multi mode with key_equal ===');
|
|
47
|
+
|
|
48
|
+
// 1. Обычный forEach - должен показать все записи
|
|
49
|
+
console.log('\n1. forEach(fn) - все записи:');
|
|
50
|
+
let count = dbi.forEach((k, v, i) => {
|
|
51
|
+
console.log(` ${i}: key=${k} value=${v}`);
|
|
52
|
+
return false; // продолжаем
|
|
53
|
+
});
|
|
54
|
+
console.log(`Total processed: ${count} items`);
|
|
55
|
+
|
|
56
|
+
// 2. forEach с key_equal для ключа 5 - должен показать все три записи
|
|
57
|
+
console.log('\n2. forEach(key=5, "keyEqual", fn) - три записи для ключа 5:');
|
|
58
|
+
count = dbi.forEach(5, 'keyEqual', (k, v, i) => {
|
|
59
|
+
console.log(` ${i}: key=${k} value=${v}`);
|
|
60
|
+
});
|
|
61
|
+
console.log(`Processed: ${count} items`);
|
|
62
|
+
|
|
63
|
+
// 3. forEach с key_greater_or_equal для ключа 5 - должен показать все записи начиная с ключа 5
|
|
64
|
+
console.log('\n3. forEach(key=5, "keyGreaterOrEqual", fn) - все записи от ключа 5:');
|
|
65
|
+
count = dbi.forEach(5, 'keyGreaterOrEqual', (k, v, i) => {
|
|
66
|
+
console.log(` ${i}: key=${k} value=${v}`);
|
|
67
|
+
return i >= 4; // останавливаем после 5 элементов
|
|
68
|
+
});
|
|
69
|
+
console.log(`Processed: ${count} items`);
|
|
70
|
+
|
|
71
|
+
// 4. keysFrom с key_equal - должен вернуть три ключа
|
|
72
|
+
console.log('\n4. keysFrom(key=5, limit=10, "keyEqual") - три ключа:');
|
|
73
|
+
const keysEqual = dbi.keysFrom(5, 10, 'keyEqual');
|
|
74
|
+
console.log(`Keys: [${keysEqual.join(', ')}]`);
|
|
75
|
+
|
|
76
|
+
// 5. keysFrom с key_greater_or_equal - должен вернуть все ключи от 5
|
|
77
|
+
console.log('\n5. keysFrom(key=5, limit=10, "keyGreaterOrEqual") - все ключи от 5:');
|
|
78
|
+
const keysGreater = dbi.keysFrom(5, 10, 'keyGreaterOrEqual');
|
|
79
|
+
console.log(`Keys: [${keysGreater.join(', ')}]`);
|
|
80
|
+
|
|
81
|
+
r.commit();
|
|
82
|
+
await db.close();
|
|
83
|
+
|
|
84
|
+
console.log('\n=== Multi mode test completed successfully ===');
|
|
85
|
+
}
|
|
86
|
+
|
|
87
|
+
testMultiMode().catch(console.error);
|