@wxn0brp/db 0.10.0 → 0.20.1
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/LICENSE +1 -1
- package/dist/{helpers/autoCreate.d.ts → autoCreate.d.ts} +2 -2
- package/dist/{helpers/autoCreate.js → autoCreate.js} +2 -2
- package/dist/{db/graph.d.ts → graph.d.ts} +1 -1
- package/dist/index.d.ts +8 -15
- package/dist/index.js +7 -10
- package/dist/valthera.d.ts +7 -0
- package/dist/valthera.js +14 -0
- package/dist/version.js +1 -1
- package/package.json +11 -21
- package/dist/actions/action.d.ts +0 -69
- package/dist/actions/action.js +0 -234
- package/dist/actions/memory.d.ts +0 -72
- package/dist/actions/memory.js +0 -145
- package/dist/base/actions.d.ts +0 -17
- package/dist/base/actions.js +0 -56
- package/dist/base/db.d.ts +0 -21
- package/dist/base/db.js +0 -56
- package/dist/client/function.d.ts +0 -5
- package/dist/client/function.js +0 -30
- package/dist/client/graph.d.ts +0 -54
- package/dist/client/graph.js +0 -108
- package/dist/client/remote.d.ts +0 -15
- package/dist/client/remote.js +0 -1
- package/dist/client/valthera.d.ts +0 -74
- package/dist/client/valthera.js +0 -135
- package/dist/db/valthera.d.ts +0 -75
- package/dist/db/valthera.js +0 -110
- package/dist/file/customFileCpu.d.ts +0 -18
- package/dist/file/customFileCpu.js +0 -68
- package/dist/file/find.d.ts +0 -11
- package/dist/file/find.js +0 -73
- package/dist/file/index.d.ts +0 -3
- package/dist/file/index.js +0 -16
- package/dist/file/remove.d.ts +0 -7
- package/dist/file/remove.js +0 -41
- package/dist/file/update.d.ts +0 -7
- package/dist/file/update.js +0 -50
- package/dist/file/utils.d.ts +0 -8
- package/dist/file/utils.js +0 -84
- package/dist/helpers/CollectionManager.d.ts +0 -43
- package/dist/helpers/CollectionManager.js +0 -57
- package/dist/helpers/executor.d.ts +0 -28
- package/dist/helpers/executor.js +0 -45
- package/dist/helpers/format.d.ts +0 -12
- package/dist/helpers/format.js +0 -23
- package/dist/helpers/gen.d.ts +0 -8
- package/dist/helpers/gen.js +0 -134
- package/dist/helpers/relation.d.ts +0 -10
- package/dist/helpers/relation.js +0 -155
- package/dist/helpers/updateOneOrAdd.d.ts +0 -2
- package/dist/helpers/updateOneOrAdd.js +0 -18
- package/dist/types/Id.d.ts +0 -3
- package/dist/types/Id.js +0 -1
- package/dist/types/arg.d.ts +0 -12
- package/dist/types/arg.js +0 -1
- package/dist/types/data.d.ts +0 -4
- package/dist/types/data.js +0 -1
- package/dist/types/export.d.ts +0 -11
- package/dist/types/export.js +0 -1
- package/dist/types/fileCpu.d.ts +0 -51
- package/dist/types/fileCpu.js +0 -1
- package/dist/types/options.d.ts +0 -19
- package/dist/types/options.js +0 -1
- package/dist/types/query.d.ts +0 -15
- package/dist/types/query.js +0 -1
- package/dist/types/relation.d.ts +0 -28
- package/dist/types/relation.js +0 -1
- package/dist/types/searchOpts.d.ts +0 -62
- package/dist/types/searchOpts.js +0 -7
- package/dist/types/types.d.ts +0 -3
- package/dist/types/types.js +0 -1
- package/dist/types/updater.d.ts +0 -26
- package/dist/types/updater.js +0 -4
- package/dist/types/valthera.d.ts +0 -36
- package/dist/types/valthera.js +0 -1
- package/dist/utils/hasFields.d.ts +0 -7
- package/dist/utils/hasFields.js +0 -18
- package/dist/utils/hasFieldsAdvanced.d.ts +0 -5
- package/dist/utils/hasFieldsAdvanced.js +0 -176
- package/dist/utils/sort.d.ts +0 -1
- package/dist/utils/sort.js +0 -23
- package/dist/utils/updateFindObject.d.ts +0 -11
- package/dist/utils/updateFindObject.js +0 -28
- package/dist/utils/updateObject.d.ts +0 -7
- package/dist/utils/updateObject.js +0 -145
- /package/dist/{db/graph.js → graph.js} +0 -0
package/dist/file/utils.js
DELETED
|
@@ -1,84 +0,0 @@
|
|
|
1
|
-
import { createReadStream } from "fs";
|
|
2
|
-
/**
|
|
3
|
-
* Repairs a file path by replacing double slashes
|
|
4
|
-
*/
|
|
5
|
-
export function pathRepair(path) {
|
|
6
|
-
return path.replaceAll("//", "/");
|
|
7
|
-
}
|
|
8
|
-
export function createRL(file) {
|
|
9
|
-
const stream = createReadStream(file, { highWaterMark: 64 * 1024 });
|
|
10
|
-
let buffer = "";
|
|
11
|
-
let done = false;
|
|
12
|
-
let error = null;
|
|
13
|
-
const lines = [];
|
|
14
|
-
let waiting = null;
|
|
15
|
-
stream.on("data", (chunk) => {
|
|
16
|
-
buffer += chunk.toString("utf8");
|
|
17
|
-
let index;
|
|
18
|
-
while ((index = buffer.search(/\r?\n/)) >= 0) {
|
|
19
|
-
const line = buffer.slice(0, index);
|
|
20
|
-
lines.push(line);
|
|
21
|
-
buffer = buffer.slice(index + (buffer[index] === "\r" && buffer[index + 1] === "\n" ? 2 : 1));
|
|
22
|
-
}
|
|
23
|
-
feed();
|
|
24
|
-
});
|
|
25
|
-
stream.on("end", () => {
|
|
26
|
-
if (buffer.length > 0) {
|
|
27
|
-
lines.push(buffer);
|
|
28
|
-
buffer = "";
|
|
29
|
-
}
|
|
30
|
-
done = true;
|
|
31
|
-
feed();
|
|
32
|
-
});
|
|
33
|
-
stream.on("error", (err) => {
|
|
34
|
-
error = err;
|
|
35
|
-
done = true;
|
|
36
|
-
feed();
|
|
37
|
-
});
|
|
38
|
-
const feed = () => {
|
|
39
|
-
if (waiting) {
|
|
40
|
-
if (error) {
|
|
41
|
-
waiting(Promise.reject(error));
|
|
42
|
-
}
|
|
43
|
-
else if (lines.length > 0) {
|
|
44
|
-
waiting({ value: lines.shift(), done: false });
|
|
45
|
-
}
|
|
46
|
-
else if (done) {
|
|
47
|
-
waiting({ value: undefined, done: true });
|
|
48
|
-
}
|
|
49
|
-
else {
|
|
50
|
-
return;
|
|
51
|
-
}
|
|
52
|
-
waiting = null;
|
|
53
|
-
}
|
|
54
|
-
};
|
|
55
|
-
const iterator = {
|
|
56
|
-
next() {
|
|
57
|
-
if (error)
|
|
58
|
-
return Promise.reject(error);
|
|
59
|
-
if (lines.length > 0)
|
|
60
|
-
return Promise.resolve({ value: lines.shift(), done: false });
|
|
61
|
-
if (done)
|
|
62
|
-
return Promise.resolve({ value: undefined, done: true });
|
|
63
|
-
return new Promise(res => {
|
|
64
|
-
waiting = res;
|
|
65
|
-
});
|
|
66
|
-
},
|
|
67
|
-
return() {
|
|
68
|
-
rl.close();
|
|
69
|
-
return Promise.resolve({ value: undefined, done: true });
|
|
70
|
-
}
|
|
71
|
-
};
|
|
72
|
-
const rl = {
|
|
73
|
-
[Symbol.asyncIterator]() {
|
|
74
|
-
return iterator;
|
|
75
|
-
},
|
|
76
|
-
close() {
|
|
77
|
-
if (!done) {
|
|
78
|
-
done = true;
|
|
79
|
-
stream.destroy();
|
|
80
|
-
}
|
|
81
|
-
}
|
|
82
|
-
};
|
|
83
|
-
return rl;
|
|
84
|
-
}
|
|
@@ -1,43 +0,0 @@
|
|
|
1
|
-
import { Arg, Search, Updater } from "../types/arg.js";
|
|
2
|
-
import { DbFindOpts, FindOpts } from "../types/options.js";
|
|
3
|
-
import { Context } from "../types/types.js";
|
|
4
|
-
import Data from "../types/data.js";
|
|
5
|
-
import { ValtheraCompatible } from "../types/valthera.js";
|
|
6
|
-
declare class CollectionManager {
|
|
7
|
-
private db;
|
|
8
|
-
private collection;
|
|
9
|
-
constructor(db: ValtheraCompatible, collection: string);
|
|
10
|
-
/**
|
|
11
|
-
* Add data to a database.
|
|
12
|
-
*/
|
|
13
|
-
add<T = Data>(data: Arg, id_gen?: boolean): Promise<T>;
|
|
14
|
-
/**
|
|
15
|
-
* Find data in a database.
|
|
16
|
-
*/
|
|
17
|
-
find<T = Data>(search: Search, context?: Context, options?: DbFindOpts, findOpts?: FindOpts): Promise<T[]>;
|
|
18
|
-
/**
|
|
19
|
-
* Find one data entry in a database.
|
|
20
|
-
*/
|
|
21
|
-
findOne<T = Data>(search: Search, context?: Context, findOpts?: FindOpts): Promise<T>;
|
|
22
|
-
/**
|
|
23
|
-
* Update data in a database.
|
|
24
|
-
*/
|
|
25
|
-
update(search: Search, updater: Updater, context?: Context): Promise<boolean>;
|
|
26
|
-
/**
|
|
27
|
-
* Update one data entry in a database.
|
|
28
|
-
*/
|
|
29
|
-
updateOne(search: Search, updater: Updater, context?: Context): Promise<boolean>;
|
|
30
|
-
/**
|
|
31
|
-
* Remove data from a database.
|
|
32
|
-
*/
|
|
33
|
-
remove(search: Search, context?: Context): Promise<boolean>;
|
|
34
|
-
/**
|
|
35
|
-
* Remove one data entry from a database.
|
|
36
|
-
*/
|
|
37
|
-
removeOne(search: Search, context?: Context): Promise<boolean>;
|
|
38
|
-
/**
|
|
39
|
-
* Asynchronously updates one entry in a database or adds a new one if it doesn't exist.
|
|
40
|
-
*/
|
|
41
|
-
updateOneOrAdd(search: Search, updater: Updater, add_arg?: Arg, context?: Context, id_gen?: boolean): Promise<boolean>;
|
|
42
|
-
}
|
|
43
|
-
export default CollectionManager;
|
|
@@ -1,57 +0,0 @@
|
|
|
1
|
-
class CollectionManager {
|
|
2
|
-
db;
|
|
3
|
-
collection;
|
|
4
|
-
constructor(db, collection) {
|
|
5
|
-
this.db = db;
|
|
6
|
-
this.collection = collection;
|
|
7
|
-
}
|
|
8
|
-
/**
|
|
9
|
-
* Add data to a database.
|
|
10
|
-
*/
|
|
11
|
-
async add(data, id_gen = true) {
|
|
12
|
-
return await this.db.add(this.collection, data, id_gen);
|
|
13
|
-
}
|
|
14
|
-
/**
|
|
15
|
-
* Find data in a database.
|
|
16
|
-
*/
|
|
17
|
-
async find(search, context = {}, options = {}, findOpts = {}) {
|
|
18
|
-
return await this.db.find(this.collection, search, context, options, findOpts);
|
|
19
|
-
}
|
|
20
|
-
/**
|
|
21
|
-
* Find one data entry in a database.
|
|
22
|
-
*/
|
|
23
|
-
async findOne(search, context = {}, findOpts = {}) {
|
|
24
|
-
return await this.db.findOne(this.collection, search, context, findOpts);
|
|
25
|
-
}
|
|
26
|
-
/**
|
|
27
|
-
* Update data in a database.
|
|
28
|
-
*/
|
|
29
|
-
async update(search, updater, context = {}) {
|
|
30
|
-
return await this.db.update(this.collection, search, updater, context);
|
|
31
|
-
}
|
|
32
|
-
/**
|
|
33
|
-
* Update one data entry in a database.
|
|
34
|
-
*/
|
|
35
|
-
async updateOne(search, updater, context = {}) {
|
|
36
|
-
return await this.db.updateOne(this.collection, search, updater, context);
|
|
37
|
-
}
|
|
38
|
-
/**
|
|
39
|
-
* Remove data from a database.
|
|
40
|
-
*/
|
|
41
|
-
async remove(search, context = {}) {
|
|
42
|
-
return await this.db.remove(this.collection, search, context);
|
|
43
|
-
}
|
|
44
|
-
/**
|
|
45
|
-
* Remove one data entry from a database.
|
|
46
|
-
*/
|
|
47
|
-
async removeOne(search, context = {}) {
|
|
48
|
-
return await this.db.removeOne(this.collection, search, context);
|
|
49
|
-
}
|
|
50
|
-
/**
|
|
51
|
-
* Asynchronously updates one entry in a database or adds a new one if it doesn't exist.
|
|
52
|
-
*/
|
|
53
|
-
async updateOneOrAdd(search, updater, add_arg = {}, context = {}, id_gen = true) {
|
|
54
|
-
return await this.db.updateOneOrAdd(this.collection, search, updater, add_arg, context, id_gen);
|
|
55
|
-
}
|
|
56
|
-
}
|
|
57
|
-
export default CollectionManager;
|
|
@@ -1,28 +0,0 @@
|
|
|
1
|
-
interface Task {
|
|
2
|
-
func: Function;
|
|
3
|
-
param: any[];
|
|
4
|
-
resolve: Function;
|
|
5
|
-
reject: Function;
|
|
6
|
-
}
|
|
7
|
-
/**
|
|
8
|
-
* A simple executor for queuing and executing asynchronous operations sequentially.
|
|
9
|
-
* @class
|
|
10
|
-
*/
|
|
11
|
-
declare class executorC {
|
|
12
|
-
quote: Task[];
|
|
13
|
-
isExecuting: boolean;
|
|
14
|
-
/**
|
|
15
|
-
* Create a new executor instance.
|
|
16
|
-
* @constructor
|
|
17
|
-
*/
|
|
18
|
-
constructor();
|
|
19
|
-
/**
|
|
20
|
-
* Add an asynchronous operation to the execution queue.
|
|
21
|
-
*/
|
|
22
|
-
addOp(func: Function, ...param: any[]): Promise<unknown>;
|
|
23
|
-
/**
|
|
24
|
-
* Execute the queued asynchronous operations sequentially.
|
|
25
|
-
*/
|
|
26
|
-
execute(): Promise<void>;
|
|
27
|
-
}
|
|
28
|
-
export default executorC;
|
package/dist/helpers/executor.js
DELETED
|
@@ -1,45 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* A simple executor for queuing and executing asynchronous operations sequentially.
|
|
3
|
-
* @class
|
|
4
|
-
*/
|
|
5
|
-
class executorC {
|
|
6
|
-
quote;
|
|
7
|
-
isExecuting;
|
|
8
|
-
/**
|
|
9
|
-
* Create a new executor instance.
|
|
10
|
-
* @constructor
|
|
11
|
-
*/
|
|
12
|
-
constructor() {
|
|
13
|
-
this.quote = [];
|
|
14
|
-
this.isExecuting = false;
|
|
15
|
-
}
|
|
16
|
-
/**
|
|
17
|
-
* Add an asynchronous operation to the execution queue.
|
|
18
|
-
*/
|
|
19
|
-
async addOp(func, ...param) {
|
|
20
|
-
return await new Promise((resolve, reject) => {
|
|
21
|
-
this.quote.push({
|
|
22
|
-
func,
|
|
23
|
-
param,
|
|
24
|
-
resolve,
|
|
25
|
-
reject
|
|
26
|
-
});
|
|
27
|
-
this.execute();
|
|
28
|
-
});
|
|
29
|
-
}
|
|
30
|
-
/**
|
|
31
|
-
* Execute the queued asynchronous operations sequentially.
|
|
32
|
-
*/
|
|
33
|
-
async execute() {
|
|
34
|
-
if (this.isExecuting)
|
|
35
|
-
return;
|
|
36
|
-
this.isExecuting = true;
|
|
37
|
-
while (this.quote.length > 0) {
|
|
38
|
-
let q = this.quote.shift();
|
|
39
|
-
let res = await q.func(...q.param);
|
|
40
|
-
q.resolve(res);
|
|
41
|
-
}
|
|
42
|
-
this.isExecuting = false;
|
|
43
|
-
}
|
|
44
|
-
}
|
|
45
|
-
export default executorC;
|
package/dist/helpers/format.d.ts
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
/**
|
|
2
|
-
* Parses given string into a JSON object. If the string does not start with
|
|
3
|
-
* a {, it is wrapped in one. This allows for a shorthand when
|
|
4
|
-
* storing/reading data from a file.
|
|
5
|
-
*/
|
|
6
|
-
export declare function parse(data: string): any;
|
|
7
|
-
/**
|
|
8
|
-
* Converts given object to a string. If the string is a valid json5, it is
|
|
9
|
-
* returned as is. If it is a valid json5 wrapped in {}, the curly brackets
|
|
10
|
-
* are removed. Otherwise the string is wrapped in {}.
|
|
11
|
-
*/
|
|
12
|
-
export declare function stringify(data: any): any;
|
package/dist/helpers/format.js
DELETED
|
@@ -1,23 +0,0 @@
|
|
|
1
|
-
import json5 from "json5";
|
|
2
|
-
/**
|
|
3
|
-
* Parses given string into a JSON object. If the string does not start with
|
|
4
|
-
* a {, it is wrapped in one. This allows for a shorthand when
|
|
5
|
-
* storing/reading data from a file.
|
|
6
|
-
*/
|
|
7
|
-
export function parse(data) {
|
|
8
|
-
if (!data.startsWith("{"))
|
|
9
|
-
data = "{" + data + "}";
|
|
10
|
-
return json5.parse(data);
|
|
11
|
-
}
|
|
12
|
-
/**
|
|
13
|
-
* Converts given object to a string. If the string is a valid json5, it is
|
|
14
|
-
* returned as is. If it is a valid json5 wrapped in {}, the curly brackets
|
|
15
|
-
* are removed. Otherwise the string is wrapped in {}.
|
|
16
|
-
*/
|
|
17
|
-
export function stringify(data) {
|
|
18
|
-
data = json5.stringify(data);
|
|
19
|
-
if (data.startsWith("{")) {
|
|
20
|
-
data = data.slice(1, -1);
|
|
21
|
-
}
|
|
22
|
-
return data;
|
|
23
|
-
}
|
package/dist/helpers/gen.d.ts
DELETED
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
import Id from "../types/Id.js";
|
|
2
|
-
/**
|
|
3
|
-
* Generates a unique random identifier based on time and parts.
|
|
4
|
-
*
|
|
5
|
-
* @param {number[]} [parts] - an array of lengths of parts of the identifier
|
|
6
|
-
* @returns {Id} - a new unique identifier
|
|
7
|
-
*/
|
|
8
|
-
export default function genId(parts?: number[]): Id;
|
package/dist/helpers/gen.js
DELETED
|
@@ -1,134 +0,0 @@
|
|
|
1
|
-
const usedIdsMap = new Map();
|
|
2
|
-
let lastId;
|
|
3
|
-
const recentIdsTimestamps = [];
|
|
4
|
-
let startIndex = 0;
|
|
5
|
-
let lastGeneratedMs = 0;
|
|
6
|
-
let lastRandomValue = 0;
|
|
7
|
-
/**
|
|
8
|
-
* Generates a unique random identifier based on time and parts.
|
|
9
|
-
*
|
|
10
|
-
* @param {number[]} [parts] - an array of lengths of parts of the identifier
|
|
11
|
-
* @returns {Id} - a new unique identifier
|
|
12
|
-
*/
|
|
13
|
-
export default function genId(parts = null) {
|
|
14
|
-
if (parts === null)
|
|
15
|
-
parts = [1, 1];
|
|
16
|
-
const time = getTime();
|
|
17
|
-
const id = getUniqueRandom({
|
|
18
|
-
time,
|
|
19
|
-
partsSchema: parts,
|
|
20
|
-
s: 0,
|
|
21
|
-
});
|
|
22
|
-
return id;
|
|
23
|
-
}
|
|
24
|
-
/**
|
|
25
|
-
* Generates a unique random identifier based on time and parts.
|
|
26
|
-
*/
|
|
27
|
-
function getUniqueRandom(opts) {
|
|
28
|
-
while (true) {
|
|
29
|
-
let minValue = 0;
|
|
30
|
-
if (lastId) {
|
|
31
|
-
const parts = lastId.split("-");
|
|
32
|
-
const lastTime = parts.shift();
|
|
33
|
-
if (lastTime === opts.time) {
|
|
34
|
-
const int36 = parts.join("");
|
|
35
|
-
minValue = parseInt(int36, 36) + 1;
|
|
36
|
-
}
|
|
37
|
-
}
|
|
38
|
-
const partsLengthSum = opts.partsSchema.reduce((acc, num) => acc + num, 0);
|
|
39
|
-
const partsData = generateBase36InRange(minValue, partsLengthSum);
|
|
40
|
-
const parts = splitStringByArray(opts.partsSchema, partsData);
|
|
41
|
-
const id = [opts.time, ...parts].join("-");
|
|
42
|
-
if (!usedIdsMap.has(id)) {
|
|
43
|
-
usedIdsMap.set(id, true);
|
|
44
|
-
setTimeout(() => usedIdsMap.delete(id), 1000);
|
|
45
|
-
lastId = id;
|
|
46
|
-
return id;
|
|
47
|
-
}
|
|
48
|
-
opts.s++;
|
|
49
|
-
if (opts.s >= partsLengthSum) {
|
|
50
|
-
opts.time = getTime();
|
|
51
|
-
opts.s = 0;
|
|
52
|
-
}
|
|
53
|
-
}
|
|
54
|
-
}
|
|
55
|
-
/**
|
|
56
|
-
* Tracks the current load of the application by counting the number of ids that have been generated in the last second.
|
|
57
|
-
* @returns The number of ids that have been generated in the last second.
|
|
58
|
-
*/
|
|
59
|
-
function trackLoad() {
|
|
60
|
-
const now = Date.now();
|
|
61
|
-
recentIdsTimestamps.push(now);
|
|
62
|
-
while (startIndex < recentIdsTimestamps.length && recentIdsTimestamps[startIndex] < now - 1) {
|
|
63
|
-
startIndex++;
|
|
64
|
-
}
|
|
65
|
-
return recentIdsTimestamps.length - startIndex;
|
|
66
|
-
}
|
|
67
|
-
/**
|
|
68
|
-
* Generates a base-36 encoded string with a specified length based on a random value within a range.
|
|
69
|
-
*
|
|
70
|
-
* The function calculates a random value within the base-36 range determined by the provided
|
|
71
|
-
* `minValue` and `length`. It uses a bias mechanism to adjust the randomness based on the
|
|
72
|
-
* current load, ensuring unique generation over short periods. If the system load is low or
|
|
73
|
-
* the current millisecond has changed, a new random value is generated. Otherwise, the random
|
|
74
|
-
* value is incremented by a small amount with certain probabilities.
|
|
75
|
-
*
|
|
76
|
-
* @param minValue - The minimum value for the base-36 encoded number.
|
|
77
|
-
* @param length - The length of the resulting base-36 string.
|
|
78
|
-
* @returns A base-36 encoded string representation of the random value, padded to the specified length.
|
|
79
|
-
*/
|
|
80
|
-
function generateBase36InRange(minValue, length) {
|
|
81
|
-
const maxValue = Math.pow(36, length) - 1;
|
|
82
|
-
const load = trackLoad();
|
|
83
|
-
const currentMs = Date.now();
|
|
84
|
-
if (load < 3 || currentMs !== lastGeneratedMs) {
|
|
85
|
-
lastRandomValue = biasedRandomInRange(minValue, maxValue);
|
|
86
|
-
lastGeneratedMs = currentMs;
|
|
87
|
-
}
|
|
88
|
-
else {
|
|
89
|
-
const rand = Math.random();
|
|
90
|
-
if (rand < 0.6) {
|
|
91
|
-
lastRandomValue += 1;
|
|
92
|
-
}
|
|
93
|
-
else if (rand < 0.9) {
|
|
94
|
-
lastRandomValue += 2;
|
|
95
|
-
}
|
|
96
|
-
else {
|
|
97
|
-
lastRandomValue = biasedRandomInRange(lastRandomValue, maxValue);
|
|
98
|
-
}
|
|
99
|
-
}
|
|
100
|
-
return lastRandomValue.toString(36).padStart(length, "0");
|
|
101
|
-
}
|
|
102
|
-
/**
|
|
103
|
-
* Generates a random number between the specified range, but with a bias towards the lower
|
|
104
|
-
* end of the range. The bias is calculated as the cube root of the random value, which
|
|
105
|
-
* will make the random value more likely to be closer to the minimum value.
|
|
106
|
-
* @param min - The minimum value of the range.
|
|
107
|
-
* @param max - The maximum value of the range.
|
|
108
|
-
* @returns A random number between the specified range, with a bias towards the lower end.
|
|
109
|
-
*/
|
|
110
|
-
function biasedRandomInRange(min, max) {
|
|
111
|
-
let randomValue = min;
|
|
112
|
-
const bias = Math.pow(Math.random(), 3);
|
|
113
|
-
randomValue = Math.floor(min + (max - min) * bias);
|
|
114
|
-
return Math.min(randomValue, max);
|
|
115
|
-
}
|
|
116
|
-
/**
|
|
117
|
-
* Splits a string into an array of substrings, where each substring is determined by
|
|
118
|
-
* the values in the provided array.
|
|
119
|
-
*
|
|
120
|
-
* @param arr - An array of numbers, where each number represents the length of a substring.
|
|
121
|
-
* @param str - The string to split.
|
|
122
|
-
* @returns An array of substrings, where each element is a substring of the original string,
|
|
123
|
-
* determined by the corresponding element in the provided array.
|
|
124
|
-
*/
|
|
125
|
-
function splitStringByArray(arr, str) {
|
|
126
|
-
let start = 0;
|
|
127
|
-
return arr.map(length => str.slice(start, start += length));
|
|
128
|
-
}
|
|
129
|
-
/**
|
|
130
|
-
* Gets the current time in a base36 string format.
|
|
131
|
-
*/
|
|
132
|
-
function getTime() {
|
|
133
|
-
return new Date().getTime().toString(36);
|
|
134
|
-
}
|
|
@@ -1,10 +0,0 @@
|
|
|
1
|
-
import { Search } from "../types/arg.js";
|
|
2
|
-
import { DbFindOpts } from "../types/options.js";
|
|
3
|
-
import { RelationTypes } from "../types/relation.js";
|
|
4
|
-
declare class Relation {
|
|
5
|
-
dbs: RelationTypes.DBS;
|
|
6
|
-
constructor(dbs: RelationTypes.DBS);
|
|
7
|
-
findOne(path: RelationTypes.Path, search: Search, relations: RelationTypes.Relation, select?: string[][] | Record<string, any>): Promise<any>;
|
|
8
|
-
find(path: RelationTypes.Path, search: Search, relations: RelationTypes.Relation, select?: string[][] | Record<string, any>, findOpts?: DbFindOpts): Promise<any[]>;
|
|
9
|
-
}
|
|
10
|
-
export default Relation;
|
package/dist/helpers/relation.js
DELETED
|
@@ -1,155 +0,0 @@
|
|
|
1
|
-
function pickByPath(obj, paths) {
|
|
2
|
-
const result = {};
|
|
3
|
-
for (const path of paths) {
|
|
4
|
-
let src = obj;
|
|
5
|
-
let dst = result;
|
|
6
|
-
for (let i = 0; i < path.length; i++) {
|
|
7
|
-
const k = path[i];
|
|
8
|
-
if (src == null)
|
|
9
|
-
break;
|
|
10
|
-
if (i === path.length - 1) {
|
|
11
|
-
dst[k] = src[k];
|
|
12
|
-
}
|
|
13
|
-
else {
|
|
14
|
-
dst[k] ||= {};
|
|
15
|
-
dst = dst[k];
|
|
16
|
-
src = src[k];
|
|
17
|
-
}
|
|
18
|
-
}
|
|
19
|
-
}
|
|
20
|
-
return result;
|
|
21
|
-
}
|
|
22
|
-
function autoSelect(rel, key) {
|
|
23
|
-
const select = Array.isArray(rel.select) ? [...rel.select] : undefined;
|
|
24
|
-
const shouldDelete = select && !select.includes(key);
|
|
25
|
-
if (shouldDelete)
|
|
26
|
-
select.push(key);
|
|
27
|
-
return [select, shouldDelete];
|
|
28
|
-
}
|
|
29
|
-
function convertSearchObjToSearchArray(obj, parentKeys = []) {
|
|
30
|
-
return Object.entries(obj).reduce((acc, [key, value]) => {
|
|
31
|
-
const currentPath = [...parentKeys, key];
|
|
32
|
-
if (!value) {
|
|
33
|
-
return acc;
|
|
34
|
-
}
|
|
35
|
-
else if (typeof value === 'object' && value !== null && !Array.isArray(value)) {
|
|
36
|
-
return [...acc, ...convertSearchObjToSearchArray(value, currentPath)];
|
|
37
|
-
}
|
|
38
|
-
else {
|
|
39
|
-
return [...acc, currentPath];
|
|
40
|
-
}
|
|
41
|
-
}, []);
|
|
42
|
-
}
|
|
43
|
-
async function processRelations(dbs, cfg, data, parentList = null) {
|
|
44
|
-
if (!data && !parentList)
|
|
45
|
-
return;
|
|
46
|
-
const batchMode = Array.isArray(parentList);
|
|
47
|
-
const targets = batchMode ? parentList : [data];
|
|
48
|
-
for (const key in cfg) {
|
|
49
|
-
if (!cfg.hasOwnProperty(key))
|
|
50
|
-
continue;
|
|
51
|
-
const rel = cfg[key];
|
|
52
|
-
const { pk = "_id", fk = "_id", type = "1", path, as = key, select, findOpts = {}, through } = rel;
|
|
53
|
-
const [dbKey, coll] = path;
|
|
54
|
-
const db = dbs[dbKey];
|
|
55
|
-
if (type === "1") {
|
|
56
|
-
const keys = [...new Set(targets.map(i => i[pk]))];
|
|
57
|
-
const [selectSafe, deleteSelect] = autoSelect(rel, fk);
|
|
58
|
-
const results = await db.find(coll, { $in: { [fk]: keys } }, {}, {}, { select: selectSafe });
|
|
59
|
-
const map = new Map(results.map(row => [row[fk], row]));
|
|
60
|
-
for (const item of targets) {
|
|
61
|
-
const result = map.get(item[pk]) || null;
|
|
62
|
-
if (result && rel.relations) {
|
|
63
|
-
await processRelations(dbs, rel.relations, result);
|
|
64
|
-
}
|
|
65
|
-
if (deleteSelect && result)
|
|
66
|
-
delete result[fk];
|
|
67
|
-
item[as] = result;
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
else if (type === "11") {
|
|
71
|
-
const cache = new Map();
|
|
72
|
-
const [selectSafe, deleteSelect] = autoSelect(rel, fk);
|
|
73
|
-
for (const item of targets) {
|
|
74
|
-
const id = item[pk];
|
|
75
|
-
if (!cache.has(id)) {
|
|
76
|
-
cache.set(id, await db.findOne(coll, { [fk]: id }, {}, { select: selectSafe }));
|
|
77
|
-
}
|
|
78
|
-
const result = cache.get(id) || null;
|
|
79
|
-
if (result && rel.relations) {
|
|
80
|
-
await processRelations(dbs, rel.relations, result);
|
|
81
|
-
}
|
|
82
|
-
if (deleteSelect && result)
|
|
83
|
-
delete result[fk];
|
|
84
|
-
item[as] = result;
|
|
85
|
-
}
|
|
86
|
-
}
|
|
87
|
-
else if (type === "1n") {
|
|
88
|
-
const ids = targets.map(i => i[pk]);
|
|
89
|
-
const [selectSafe, deleteSelect] = autoSelect(rel, fk);
|
|
90
|
-
const results = await db.find(coll, { $in: { [fk]: ids } }, {}, findOpts || {}, { select: selectSafe });
|
|
91
|
-
const grouped = results.reduce((acc, row) => {
|
|
92
|
-
const id = row[fk];
|
|
93
|
-
(acc[id] ||= []).push(row);
|
|
94
|
-
return acc;
|
|
95
|
-
}, {});
|
|
96
|
-
for (const item of targets) {
|
|
97
|
-
item[as] = grouped[item[pk]] || [];
|
|
98
|
-
}
|
|
99
|
-
if (rel.relations) {
|
|
100
|
-
await Promise.all(results.map(row => processRelations(dbs, rel.relations, row)));
|
|
101
|
-
}
|
|
102
|
-
if (deleteSelect)
|
|
103
|
-
for (const r of results)
|
|
104
|
-
delete r[fk];
|
|
105
|
-
}
|
|
106
|
-
else if (type === "nm") {
|
|
107
|
-
if (!through || !through.table || !through.pk || !through.fk) {
|
|
108
|
-
throw new Error(`Relation type "nm" requires a defined 'through' in '${key}'`);
|
|
109
|
-
}
|
|
110
|
-
for (const item of targets) {
|
|
111
|
-
const pivotDb = dbs[through.db || dbKey];
|
|
112
|
-
const pivots = await pivotDb.find(through.table, { [through.pk]: item[pk] });
|
|
113
|
-
const ids = pivots.map(p => p[through.fk]);
|
|
114
|
-
const related = await db.find(coll, { $in: { [fk]: ids } }, {}, {}, { select });
|
|
115
|
-
item[as] = related;
|
|
116
|
-
if (rel.relations) {
|
|
117
|
-
await Promise.all(related.map(row => processRelations(dbs, rel.relations, row)));
|
|
118
|
-
}
|
|
119
|
-
}
|
|
120
|
-
}
|
|
121
|
-
else {
|
|
122
|
-
throw new Error(`Unknown relation type: ${type}`);
|
|
123
|
-
}
|
|
124
|
-
}
|
|
125
|
-
}
|
|
126
|
-
class Relation {
|
|
127
|
-
dbs;
|
|
128
|
-
constructor(dbs) {
|
|
129
|
-
this.dbs = dbs;
|
|
130
|
-
}
|
|
131
|
-
async findOne(path, search, relations, select) {
|
|
132
|
-
const [dbKey, coll] = path;
|
|
133
|
-
const db = this.dbs[dbKey];
|
|
134
|
-
const data = await db.findOne(coll, search);
|
|
135
|
-
if (!data)
|
|
136
|
-
return null;
|
|
137
|
-
if (typeof select === "object" && !Array.isArray(select)) {
|
|
138
|
-
select = convertSearchObjToSearchArray(select);
|
|
139
|
-
}
|
|
140
|
-
await processRelations(this.dbs, relations, data);
|
|
141
|
-
return select ? pickByPath(data, select) : data;
|
|
142
|
-
}
|
|
143
|
-
async find(path, search, relations, select, findOpts = {}) {
|
|
144
|
-
const [dbKey, coll] = path;
|
|
145
|
-
const db = this.dbs[dbKey];
|
|
146
|
-
const data = await db.find(coll, search, {}, findOpts);
|
|
147
|
-
if (relations)
|
|
148
|
-
await processRelations(this.dbs, relations, null, data);
|
|
149
|
-
if (typeof select === "object" && !Array.isArray(select)) {
|
|
150
|
-
select = convertSearchObjToSearchArray(select);
|
|
151
|
-
}
|
|
152
|
-
return select ? data.map(d => pickByPath(d, select)) : data;
|
|
153
|
-
}
|
|
154
|
-
}
|
|
155
|
-
export default Relation;
|
|
@@ -1,18 +0,0 @@
|
|
|
1
|
-
function assignDataPush(data) {
|
|
2
|
-
if (typeof data !== "object" || Array.isArray(data))
|
|
3
|
-
return;
|
|
4
|
-
const obj = {};
|
|
5
|
-
for (const key of Object.keys(data)) {
|
|
6
|
-
if (key.startsWith("$")) {
|
|
7
|
-
Object.keys(data[key]).forEach((k) => {
|
|
8
|
-
obj[k] = data[key][k];
|
|
9
|
-
});
|
|
10
|
-
}
|
|
11
|
-
else
|
|
12
|
-
obj[key] = data[key];
|
|
13
|
-
}
|
|
14
|
-
return obj;
|
|
15
|
-
}
|
|
16
|
-
export function setDataUsingUpdateOneOrAdd(query) {
|
|
17
|
-
query.data = Object.assign({}, assignDataPush(query.search), assignDataPush(query.updater), assignDataPush(query.add_arg));
|
|
18
|
-
}
|
package/dist/types/Id.d.ts
DELETED
package/dist/types/Id.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
package/dist/types/arg.d.ts
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import Id from "./Id.js";
|
|
2
|
-
import { SearchOptions } from "./searchOpts.js";
|
|
3
|
-
import { Context } from "./types.js";
|
|
4
|
-
import { UpdaterArg } from "./updater.js";
|
|
5
|
-
export interface Arg {
|
|
6
|
-
_id?: Id;
|
|
7
|
-
[key: string]: any;
|
|
8
|
-
}
|
|
9
|
-
export type SearchFunc<T = any> = (data: T, context: Context) => boolean;
|
|
10
|
-
export type UpdaterFunc<T = any> = (data: T, context: Context) => boolean;
|
|
11
|
-
export type Search<T = any> = SearchOptions | SearchFunc<T>;
|
|
12
|
-
export type Updater<T = any> = UpdaterArg | UpdaterArg[] | UpdaterFunc<T>;
|
package/dist/types/arg.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
package/dist/types/data.d.ts
DELETED
package/dist/types/data.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|
package/dist/types/export.d.ts
DELETED
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
export declare namespace ValtheraTypes {
|
|
2
|
-
type Arg = import("./arg.js").Arg;
|
|
3
|
-
type Search = import("./arg.js").Search;
|
|
4
|
-
type Updater = import("./arg.js").Updater;
|
|
5
|
-
type DbFindOpts = import("./options.js").DbFindOpts;
|
|
6
|
-
type FindOpts = import("./options.js").FindOpts;
|
|
7
|
-
type DbOpts = import("./options.js").DbOpts;
|
|
8
|
-
type Data = import("./data.js").Data;
|
|
9
|
-
type SearchOptions = import("./searchOpts.js").SearchOptions;
|
|
10
|
-
type Id = import("./Id.js").Id;
|
|
11
|
-
}
|
package/dist/types/export.js
DELETED
|
@@ -1 +0,0 @@
|
|
|
1
|
-
export {};
|