@wxn0brp/db 0.0.5 → 0.0.7
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/README.md +4 -1
- package/dist/cjs/CollectionManager.d.ts +44 -0
- package/dist/cjs/CollectionManager.js +59 -0
- package/dist/cjs/action.d.ts +66 -0
- package/dist/cjs/action.js +193 -0
- package/dist/cjs/client/database.d.ts +72 -0
- package/dist/cjs/client/database.js +145 -0
- package/dist/cjs/client/function.d.ts +5 -0
- package/dist/cjs/client/function.js +32 -0
- package/dist/cjs/client/graph.d.ts +54 -0
- package/dist/cjs/client/graph.js +93 -0
- package/dist/cjs/client/remote.d.ts +16 -0
- package/dist/cjs/client/remote.js +2 -0
- package/dist/cjs/database.d.ts +69 -0
- package/dist/cjs/database.js +110 -0
- package/dist/cjs/executor.d.ts +28 -0
- package/{executor.js → dist/cjs/executor.js} +47 -54
- package/dist/cjs/file/find.d.ts +11 -0
- package/dist/cjs/file/find.js +80 -0
- package/dist/cjs/file/index.d.ts +3 -0
- package/dist/cjs/file/index.js +25 -0
- package/dist/cjs/file/remove.d.ts +7 -0
- package/dist/cjs/file/remove.js +61 -0
- package/dist/cjs/file/update.d.ts +7 -0
- package/dist/cjs/file/update.js +70 -0
- package/dist/cjs/file/utils.d.ts +8 -0
- package/dist/cjs/file/utils.js +23 -0
- package/dist/cjs/format.d.ts +18 -0
- package/dist/cjs/format.js +36 -0
- package/dist/cjs/gen.d.ts +5 -0
- package/dist/cjs/gen.js +78 -0
- package/dist/cjs/graph.d.ts +47 -0
- package/dist/cjs/graph.js +90 -0
- package/dist/cjs/index.d.ts +13 -0
- package/dist/cjs/index.js +18 -0
- package/dist/cjs/relation.d.ts +64 -0
- package/{relation.js → dist/cjs/relation.js} +26 -45
- package/dist/cjs/types/Id.d.ts +3 -0
- package/dist/cjs/types/Id.js +2 -0
- package/dist/cjs/types/arg.d.ts +12 -0
- package/dist/cjs/types/arg.js +2 -0
- package/dist/cjs/types/data.d.ts +4 -0
- package/dist/cjs/types/data.js +2 -0
- package/dist/cjs/types/options.d.ts +12 -0
- package/dist/cjs/types/options.js +2 -0
- package/dist/cjs/types/searchOpts.d.ts +61 -0
- package/dist/cjs/types/searchOpts.js +8 -0
- package/dist/cjs/types/types.d.ts +6 -0
- package/dist/cjs/types/types.js +2 -0
- package/dist/cjs/types/updater.d.ts +26 -0
- package/dist/cjs/types/updater.js +5 -0
- package/dist/cjs/utils/hasFields.d.ts +8 -0
- package/dist/cjs/utils/hasFields.js +22 -0
- package/dist/cjs/utils/hasFieldsAdvanced.d.ts +5 -0
- package/dist/cjs/utils/hasFieldsAdvanced.js +182 -0
- package/dist/cjs/utils/updateFindObject.d.ts +11 -0
- package/dist/cjs/utils/updateFindObject.js +32 -0
- package/dist/cjs/utils/updateObject.d.ts +7 -0
- package/dist/cjs/utils/updateObject.js +148 -0
- package/dist/esm/CollectionManager.d.ts +44 -0
- package/dist/esm/CollectionManager.js +57 -0
- package/dist/esm/action.d.ts +66 -0
- package/dist/esm/action.js +188 -0
- package/dist/esm/client/database.d.ts +72 -0
- package/dist/esm/client/database.js +140 -0
- package/dist/esm/client/function.d.ts +5 -0
- package/dist/esm/client/function.js +30 -0
- package/dist/esm/client/graph.d.ts +54 -0
- package/dist/esm/client/graph.js +88 -0
- package/dist/esm/client/remote.d.ts +16 -0
- package/dist/esm/client/remote.js +1 -0
- package/dist/esm/database.d.ts +69 -0
- package/dist/esm/database.js +105 -0
- package/dist/esm/executor.d.ts +28 -0
- package/dist/esm/executor.js +45 -0
- package/dist/esm/file/find.d.ts +11 -0
- package/dist/esm/file/find.js +73 -0
- package/dist/esm/file/index.d.ts +3 -0
- package/{file → dist/esm/file}/index.js +1 -1
- package/dist/esm/file/remove.d.ts +7 -0
- package/dist/esm/file/remove.js +56 -0
- package/dist/esm/file/update.d.ts +7 -0
- package/dist/esm/file/update.js +65 -0
- package/dist/esm/file/utils.d.ts +8 -0
- package/{file → dist/esm/file}/utils.js +3 -11
- package/dist/esm/format.d.ts +18 -0
- package/{format.js → dist/esm/format.js} +29 -29
- package/dist/esm/gen.d.ts +5 -0
- package/dist/esm/gen.js +75 -0
- package/dist/esm/graph.d.ts +47 -0
- package/dist/esm/graph.js +85 -0
- package/dist/esm/index.d.ts +13 -0
- package/dist/esm/index.js +7 -0
- package/dist/esm/relation.d.ts +64 -0
- package/dist/esm/relation.js +65 -0
- package/dist/esm/types/Id.d.ts +3 -0
- package/dist/esm/types/Id.js +1 -0
- package/dist/esm/types/arg.d.ts +12 -0
- package/dist/esm/types/arg.js +1 -0
- package/dist/esm/types/data.d.ts +4 -0
- package/dist/esm/types/data.js +1 -0
- package/dist/esm/types/options.d.ts +12 -0
- package/dist/esm/types/options.js +1 -0
- package/dist/esm/types/searchOpts.d.ts +61 -0
- package/dist/esm/types/searchOpts.js +7 -0
- package/dist/esm/types/types.d.ts +6 -0
- package/dist/esm/types/types.js +1 -0
- package/dist/esm/types/updater.d.ts +26 -0
- package/dist/esm/types/updater.js +4 -0
- package/dist/esm/utils/hasFields.d.ts +8 -0
- package/{utils → dist/esm/utils}/hasFields.js +4 -4
- package/dist/esm/utils/hasFieldsAdvanced.d.ts +5 -0
- package/dist/esm/utils/hasFieldsAdvanced.js +176 -0
- package/dist/esm/utils/updateFindObject.d.ts +11 -0
- package/{utils → dist/esm/utils}/updateFindObject.js +11 -16
- package/dist/esm/utils/updateObject.d.ts +7 -0
- package/dist/esm/utils/updateObject.js +145 -0
- package/package.json +52 -36
- package/CollectionManager.js +0 -119
- package/action.js +0 -258
- package/database.d.ts +0 -44
- package/database.js +0 -203
- package/docs/database.md +0 -140
- package/docs/graph.md +0 -86
- package/docs/relation.md +0 -51
- package/docs/remote.md +0 -30
- package/docs/remote_server.md +0 -35
- package/docs/search_opts.md +0 -227
- package/file/find.js +0 -89
- package/file/remove.js +0 -74
- package/file/update.js +0 -83
- package/gen.d.ts +0 -1
- package/gen.js +0 -97
- package/graph.d.ts +0 -27
- package/graph.js +0 -140
- package/index.d.ts +0 -7
- package/index.js +0 -15
- package/relation.d.ts +0 -23
- package/remote/client/database.d.ts +0 -41
- package/remote/client/database.js +0 -228
- package/remote/client/graph.d.ts +0 -31
- package/remote/client/graph.js +0 -148
- package/remote/server/auth.js +0 -100
- package/remote/server/db.js +0 -197
- package/remote/server/function.js +0 -43
- package/remote/server/graph.js +0 -136
- package/remote/server/gui/css/main.css +0 -130
- package/remote/server/gui/css/scrool.css +0 -81
- package/remote/server/gui/css/style.css +0 -61
- package/remote/server/gui/favicon.svg +0 -12
- package/remote/server/gui/html/data.html +0 -15
- package/remote/server/gui/html/main.html +0 -46
- package/remote/server/gui/html/nav.html +0 -25
- package/remote/server/gui/html/popup.html +0 -51
- package/remote/server/gui/index.html +0 -49
- package/remote/server/gui/js/api.js +0 -166
- package/remote/server/gui/js/index.js +0 -17
- package/remote/server/gui/js/loadHTML.js +0 -16
- package/remote/server/gui/js/popUp.js +0 -72
- package/remote/server/gui/js/queryApi.js +0 -51
- package/remote/server/gui/js/queryDb.js +0 -79
- package/remote/server/gui/js/queryGraph.js +0 -144
- package/remote/server/gui/js/render.js +0 -64
- package/remote/server/gui/js/templates.js +0 -31
- package/remote/server/gui/js/utils.js +0 -36
- package/remote/server/gui/js/vars.js +0 -9
- package/remote/server/gui/libs/core.js +0 -176
- package/remote/server/gui/libs/d3.v7.min.js +0 -2
- package/remote/server/gui/libs/handlebars.min.js +0 -29
- package/remote/server/gui/libs/json5.min.js +0 -1
- package/remote/server/index.js +0 -63
- package/remote/server/initDataBases.js +0 -20
- package/remote/server/pathUtils.js +0 -7
- package/remote/server/secret.js +0 -23
- package/remote/serverMgmt/index.js +0 -86
- package/test/hasFieldsAdvanced.test.js +0 -70
- package/utils/hasFieldsAdvanced.js +0 -184
- package/utils/updateObject.js +0 -15
package/dist/esm/gen.js
ADDED
|
@@ -0,0 +1,75 @@
|
|
|
1
|
+
const usedIdsMap = new Map();
|
|
2
|
+
/**
|
|
3
|
+
* Generates a unique identifier based on specified parts.
|
|
4
|
+
*/
|
|
5
|
+
export default function genId(parts = null, fill = 1) {
|
|
6
|
+
parts = changeInputToPartsArray(parts, fill);
|
|
7
|
+
const time = getTime();
|
|
8
|
+
const id = getUniqueRandom(time, parts);
|
|
9
|
+
return id;
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Generates a unique random identifier based on time and parts.
|
|
13
|
+
* @param time - The current time in a base36 string format.
|
|
14
|
+
* @param parts - An array of parts to be used for generating the identifier.
|
|
15
|
+
* @param s - Recursion counter for handling collision (default: 0).
|
|
16
|
+
* @returns {string} The unique random identifier.
|
|
17
|
+
*/
|
|
18
|
+
function getUniqueRandom(time, partsA, s = 0) {
|
|
19
|
+
const parts = partsA.map(l => getRandom(l));
|
|
20
|
+
const id = [time, ...parts].join("-");
|
|
21
|
+
if (usedIdsMap.has(id)) {
|
|
22
|
+
s++;
|
|
23
|
+
if (s < 25)
|
|
24
|
+
return getUniqueRandom(time, partsA, s);
|
|
25
|
+
partsA = addOneToPods(partsA);
|
|
26
|
+
time = getTime();
|
|
27
|
+
return getUniqueRandom(time, partsA);
|
|
28
|
+
}
|
|
29
|
+
usedIdsMap.set(id, Date.now() + 2000);
|
|
30
|
+
usedIdsMap.forEach((value, key) => {
|
|
31
|
+
if (value < Date.now())
|
|
32
|
+
usedIdsMap.delete(key);
|
|
33
|
+
});
|
|
34
|
+
return id;
|
|
35
|
+
}
|
|
36
|
+
/**
|
|
37
|
+
* Generates a random string of base36 characters.
|
|
38
|
+
*/
|
|
39
|
+
function getRandom(unix) {
|
|
40
|
+
return (Math.floor(Math.random() * Math.pow(36, unix))).toString(36);
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Gets the current time in a base36 string format.
|
|
44
|
+
*/
|
|
45
|
+
function getTime() {
|
|
46
|
+
return Math.floor(new Date().getTime() / 1000).toString(36);
|
|
47
|
+
}
|
|
48
|
+
/**
|
|
49
|
+
* Adds one to each part of the input array.
|
|
50
|
+
*/
|
|
51
|
+
function addOneToPods(array) {
|
|
52
|
+
const sum = array.reduce((acc, current) => acc + current, 0);
|
|
53
|
+
const num = sum + 1;
|
|
54
|
+
const len = array.length;
|
|
55
|
+
const result = [];
|
|
56
|
+
const quotient = Math.floor(num / len);
|
|
57
|
+
const remainder = num % len;
|
|
58
|
+
for (let i = 0; i < len; i++) {
|
|
59
|
+
if (i < remainder)
|
|
60
|
+
result.push(quotient + 1);
|
|
61
|
+
else
|
|
62
|
+
result.push(quotient);
|
|
63
|
+
}
|
|
64
|
+
return result;
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Converts input to an array of parts.
|
|
68
|
+
*/
|
|
69
|
+
function changeInputToPartsArray(parts = null, fill = 1) {
|
|
70
|
+
if (Array.isArray(parts))
|
|
71
|
+
return parts;
|
|
72
|
+
if (typeof parts == "number")
|
|
73
|
+
return Array(parts).fill(fill);
|
|
74
|
+
return [1, 1];
|
|
75
|
+
}
|
|
@@ -0,0 +1,47 @@
|
|
|
1
|
+
import DataBase from "./database.js";
|
|
2
|
+
import Data from "./types/data.js";
|
|
3
|
+
/**
|
|
4
|
+
* A class representing a graph database.
|
|
5
|
+
* @class
|
|
6
|
+
*/
|
|
7
|
+
declare class Graph {
|
|
8
|
+
db: DataBase;
|
|
9
|
+
constructor(databaseFolder: string);
|
|
10
|
+
/**
|
|
11
|
+
* Adds an edge between two nodes.
|
|
12
|
+
*/
|
|
13
|
+
add(collection: string, nodeA: string, nodeB: string): Promise<Data>;
|
|
14
|
+
/**
|
|
15
|
+
* Removes an edge between two nodes.
|
|
16
|
+
*/
|
|
17
|
+
remove(collection: string, nodeA: string, nodeB: string): Promise<boolean>;
|
|
18
|
+
/**
|
|
19
|
+
* Finds all edges with either node equal to `node`.
|
|
20
|
+
*/
|
|
21
|
+
find(collection: string, node: string): Promise<Data[]>;
|
|
22
|
+
/**
|
|
23
|
+
* Finds one edge with either node equal to `nodeA` and the other equal to `nodeB`.
|
|
24
|
+
*/
|
|
25
|
+
findOne(collection: any, nodeA: any, nodeB: any): Promise<Data>;
|
|
26
|
+
/**
|
|
27
|
+
* Gets all edges in the database.
|
|
28
|
+
*/
|
|
29
|
+
getAll(collection: any): Promise<Data[]>;
|
|
30
|
+
/**
|
|
31
|
+
* Get the names of all available databases.
|
|
32
|
+
*/
|
|
33
|
+
getCollections(): Promise<string[]>;
|
|
34
|
+
/**
|
|
35
|
+
* Check and create the specified collection if it doesn't exist.
|
|
36
|
+
*/
|
|
37
|
+
checkCollection(collection: any): Promise<void>;
|
|
38
|
+
/**
|
|
39
|
+
* Check if a collection exists.
|
|
40
|
+
*/
|
|
41
|
+
issetCollection(collection: any): Promise<boolean>;
|
|
42
|
+
/**
|
|
43
|
+
* Removes a database collection from the file system.
|
|
44
|
+
*/
|
|
45
|
+
removeCollection(collection: any): void;
|
|
46
|
+
}
|
|
47
|
+
export default Graph;
|
|
@@ -0,0 +1,85 @@
|
|
|
1
|
+
import DataBase from "./database.js";
|
|
2
|
+
/**
|
|
3
|
+
* A class representing a graph database.
|
|
4
|
+
* @class
|
|
5
|
+
*/
|
|
6
|
+
class Graph {
|
|
7
|
+
db;
|
|
8
|
+
constructor(databaseFolder) {
|
|
9
|
+
this.db = new DataBase(databaseFolder);
|
|
10
|
+
}
|
|
11
|
+
/**
|
|
12
|
+
* Adds an edge between two nodes.
|
|
13
|
+
*/
|
|
14
|
+
async add(collection, nodeA, nodeB) {
|
|
15
|
+
const sortedNodes = [nodeA, nodeB].sort();
|
|
16
|
+
return await this.db.add(collection, {
|
|
17
|
+
a: sortedNodes[0],
|
|
18
|
+
b: sortedNodes[1]
|
|
19
|
+
}, false);
|
|
20
|
+
}
|
|
21
|
+
/**
|
|
22
|
+
* Removes an edge between two nodes.
|
|
23
|
+
*/
|
|
24
|
+
async remove(collection, nodeA, nodeB) {
|
|
25
|
+
const sortedNodes = [nodeA, nodeB].sort();
|
|
26
|
+
const query = { a: sortedNodes[0], b: sortedNodes[1] };
|
|
27
|
+
return await this.db.removeOne(collection, query);
|
|
28
|
+
}
|
|
29
|
+
/**
|
|
30
|
+
* Finds all edges with either node equal to `node`.
|
|
31
|
+
*/
|
|
32
|
+
async find(collection, node) {
|
|
33
|
+
const edges = [];
|
|
34
|
+
const edgesByANode = await this.db.find(collection, { a: node });
|
|
35
|
+
const edgesByBNode = await this.db.find(collection, { b: node });
|
|
36
|
+
if (edgesByANode)
|
|
37
|
+
edges.push(...edgesByANode);
|
|
38
|
+
if (edgesByBNode)
|
|
39
|
+
edges.push(...edgesByBNode);
|
|
40
|
+
return edges;
|
|
41
|
+
}
|
|
42
|
+
/**
|
|
43
|
+
* Finds one edge with either node equal to `nodeA` and the other equal to `nodeB`.
|
|
44
|
+
*/
|
|
45
|
+
async findOne(collection, nodeA, nodeB) {
|
|
46
|
+
const edgeAB = await this.db.findOne(collection, { a: nodeA, b: nodeB });
|
|
47
|
+
if (edgeAB)
|
|
48
|
+
return edgeAB;
|
|
49
|
+
const edgeBA = await this.db.findOne(collection, { a: nodeB, b: nodeA });
|
|
50
|
+
if (edgeBA)
|
|
51
|
+
return edgeBA;
|
|
52
|
+
return null;
|
|
53
|
+
}
|
|
54
|
+
/**
|
|
55
|
+
* Gets all edges in the database.
|
|
56
|
+
*/
|
|
57
|
+
async getAll(collection) {
|
|
58
|
+
return await this.db.find(collection, {});
|
|
59
|
+
}
|
|
60
|
+
/**
|
|
61
|
+
* Get the names of all available databases.
|
|
62
|
+
*/
|
|
63
|
+
async getCollections() {
|
|
64
|
+
return await this.db.getCollections();
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Check and create the specified collection if it doesn't exist.
|
|
68
|
+
*/
|
|
69
|
+
async checkCollection(collection) {
|
|
70
|
+
await this.db.checkCollection(collection);
|
|
71
|
+
}
|
|
72
|
+
/**
|
|
73
|
+
* Check if a collection exists.
|
|
74
|
+
*/
|
|
75
|
+
async issetCollection(collection) {
|
|
76
|
+
return await this.db.issetCollection(collection);
|
|
77
|
+
}
|
|
78
|
+
/**
|
|
79
|
+
* Removes a database collection from the file system.
|
|
80
|
+
*/
|
|
81
|
+
removeCollection(collection) {
|
|
82
|
+
this.db.removeCollection(collection);
|
|
83
|
+
}
|
|
84
|
+
}
|
|
85
|
+
export default Graph;
|
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
import DataBase from "./database.js";
|
|
2
|
+
import Graph from "./graph.js";
|
|
3
|
+
import DataBaseRemote from "./client/database.js";
|
|
4
|
+
import GraphRemote from "./client/graph.js";
|
|
5
|
+
import genId from "./gen.js";
|
|
6
|
+
import Relation from "./relation.js";
|
|
7
|
+
export { DataBase, Graph, DataBaseRemote, GraphRemote, Relation, genId };
|
|
8
|
+
import type Id from "./types/Id.js";
|
|
9
|
+
import type { Arg, Search, Updater } from "./types/arg.js";
|
|
10
|
+
import type { DbFindOpts, FindOpts, DbOpts } from "./types/options.js";
|
|
11
|
+
import type Data from "./types/data.js";
|
|
12
|
+
import type { SearchOptions } from "./types/searchOpts.js";
|
|
13
|
+
export type { Id, Arg, Search, Updater, DbFindOpts, FindOpts, DbOpts, Data, SearchOptions };
|
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
import DataBase from "./database.js";
|
|
2
|
+
import Graph from "./graph.js";
|
|
3
|
+
import DataBaseRemote from "./client/database.js";
|
|
4
|
+
import GraphRemote from "./client/graph.js";
|
|
5
|
+
import genId from "./gen.js";
|
|
6
|
+
import Relation from "./relation.js";
|
|
7
|
+
export { DataBase, Graph, DataBaseRemote, GraphRemote, Relation, genId };
|
|
@@ -0,0 +1,64 @@
|
|
|
1
|
+
import DataBase from "./database.js";
|
|
2
|
+
import { Search } from "./types/arg.js";
|
|
3
|
+
import { DbFindOpts } from "./types/options.js";
|
|
4
|
+
export interface Databases {
|
|
5
|
+
[key: string]: DataBase;
|
|
6
|
+
}
|
|
7
|
+
declare class Relation {
|
|
8
|
+
databases: Databases;
|
|
9
|
+
constructor(databases: Databases);
|
|
10
|
+
/**
|
|
11
|
+
* Resolves the relation path in format 'dbName.collectionName'
|
|
12
|
+
*/
|
|
13
|
+
_resolvePath(path: string): {
|
|
14
|
+
db: DataBase;
|
|
15
|
+
collection: string;
|
|
16
|
+
};
|
|
17
|
+
/**
|
|
18
|
+
* Processes relations for a single item
|
|
19
|
+
* @param {Object} item - Item to process relations for
|
|
20
|
+
* @param {Object} relations - Relations configuration
|
|
21
|
+
* @returns {Promise<Object>} Processed item with resolved relations
|
|
22
|
+
*/
|
|
23
|
+
_processItemRelations(item: Object, relations: Object): Promise<{
|
|
24
|
+
constructor: Function;
|
|
25
|
+
toString(): string;
|
|
26
|
+
toLocaleString(): string;
|
|
27
|
+
valueOf(): Object;
|
|
28
|
+
hasOwnProperty(v: PropertyKey): boolean;
|
|
29
|
+
isPrototypeOf(v: Object): boolean;
|
|
30
|
+
propertyIsEnumerable(v: PropertyKey): boolean;
|
|
31
|
+
}>;
|
|
32
|
+
/**
|
|
33
|
+
* Finds items with relations
|
|
34
|
+
* @param path - Path in format 'dbName.collectionName'
|
|
35
|
+
* @param search - Search query or function
|
|
36
|
+
* @param relations - Relations configuration
|
|
37
|
+
* @param options - Search options
|
|
38
|
+
*/
|
|
39
|
+
find(path: string, search: Search, relations?: {}, options?: DbFindOpts): Promise<{
|
|
40
|
+
constructor: Function;
|
|
41
|
+
toString(): string;
|
|
42
|
+
toLocaleString(): string;
|
|
43
|
+
valueOf(): Object;
|
|
44
|
+
hasOwnProperty(v: PropertyKey): boolean;
|
|
45
|
+
isPrototypeOf(v: Object): boolean;
|
|
46
|
+
propertyIsEnumerable(v: PropertyKey): boolean;
|
|
47
|
+
}[]>;
|
|
48
|
+
/**
|
|
49
|
+
* Finds one item with relations
|
|
50
|
+
* @param path - Path in format 'dbName.collectionName'
|
|
51
|
+
* @param search - Search query or function
|
|
52
|
+
* @param relations - Relations configuration
|
|
53
|
+
*/
|
|
54
|
+
findOne(path: string, search: Search, relations?: Object): Promise<{
|
|
55
|
+
constructor: Function;
|
|
56
|
+
toString(): string;
|
|
57
|
+
toLocaleString(): string;
|
|
58
|
+
valueOf(): Object;
|
|
59
|
+
hasOwnProperty(v: PropertyKey): boolean;
|
|
60
|
+
isPrototypeOf(v: Object): boolean;
|
|
61
|
+
propertyIsEnumerable(v: PropertyKey): boolean;
|
|
62
|
+
}>;
|
|
63
|
+
}
|
|
64
|
+
export default Relation;
|
|
@@ -0,0 +1,65 @@
|
|
|
1
|
+
class Relation {
|
|
2
|
+
databases;
|
|
3
|
+
constructor(databases) {
|
|
4
|
+
this.databases = databases;
|
|
5
|
+
}
|
|
6
|
+
/**
|
|
7
|
+
* Resolves the relation path in format 'dbName.collectionName'
|
|
8
|
+
*/
|
|
9
|
+
_resolvePath(path) {
|
|
10
|
+
const sanitizedPath = path.replace(/\\\./g, '\uffff');
|
|
11
|
+
const separatorIndex = sanitizedPath.indexOf('.');
|
|
12
|
+
if (separatorIndex === -1)
|
|
13
|
+
throw new Error(`Invalid path format "${path}". Expected format 'dbName.collectionName'.`);
|
|
14
|
+
const dbName = sanitizedPath.slice(0, separatorIndex).replace(/\uffff/g, '.');
|
|
15
|
+
const collectionName = sanitizedPath.slice(separatorIndex + 1).replace(/\uffff/g, '.');
|
|
16
|
+
if (!this.databases[dbName])
|
|
17
|
+
throw new Error(`Database "${dbName}" not found`);
|
|
18
|
+
return { db: this.databases[dbName], collection: collectionName };
|
|
19
|
+
}
|
|
20
|
+
/**
|
|
21
|
+
* Processes relations for a single item
|
|
22
|
+
* @param {Object} item - Item to process relations for
|
|
23
|
+
* @param {Object} relations - Relations configuration
|
|
24
|
+
* @returns {Promise<Object>} Processed item with resolved relations
|
|
25
|
+
*/
|
|
26
|
+
async _processItemRelations(item, relations) {
|
|
27
|
+
const result = { ...item };
|
|
28
|
+
for (const [field, relationConfig] of Object.entries(relations)) {
|
|
29
|
+
const { from, localField, foreignField, as, multiple = false } = relationConfig;
|
|
30
|
+
const { db, collection } = this._resolvePath(from);
|
|
31
|
+
const searchQuery = { [foreignField]: item[localField] };
|
|
32
|
+
const fn = multiple ? db.find : db.findOne;
|
|
33
|
+
const relatedItem = await fn(collection, searchQuery);
|
|
34
|
+
result[as || field] = relatedItem;
|
|
35
|
+
}
|
|
36
|
+
return result;
|
|
37
|
+
}
|
|
38
|
+
/**
|
|
39
|
+
* Finds items with relations
|
|
40
|
+
* @param path - Path in format 'dbName.collectionName'
|
|
41
|
+
* @param search - Search query or function
|
|
42
|
+
* @param relations - Relations configuration
|
|
43
|
+
* @param options - Search options
|
|
44
|
+
*/
|
|
45
|
+
async find(path, search, relations = {}, options = {}) {
|
|
46
|
+
const { db, collection } = this._resolvePath(path);
|
|
47
|
+
const items = await db.find(collection, search, {}, options);
|
|
48
|
+
const results = await Promise.all(items.map(item => this._processItemRelations(item, relations)));
|
|
49
|
+
return results;
|
|
50
|
+
}
|
|
51
|
+
/**
|
|
52
|
+
* Finds one item with relations
|
|
53
|
+
* @param path - Path in format 'dbName.collectionName'
|
|
54
|
+
* @param search - Search query or function
|
|
55
|
+
* @param relations - Relations configuration
|
|
56
|
+
*/
|
|
57
|
+
async findOne(path, search, relations = {}) {
|
|
58
|
+
const { db, collection } = this._resolvePath(path);
|
|
59
|
+
const item = await db.findOne(collection, search);
|
|
60
|
+
if (!item)
|
|
61
|
+
return null;
|
|
62
|
+
return await this._processItemRelations(item, relations);
|
|
63
|
+
}
|
|
64
|
+
}
|
|
65
|
+
export default Relation;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,12 @@
|
|
|
1
|
+
import Id from "./Id";
|
|
2
|
+
import { SearchOptions } from "./searchOpts";
|
|
3
|
+
import { Context } from "./types";
|
|
4
|
+
import { UpdaterArg } from "./updater";
|
|
5
|
+
export interface Arg {
|
|
6
|
+
_id?: Id;
|
|
7
|
+
[key: string]: any;
|
|
8
|
+
}
|
|
9
|
+
export type SearchFunc<T> = (data: T, context: Context) => boolean;
|
|
10
|
+
export type UpdaterFunc<T> = (data: T, context: Context) => boolean;
|
|
11
|
+
export type Search<T = any> = (Arg & SearchOptions) | SearchFunc<T>;
|
|
12
|
+
export type Updater<T = any> = UpdaterArg | UpdaterArg[] | UpdaterFunc<T>;
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,61 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Predefined Search Options Quick Reference
|
|
3
|
+
*
|
|
4
|
+
* This module defines the types and structures for search operators used
|
|
5
|
+
* to validate and query data objects.
|
|
6
|
+
*/
|
|
7
|
+
/** Logical Operators */
|
|
8
|
+
export type LogicalOperators = {
|
|
9
|
+
/**
|
|
10
|
+
* Recursively applies multiple conditions, all of which must evaluate to true.
|
|
11
|
+
* Can include other operators such as $gt, $exists, or nested $and/$or conditions.
|
|
12
|
+
*/
|
|
13
|
+
$and?: Array<PredefinedSearchOperators>;
|
|
14
|
+
/**
|
|
15
|
+
* Recursively applies multiple conditions, at least one of which must evaluate to true.
|
|
16
|
+
* Can include other operators such as $lt, $type, or nested $and/$or conditions.
|
|
17
|
+
*/
|
|
18
|
+
$or?: Array<PredefinedSearchOperators>;
|
|
19
|
+
/**
|
|
20
|
+
* Negates a single condition.
|
|
21
|
+
* Can include any other operator as its value.
|
|
22
|
+
*/
|
|
23
|
+
$not?: PredefinedSearchOperators;
|
|
24
|
+
};
|
|
25
|
+
/** Comparison Operators */
|
|
26
|
+
export type ComparisonOperators = {
|
|
27
|
+
$gt?: Record<string, number>;
|
|
28
|
+
$lt?: Record<string, number>;
|
|
29
|
+
$gte?: Record<string, number>;
|
|
30
|
+
$lte?: Record<string, number>;
|
|
31
|
+
$in?: Record<string, any[]>;
|
|
32
|
+
$nin?: Record<string, any[]>;
|
|
33
|
+
$between?: Record<string, [number, number]>;
|
|
34
|
+
};
|
|
35
|
+
/** Type and Existence Operators */
|
|
36
|
+
export type TypeAndExistenceOperators = {
|
|
37
|
+
$exists?: Record<string, boolean>;
|
|
38
|
+
$type?: Record<string, string>;
|
|
39
|
+
};
|
|
40
|
+
/** Array Operators */
|
|
41
|
+
export type ArrayOperators = {
|
|
42
|
+
$arrinc?: Record<string, any[]>;
|
|
43
|
+
$arrincall?: Record<string, any[]>;
|
|
44
|
+
$size?: Record<string, number>;
|
|
45
|
+
};
|
|
46
|
+
/** String Operators */
|
|
47
|
+
export type StringOperators = {
|
|
48
|
+
$regex?: Record<string, RegExp>;
|
|
49
|
+
$startsWith?: Record<string, string>;
|
|
50
|
+
$endsWith?: Record<string, string>;
|
|
51
|
+
};
|
|
52
|
+
/** Other Operators */
|
|
53
|
+
export type OtherOperators = {
|
|
54
|
+
$subset?: Record<string, any>;
|
|
55
|
+
};
|
|
56
|
+
/** Predefined Search Operators */
|
|
57
|
+
export type PredefinedSearchOperators = LogicalOperators & ComparisonOperators & TypeAndExistenceOperators & ArrayOperators & StringOperators & OtherOperators;
|
|
58
|
+
/**
|
|
59
|
+
* SearchOptions can be either a function or an object with predefined operators.
|
|
60
|
+
*/
|
|
61
|
+
export type SearchOptions = PredefinedSearchOperators | ((doc: Record<string, any>) => boolean);
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
|
@@ -0,0 +1,26 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Predefined type for updating data.
|
|
3
|
+
*/
|
|
4
|
+
/** Arrays */
|
|
5
|
+
export type ArrayUpdater = {
|
|
6
|
+
$push?: any;
|
|
7
|
+
/** Pushes items into an array and removes duplicates */
|
|
8
|
+
$pushset?: any;
|
|
9
|
+
$pull?: any;
|
|
10
|
+
$pullall?: any;
|
|
11
|
+
};
|
|
12
|
+
/** Objects */
|
|
13
|
+
export type ObjectUpdater = {
|
|
14
|
+
$merge?: any;
|
|
15
|
+
};
|
|
16
|
+
/** Values */
|
|
17
|
+
export type ValueUpdater = {
|
|
18
|
+
$set?: any;
|
|
19
|
+
$inc?: any;
|
|
20
|
+
$dec?: any;
|
|
21
|
+
$unset?: any;
|
|
22
|
+
$rename?: any;
|
|
23
|
+
};
|
|
24
|
+
export type UpdaterArg = ArrayUpdater & ObjectUpdater & ValueUpdater & {
|
|
25
|
+
[key: string]: any;
|
|
26
|
+
};
|
|
@@ -0,0 +1,8 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Checks if an object matches the standard field comparison.
|
|
3
|
+
* @function
|
|
4
|
+
* @param {Object} obj - The object to check.
|
|
5
|
+
* @param {Object} fields - Criteria to compare.
|
|
6
|
+
* @returns {boolean} - Whether the object matches the criteria.
|
|
7
|
+
*/
|
|
8
|
+
export default function hasFields(obj: any, fields: any): any;
|
|
@@ -5,15 +5,15 @@
|
|
|
5
5
|
* @param {Object} fields - Criteria to compare.
|
|
6
6
|
* @returns {boolean} - Whether the object matches the criteria.
|
|
7
7
|
*/
|
|
8
|
-
export default function hasFields(obj, fields){
|
|
8
|
+
export default function hasFields(obj, fields) {
|
|
9
9
|
const keys = Object.keys(fields);
|
|
10
10
|
return keys.every(key => {
|
|
11
|
-
if(obj[key] !== undefined){
|
|
12
|
-
if(typeof fields[key] === "object" && fields[key] !== null){
|
|
11
|
+
if (obj[key] !== undefined) {
|
|
12
|
+
if (typeof fields[key] === "object" && fields[key] !== null) {
|
|
13
13
|
return hasFields(obj[key], fields[key]);
|
|
14
14
|
}
|
|
15
15
|
return obj[key] === fields[key];
|
|
16
16
|
}
|
|
17
17
|
return false;
|
|
18
18
|
});
|
|
19
|
-
}
|
|
19
|
+
}
|