@wxn0brp/vql 0.6.4 → 0.8.2
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 +17 -7
- package/dist/cpu/request.js +8 -3
- package/dist/cpu/utils.d.ts +1 -1
- package/dist/{apiAbstract.js → helpers/apiAbstract.js} +2 -2
- package/dist/{falconFrame.d.ts → helpers/falconFrame.d.ts} +1 -1
- package/dist/{falconFrame.js → helpers/falconFrame.js} +1 -1
- package/dist/{gw.d.ts → helpers/gw.d.ts} +1 -1
- package/dist/helpers/gw.js +5 -0
- package/dist/{merge.js → helpers/merge.js} +2 -2
- package/dist/{sheet.d.ts → helpers/sheet.d.ts} +1 -1
- package/dist/{valid.d.ts → helpers/valid.d.ts} +1 -1
- package/dist/index.d.ts +4 -4
- package/dist/index.js +4 -4
- package/dist/permissions/relation.d.ts +1 -1
- package/dist/permissions/relation.js +11 -6
- package/dist/permissions/request.d.ts +1 -1
- package/dist/permissions/request.js +18 -9
- package/dist/permissions/resolver.d.ts +9 -0
- package/dist/permissions/resolver.js +46 -0
- package/dist/permissions/utils.d.ts +1 -1
- package/dist/processor.d.ts +1 -1
- package/dist/processor.js +3 -3
- package/dist/types/perm.d.ts +10 -1
- package/dist/types/resolver.d.ts +14 -0
- package/dist/types/resolver.js +1 -0
- package/dist/vql.d.ts +12 -7
- package/package.json +26 -13
- package/dist/gw.js +0 -5
- /package/dist/{apiAbstract.d.ts → helpers/apiAbstract.d.ts} +0 -0
- /package/dist/{config.d.ts → helpers/config.d.ts} +0 -0
- /package/dist/{config.js → helpers/config.js} +0 -0
- /package/dist/{merge.d.ts → helpers/merge.d.ts} +0 -0
- /package/dist/{sheet.js → helpers/sheet.js} +0 -0
- /package/dist/{valid.js → helpers/valid.js} +0 -0
package/README.md
CHANGED
|
@@ -1,17 +1,23 @@
|
|
|
1
1
|
# VQL (Valthera Query Language)
|
|
2
2
|
|
|
3
|
-
VQL
|
|
3
|
+
VQL (Valthera Query Language) is a comprehensive framework for interacting with ValtheraDB. It combines a flexible query language, a powerful permission management system, and a suite of tools to build secure and efficient data-driven applications.
|
|
4
4
|
|
|
5
5
|
[](https://www.npmjs.com/package/@wxn0brp/vql)
|
|
6
6
|
[](./LICENSE)
|
|
7
7
|
[](https://www.npmjs.com/package/@wxn0brp/vql)
|
|
8
|
+

|
|
9
|
+

|
|
8
10
|
|
|
9
|
-
## Features
|
|
11
|
+
## Key Features
|
|
10
12
|
|
|
11
|
-
- **Query
|
|
12
|
-
- **
|
|
13
|
-
- **
|
|
14
|
-
- **
|
|
13
|
+
- **Dual Query Syntax**: Choose between VQLR (a JSON-based object query language for programmatic use) and VQLS (a human-readable string-based language for simpler queries and scripts).
|
|
14
|
+
- **Multi-Database Support**: Process queries across multiple ValtheraDB instances seamlessly.
|
|
15
|
+
- **Cross-Platform**: Run VQL in both Node.js and modern web browsers.
|
|
16
|
+
- **Extensible by Design**: Customize and extend functionality with sheets and custom configurations.
|
|
17
|
+
- **Advanced Relation Queries**: Natively handle complex relationships not just between collections, but also across entire databases.
|
|
18
|
+
- **Permission System**: Built-in, granular access control powered by Gate Warden. It's disabled by default and can be enabled when needed to enforce complex security rules.
|
|
19
|
+
- **Falcon Frame Integration**: Integrates with Falcon Frame for extended capabilities.
|
|
20
|
+
- **Variable Support**: Use predefined or custom variables in your queries, allowing for more dynamic and reusable logic.
|
|
15
21
|
|
|
16
22
|
## Example Usage
|
|
17
23
|
|
|
@@ -35,7 +41,7 @@ const query = {
|
|
|
35
41
|
d: {
|
|
36
42
|
find: {
|
|
37
43
|
collection: "users",
|
|
38
|
-
search: {
|
|
44
|
+
search: { $gt: { age: 18 } },
|
|
39
45
|
fields: { name: 1, age: 1 },
|
|
40
46
|
},
|
|
41
47
|
},
|
|
@@ -61,6 +67,10 @@ f.age = 1
|
|
|
61
67
|
})();
|
|
62
68
|
```
|
|
63
69
|
|
|
70
|
+
## Development Tools
|
|
71
|
+
|
|
72
|
+
For an enhanced development and debugging experience, you can use [VQL-dev](https://github.com/wxn0brP/VQL-dev), a dedicated tool for debugging VQL queries.
|
|
73
|
+
|
|
64
74
|
## Documentation
|
|
65
75
|
|
|
66
76
|
- [Base/Map](./docs/lang/base.md)
|
package/dist/cpu/request.js
CHANGED
|
@@ -13,14 +13,14 @@ export async function executeQuery(cpu, query, user) {
|
|
|
13
13
|
const select = parseSelect(cpu.config, params.fields || params.select || {});
|
|
14
14
|
if (select && typeof select === "object" && Object.keys(select).length !== 0)
|
|
15
15
|
params.searchOpts = { ...params.searchOpts, select };
|
|
16
|
-
return db.find(params.collection, params.search,
|
|
16
|
+
return db.find(params.collection, params.search, params.options || {}, params.searchOpts);
|
|
17
17
|
}
|
|
18
18
|
else if (operation === "findOne" || operation === "f") {
|
|
19
19
|
const params = query.d[operation];
|
|
20
20
|
const select = parseSelect(cpu.config, params.fields || params.select || {});
|
|
21
21
|
if (select && typeof select === "object" && Object.keys(select).length !== 0)
|
|
22
22
|
params.searchOpts = { ...params.searchOpts, select };
|
|
23
|
-
return db.findOne(params.collection, params.search,
|
|
23
|
+
return db.findOne(params.collection, params.search, params.searchOpts);
|
|
24
24
|
}
|
|
25
25
|
else if (operation === "add") {
|
|
26
26
|
const params = query.d[operation];
|
|
@@ -44,7 +44,12 @@ export async function executeQuery(cpu, query, user) {
|
|
|
44
44
|
}
|
|
45
45
|
else if (operation === "updateOneOrAdd") {
|
|
46
46
|
const params = query.d[operation];
|
|
47
|
-
|
|
47
|
+
const opts = {};
|
|
48
|
+
if (params.add_arg)
|
|
49
|
+
opts.add_arg = params.add_arg;
|
|
50
|
+
if (params.id_gen)
|
|
51
|
+
opts.id_gen = params.id_gen;
|
|
52
|
+
return db.updateOneOrAdd(params.collection, params.search, params.updater, opts);
|
|
48
53
|
}
|
|
49
54
|
else if (operation === "removeCollection") {
|
|
50
55
|
const params = query.d[operation];
|
package/dist/cpu/utils.d.ts
CHANGED
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { VQLConfig } from "../config.js";
|
|
1
|
+
import { VQLConfig } from "../helpers/config.js";
|
|
2
2
|
export declare function parseSelect(config: VQLConfig, select: object | object[]): any[];
|
|
@@ -22,8 +22,8 @@ export function createValtheraAdapter(resolver, extendedFind = false) {
|
|
|
22
22
|
adapter[name] = (...args) => safe(resolver[name])(...args);
|
|
23
23
|
}
|
|
24
24
|
if (extendedFind) {
|
|
25
|
-
adapter.find = async (col, search,
|
|
26
|
-
let data = await safe(resolver.find)(col, search,
|
|
25
|
+
adapter.find = async (col, search, options, findOpts, context) => {
|
|
26
|
+
let data = await safe(resolver.find)(col, search, options, findOpts, context);
|
|
27
27
|
if (options?.reverse)
|
|
28
28
|
data.reverse();
|
|
29
29
|
if (options?.max !== -1 && data.length > options?.max)
|
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
export function deepMerge(target, source) {
|
|
2
|
-
if (typeof target !==
|
|
2
|
+
if (typeof target !== "object" || target === null) {
|
|
3
3
|
target = {};
|
|
4
4
|
}
|
|
5
5
|
for (const key in source) {
|
|
6
6
|
if (source.hasOwnProperty(key)) {
|
|
7
|
-
if (typeof source[key] ===
|
|
7
|
+
if (typeof source[key] === "object" && source[key] !== null && !Array.isArray(source[key])) {
|
|
8
8
|
if (!target[key]) {
|
|
9
9
|
target[key] = {};
|
|
10
10
|
}
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { VQL_Query } from "
|
|
1
|
+
import { VQL_Query } from "../types/vql.js";
|
|
2
2
|
export declare function replaceVars(query: VQL_Query, user: any): VQL_Query;
|
package/dist/index.d.ts
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { VQLProcessor } from "./processor.js";
|
|
2
|
-
import { VQLConfig } from "./config.js";
|
|
3
|
-
import { createValtheraAdapter } from "./apiAbstract.js";
|
|
2
|
+
import { VQLConfig } from "./helpers/config.js";
|
|
3
|
+
import { createValtheraAdapter } from "./helpers/apiAbstract.js";
|
|
4
4
|
import logger from "./logger.js";
|
|
5
5
|
import { LogLevel } from "@wxn0brp/lucerna-log";
|
|
6
|
-
import { FF_VQL } from "./falconFrame.js";
|
|
7
|
-
import { createGwValidFn } from "./gw.js";
|
|
6
|
+
import { FF_VQL } from "./helpers/falconFrame.js";
|
|
7
|
+
import { createGwValidFn } from "./helpers/gw.js";
|
|
8
8
|
export default VQLProcessor;
|
|
9
9
|
export { VQLProcessor, createValtheraAdapter, VQLConfig, logger as VQLLogger, LogLevel as VQLLogLevel, FF_VQL, createGwValidFn };
|
package/dist/index.js
CHANGED
|
@@ -1,9 +1,9 @@
|
|
|
1
1
|
import { VQLProcessor } from "./processor.js";
|
|
2
|
-
import { VQLConfig } from "./config.js";
|
|
3
|
-
import { createValtheraAdapter } from "./apiAbstract.js";
|
|
2
|
+
import { VQLConfig } from "./helpers/config.js";
|
|
3
|
+
import { createValtheraAdapter } from "./helpers/apiAbstract.js";
|
|
4
4
|
import logger from "./logger.js";
|
|
5
5
|
import { LogLevel } from "@wxn0brp/lucerna-log";
|
|
6
|
-
import { FF_VQL } from "./falconFrame.js";
|
|
7
|
-
import { createGwValidFn } from "./gw.js";
|
|
6
|
+
import { FF_VQL } from "./helpers/falconFrame.js";
|
|
7
|
+
import { createGwValidFn } from "./helpers/gw.js";
|
|
8
8
|
export default VQLProcessor;
|
|
9
9
|
export { VQLProcessor, createValtheraAdapter, VQLConfig, logger as VQLLogger, LogLevel as VQLLogLevel, FF_VQL, createGwValidFn };
|
|
@@ -1,4 +1,4 @@
|
|
|
1
1
|
import { PermValidFn } from "../types/perm.js";
|
|
2
2
|
import { VQL_Query_Relation } from "../types/vql.js";
|
|
3
|
-
import { VQLConfig } from "../config.js";
|
|
3
|
+
import { VQLConfig } from "../helpers/config.js";
|
|
4
4
|
export declare function checkRelationPermission(config: VQLConfig, permValidFn: PermValidFn, user: any, query: VQL_Query_Relation): Promise<boolean>;
|
|
@@ -3,30 +3,35 @@ import { extractPathsFromData, hashKey } from "./utils.js";
|
|
|
3
3
|
export async function checkRelationPermission(config, permValidFn, user, query) {
|
|
4
4
|
const { path, search, relations, select } = query.r;
|
|
5
5
|
// Helper function to recursively check permissions with fallback mechanism
|
|
6
|
-
const checkPermissionRecursively = async (entityId, fallbackLevels = []) => {
|
|
6
|
+
const checkPermissionRecursively = async (entityId, originalPath, fallbackLevels = []) => {
|
|
7
7
|
// Check if the user has access to the current entity
|
|
8
8
|
// const result = await gw.hasAccess(user.id, entityId, PermCRUD.READ);
|
|
9
|
-
const result = await permValidFn(
|
|
9
|
+
const result = await permValidFn({
|
|
10
|
+
field: entityId,
|
|
11
|
+
path: originalPath,
|
|
12
|
+
p: PermCRUD.READ,
|
|
13
|
+
user
|
|
14
|
+
});
|
|
10
15
|
if (result.granted) {
|
|
11
16
|
return true;
|
|
12
17
|
}
|
|
13
18
|
// If the result is "entity-404", check the next fallback level
|
|
14
19
|
if (!config.strictACL && result.via === "entity-404" && fallbackLevels.length > 0) {
|
|
15
20
|
const nextFallbackEntityId = await hashKey(config, fallbackLevels.slice(0, -1));
|
|
16
|
-
return checkPermissionRecursively(nextFallbackEntityId, fallbackLevels.slice(0, -2));
|
|
21
|
+
return checkPermissionRecursively(nextFallbackEntityId, fallbackLevels.slice(0, -2), fallbackLevels.slice(0, -2));
|
|
17
22
|
}
|
|
18
23
|
// If no fallback levels are left or the result is not "entity-404", deny access
|
|
19
24
|
return false;
|
|
20
25
|
};
|
|
21
26
|
// Check permission for the relation field in the parent collection
|
|
22
|
-
if (!await checkPermissionRecursively(await hashKey(config, path), path)) {
|
|
27
|
+
if (!await checkPermissionRecursively(await hashKey(config, path), path, path)) {
|
|
23
28
|
return false;
|
|
24
29
|
}
|
|
25
30
|
// Check permissions for search fields
|
|
26
31
|
const searchPaths = extractPathsFromData(search || {});
|
|
27
32
|
for (const searchPath of searchPaths) {
|
|
28
33
|
const key = [...path, ...searchPath.path, searchPath.key];
|
|
29
|
-
if (!await checkPermissionRecursively(await hashKey(config, key), key)) {
|
|
34
|
+
if (!await checkPermissionRecursively(await hashKey(config, key), key, key)) {
|
|
30
35
|
return false;
|
|
31
36
|
}
|
|
32
37
|
}
|
|
@@ -34,7 +39,7 @@ export async function checkRelationPermission(config, permValidFn, user, query)
|
|
|
34
39
|
if (select) {
|
|
35
40
|
for (const fieldPath of select) {
|
|
36
41
|
const key = [...path, fieldPath];
|
|
37
|
-
if (!await checkPermissionRecursively(await hashKey(config, key), key)) {
|
|
42
|
+
if (!await checkPermissionRecursively(await hashKey(config, key), key, key)) {
|
|
38
43
|
return false;
|
|
39
44
|
}
|
|
40
45
|
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { VQLConfig } from "../config.js";
|
|
1
|
+
import { VQLConfig } from "../helpers/config.js";
|
|
2
2
|
import { PermCRUD, PermValidFn } from "../types/perm.js";
|
|
3
3
|
import { VQL_Query_CRUD } from "../types/vql.js";
|
|
4
4
|
export declare function extractPaths(config: VQLConfig, query: VQL_Query_CRUD): Promise<{
|
|
@@ -41,14 +41,15 @@ export async function extractPaths(config, query) {
|
|
|
41
41
|
permPaths.paths.push({ c: PermCRUD.COLLECTION });
|
|
42
42
|
break;
|
|
43
43
|
}
|
|
44
|
-
permPaths.paths = permPaths.paths.map(path => {
|
|
44
|
+
permPaths.paths = (await Promise.all(permPaths.paths.map(async (path) => {
|
|
45
45
|
if (!path.filed)
|
|
46
46
|
return path;
|
|
47
|
-
return path.filed.map(filed => {
|
|
47
|
+
return await Promise.all(path.filed.map(async (filed) => {
|
|
48
48
|
const processedPath = [query.db, collection, ...processFieldPath(filed)];
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
49
|
+
const hashedKey = await hashKey(config, processedPath);
|
|
50
|
+
return { filed: hashedKey, path: processedPath, p: path.p };
|
|
51
|
+
}));
|
|
52
|
+
}))).flat();
|
|
52
53
|
return permPaths;
|
|
53
54
|
}
|
|
54
55
|
export function processFieldPath(pathObj) {
|
|
@@ -84,17 +85,22 @@ export async function checkRequestPermission(config, permValidFn, user, query) {
|
|
|
84
85
|
return false;
|
|
85
86
|
const permPaths = await extractPaths(config, query);
|
|
86
87
|
// Helper function to recursively check permissions
|
|
87
|
-
const checkPermissionRecursively = async (entityId, requiredPerm, fallbackLevels = []) => {
|
|
88
|
+
const checkPermissionRecursively = async (entityId, originalPath, requiredPerm, fallbackLevels = []) => {
|
|
88
89
|
// Check if the user has access to the current entity
|
|
89
90
|
// const result = await gw.hasAccess(user.id, entityId, requiredPerm);
|
|
90
|
-
const result = await permValidFn(
|
|
91
|
+
const result = await permValidFn({
|
|
92
|
+
field: entityId,
|
|
93
|
+
path: originalPath,
|
|
94
|
+
p: requiredPerm,
|
|
95
|
+
user
|
|
96
|
+
});
|
|
91
97
|
if (result.granted) {
|
|
92
98
|
return true;
|
|
93
99
|
}
|
|
94
100
|
// If the result is "entity-404", check the next fallback level
|
|
95
101
|
if (!config.strictACL && result.via === "entity-404" && fallbackLevels.length > 0) {
|
|
96
102
|
const nextFallbackEntityId = await hashKey(config, fallbackLevels.slice(0, -1));
|
|
97
|
-
return checkPermissionRecursively(nextFallbackEntityId, requiredPerm, fallbackLevels.slice(0, -2));
|
|
103
|
+
return checkPermissionRecursively(nextFallbackEntityId, fallbackLevels.slice(0, -2), requiredPerm, fallbackLevels.slice(0, -2));
|
|
98
104
|
}
|
|
99
105
|
// If no fallback levels are left or the result is not "entity-404", deny access
|
|
100
106
|
return false;
|
|
@@ -105,10 +111,12 @@ export async function checkRequestPermission(config, permValidFn, user, query) {
|
|
|
105
111
|
let entityId;
|
|
106
112
|
let requiredPerm;
|
|
107
113
|
let fallbackLevels = [];
|
|
114
|
+
let originalPath = [];
|
|
108
115
|
if ("c" in path) {
|
|
109
116
|
// Collection-level permission: hash the combination of db and collection
|
|
110
117
|
entityId = await hashKey(config, [query.db, permPaths.c]);
|
|
111
118
|
requiredPerm = path.c;
|
|
119
|
+
originalPath = [query.db, permPaths.c];
|
|
112
120
|
// Fallback to database level if needed
|
|
113
121
|
fallbackLevels = [query.db];
|
|
114
122
|
}
|
|
@@ -116,11 +124,12 @@ export async function checkRequestPermission(config, permValidFn, user, query) {
|
|
|
116
124
|
// Field-level permission: use the hashed field path
|
|
117
125
|
entityId = path.filed;
|
|
118
126
|
requiredPerm = path.p;
|
|
127
|
+
originalPath = path.path;
|
|
119
128
|
// Fallback to collection and then database level if needed
|
|
120
129
|
fallbackLevels = path.path;
|
|
121
130
|
}
|
|
122
131
|
// Check permissions recursively
|
|
123
|
-
const result = await checkPermissionRecursively(entityId, requiredPerm, fallbackLevels);
|
|
132
|
+
const result = await checkPermissionRecursively(entityId, originalPath, requiredPerm, fallbackLevels);
|
|
124
133
|
results.push(result);
|
|
125
134
|
}
|
|
126
135
|
// All permissions must be granted
|
|
@@ -0,0 +1,9 @@
|
|
|
1
|
+
import { PathMatcher, PermissionResolver } from "../types/resolver.js";
|
|
2
|
+
import { PermValidFn } from "../types/perm.js";
|
|
3
|
+
import { GateWarden } from "@wxn0brp/gate-warden";
|
|
4
|
+
export declare class PermissionResolverEngine {
|
|
5
|
+
private resolvers;
|
|
6
|
+
addResolver(matcher: PathMatcher, resolver: PermissionResolver): void;
|
|
7
|
+
create(): PermValidFn;
|
|
8
|
+
createWithGw(gw: GateWarden): PermValidFn;
|
|
9
|
+
}
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
export class PermissionResolverEngine {
|
|
2
|
+
resolvers = [];
|
|
3
|
+
addResolver(matcher, resolver) {
|
|
4
|
+
this.resolvers.push({ matcher, resolver });
|
|
5
|
+
}
|
|
6
|
+
create() {
|
|
7
|
+
return async (args) => {
|
|
8
|
+
const originalPath = args.path.join("/");
|
|
9
|
+
for (const { matcher, resolver } of this.resolvers) {
|
|
10
|
+
let isMatch = false;
|
|
11
|
+
if (typeof matcher === "string") {
|
|
12
|
+
isMatch = originalPath === matcher;
|
|
13
|
+
}
|
|
14
|
+
else if (matcher instanceof RegExp) {
|
|
15
|
+
isMatch = matcher.test(originalPath);
|
|
16
|
+
}
|
|
17
|
+
else if (typeof matcher === "function") {
|
|
18
|
+
isMatch = await matcher(originalPath, args.path);
|
|
19
|
+
}
|
|
20
|
+
if (isMatch) {
|
|
21
|
+
try {
|
|
22
|
+
const resolverGranted = await resolver(args);
|
|
23
|
+
return { granted: resolverGranted, via: `resolver` };
|
|
24
|
+
}
|
|
25
|
+
catch (error) {
|
|
26
|
+
console.error(`[Resolver Engine] Error in custom resolver for path ${originalPath}:`, error);
|
|
27
|
+
return { granted: false, via: `resolver-error` };
|
|
28
|
+
}
|
|
29
|
+
}
|
|
30
|
+
}
|
|
31
|
+
return { granted: false, via: `no-resolver-match` };
|
|
32
|
+
};
|
|
33
|
+
}
|
|
34
|
+
createWithGw(gw) {
|
|
35
|
+
const resolver = this.create();
|
|
36
|
+
return async (args) => {
|
|
37
|
+
const resolverResult = await resolver(args);
|
|
38
|
+
if (resolverResult.granted)
|
|
39
|
+
return resolverResult;
|
|
40
|
+
if (!resolverResult.granted && resolverResult.via !== `no-resolver-match`)
|
|
41
|
+
return resolverResult;
|
|
42
|
+
const gwResult = await gw.hasAccess(args.user.id, args.field, args.p);
|
|
43
|
+
return { granted: gwResult.granted, via: `gate-warden` };
|
|
44
|
+
};
|
|
45
|
+
}
|
|
46
|
+
}
|
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { VQLConfig } from "../config.js";
|
|
1
|
+
import { VQLConfig } from "../helpers/config.js";
|
|
2
2
|
export declare function getHash(json: string): Promise<string>;
|
|
3
3
|
export declare function hashKey(config: VQLConfig, path: any): Promise<string>;
|
|
4
4
|
export declare function extractPathsFromData(data: any, stack?: string[]): {
|
package/dist/processor.d.ts
CHANGED
|
@@ -1,5 +1,5 @@
|
|
|
1
1
|
import { Relation, ValtheraCompatible } from "@wxn0brp/db-core";
|
|
2
|
-
import { VQLConfig, VQLConfigInterface } from "./config.js";
|
|
2
|
+
import { VQLConfig, VQLConfigInterface } from "./helpers/config.js";
|
|
3
3
|
import { VQL_Query, VQLError, VQLUQ } from "./types/vql.js";
|
|
4
4
|
import { PermValidFn } from "./types/perm.js";
|
|
5
5
|
export declare class VQLProcessor {
|
package/dist/processor.js
CHANGED
|
@@ -1,10 +1,10 @@
|
|
|
1
1
|
import { Relation } from "@wxn0brp/db-core";
|
|
2
|
-
import { VQLConfig } from "./config.js";
|
|
2
|
+
import { VQLConfig } from "./helpers/config.js";
|
|
3
3
|
import { executeRelation } from "./cpu/relation.js";
|
|
4
4
|
import { executeQuery } from "./cpu/request.js";
|
|
5
5
|
import logger from "./logger.js";
|
|
6
|
-
import { replaceVars } from "./sheet.js";
|
|
7
|
-
import { validateRaw, validateVql } from "./valid.js";
|
|
6
|
+
import { replaceVars } from "./helpers/sheet.js";
|
|
7
|
+
import { validateRaw, validateVql } from "./helpers/valid.js";
|
|
8
8
|
import { parseVQLS } from "./cpu/string/index.js";
|
|
9
9
|
export class VQLProcessor {
|
|
10
10
|
dbInstances;
|
package/dist/types/perm.d.ts
CHANGED
|
@@ -9,4 +9,13 @@ export interface ValidFnResult {
|
|
|
9
9
|
granted: boolean;
|
|
10
10
|
via?: string;
|
|
11
11
|
}
|
|
12
|
-
export
|
|
12
|
+
export interface PermValidFnArgs {
|
|
13
|
+
/** sha256/json */
|
|
14
|
+
field: string;
|
|
15
|
+
/** original path */
|
|
16
|
+
path: string[];
|
|
17
|
+
/** permission */
|
|
18
|
+
p: number;
|
|
19
|
+
user: any;
|
|
20
|
+
}
|
|
21
|
+
export type PermValidFn = (args: PermValidFnArgs) => Promise<ValidFnResult>;
|
|
@@ -0,0 +1,14 @@
|
|
|
1
|
+
import { PermValidFnArgs } from "./perm.js";
|
|
2
|
+
export interface GWUser {
|
|
3
|
+
_id: string;
|
|
4
|
+
}
|
|
5
|
+
export type PathMatcher = string | RegExp | ((path: string, pathSegments: string[]) => Promise<boolean>);
|
|
6
|
+
export type PermissionResolver = (args: PermValidFnArgs) => Promise<boolean>;
|
|
7
|
+
export interface ResolverEntry {
|
|
8
|
+
matcher: PathMatcher;
|
|
9
|
+
resolver: PermissionResolver;
|
|
10
|
+
}
|
|
11
|
+
export interface ResolverValidFnResult {
|
|
12
|
+
granted: boolean;
|
|
13
|
+
via: string;
|
|
14
|
+
}
|
|
@@ -0,0 +1 @@
|
|
|
1
|
+
export {};
|
package/dist/vql.d.ts
CHANGED
|
@@ -55,7 +55,7 @@ export type ArrayOperators<T = any> = {
|
|
|
55
55
|
};
|
|
56
56
|
/** String Operators */
|
|
57
57
|
export type StringOperators<T = any> = {
|
|
58
|
-
$regex?: PartialOfType<T, RegExp, string>;
|
|
58
|
+
$regex?: PartialOfType<T, RegExp | string, string>;
|
|
59
59
|
$startsWith?: PartialOfType<T, string>;
|
|
60
60
|
$endsWith?: PartialOfType<T, string>;
|
|
61
61
|
};
|
|
@@ -119,11 +119,11 @@ declare class CollectionManager<D = Data> {
|
|
|
119
119
|
/**
|
|
120
120
|
* Find data in a database.
|
|
121
121
|
*/
|
|
122
|
-
find<T = Data>(search?: Search<T & D>,
|
|
122
|
+
find<T = Data>(search?: Search<T & D>, options?: DbFindOpts<T & Data>, findOpts?: FindOpts<T & Data>, context?: VContext): Promise<T[]>;
|
|
123
123
|
/**
|
|
124
124
|
* Find one data entry in a database.
|
|
125
125
|
*/
|
|
126
|
-
findOne<T = Data>(search?: Search<T & Data>,
|
|
126
|
+
findOne<T = Data>(search?: Search<T & Data>, findOpts?: FindOpts<T & Data>, context?: VContext): Promise<T>;
|
|
127
127
|
/**
|
|
128
128
|
* Update data in a database.
|
|
129
129
|
*/
|
|
@@ -143,7 +143,7 @@ declare class CollectionManager<D = Data> {
|
|
|
143
143
|
/**
|
|
144
144
|
* Asynchronously updates one entry in a database or adds a new one if it doesn't exist.
|
|
145
145
|
*/
|
|
146
|
-
updateOneOrAdd<T = Data>(search: Search<T & Data>, updater: Updater<T & Data>, add_arg
|
|
146
|
+
updateOneOrAdd<T = Data>(search: Search<T & Data>, updater: Updater<T & Data>, { add_arg, context, id_gen }: UpdateOneOrAdd<T & Data>): Promise<boolean>;
|
|
147
147
|
}
|
|
148
148
|
export interface ValtheraCompatible {
|
|
149
149
|
c(collection: string): CollectionManager;
|
|
@@ -151,14 +151,19 @@ export interface ValtheraCompatible {
|
|
|
151
151
|
ensureCollection(collection: string): Promise<boolean>;
|
|
152
152
|
issetCollection(collection: string): Promise<boolean>;
|
|
153
153
|
add<T = Data>(collection: string, data: Arg<T>, id_gen?: boolean): Promise<T>;
|
|
154
|
-
find<T = Data>(collection: string, search
|
|
155
|
-
findOne<T = Data>(collection: string, search
|
|
154
|
+
find<T = Data>(collection: string, search?: Search<T>, options?: DbFindOpts<T>, findOpts?: FindOpts<T>, context?: VContext): Promise<T[]>;
|
|
155
|
+
findOne<T = Data>(collection: string, search?: Search<T>, findOpts?: FindOpts<T>, context?: VContext): Promise<T | null>;
|
|
156
156
|
update<T = Data>(collection: string, search: Search<T>, updater: Updater<T>, context?: VContext): Promise<boolean>;
|
|
157
157
|
updateOne<T = Data>(collection: string, search: Search<T>, updater: Updater<T>, context?: VContext): Promise<boolean>;
|
|
158
158
|
remove<T = Data>(collection: string, search: Search<T>, context?: VContext): Promise<boolean>;
|
|
159
159
|
removeOne<T = Data>(collection: string, search: Search<T>, context?: VContext): Promise<boolean>;
|
|
160
160
|
removeCollection(collection: string): Promise<boolean>;
|
|
161
|
-
updateOneOrAdd<T = Data>(collection: string, search: Search<T>, updater: Updater<T>,
|
|
161
|
+
updateOneOrAdd<T = Data>(collection: string, search: Search<T>, updater: Updater<T>, opts?: UpdateOneOrAdd<T>): Promise<boolean>;
|
|
162
|
+
}
|
|
163
|
+
export interface UpdateOneOrAdd<T> {
|
|
164
|
+
add_arg?: Arg<T>;
|
|
165
|
+
id_gen?: boolean;
|
|
166
|
+
context?: VContext;
|
|
162
167
|
}
|
|
163
168
|
declare namespace RelationTypes {
|
|
164
169
|
type Path = [
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@wxn0brp/vql",
|
|
3
|
-
"version": "0.
|
|
3
|
+
"version": "0.8.2",
|
|
4
4
|
"main": "dist/index.js",
|
|
5
5
|
"author": "wxn0brP",
|
|
6
6
|
"license": "MIT",
|
|
@@ -14,10 +14,22 @@
|
|
|
14
14
|
"files": [
|
|
15
15
|
"dist"
|
|
16
16
|
],
|
|
17
|
+
"keywords": [
|
|
18
|
+
"vql",
|
|
19
|
+
"valthera",
|
|
20
|
+
"database",
|
|
21
|
+
"orm",
|
|
22
|
+
"api",
|
|
23
|
+
"crud",
|
|
24
|
+
"nosql",
|
|
25
|
+
"query",
|
|
26
|
+
"db",
|
|
27
|
+
"query-language"
|
|
28
|
+
],
|
|
17
29
|
"peerDependencies": {
|
|
18
|
-
"@wxn0brp/db-core": ">=0.
|
|
19
|
-
"@wxn0brp/falcon-frame": ">=0.0
|
|
20
|
-
"@wxn0brp/gate-warden": ">=0.4.
|
|
30
|
+
"@wxn0brp/db-core": ">=0.2.3",
|
|
31
|
+
"@wxn0brp/falcon-frame": ">=0.4.0",
|
|
32
|
+
"@wxn0brp/gate-warden": ">=0.4.1"
|
|
21
33
|
},
|
|
22
34
|
"peerDependenciesMeta": {
|
|
23
35
|
"@wxn0brp/falcon-frame": {
|
|
@@ -31,16 +43,17 @@
|
|
|
31
43
|
}
|
|
32
44
|
},
|
|
33
45
|
"devDependencies": {
|
|
34
|
-
"@types/node": "
|
|
35
|
-
"@wxn0brp/db": "^0.
|
|
36
|
-
"@wxn0brp/
|
|
37
|
-
"@wxn0brp/
|
|
38
|
-
"
|
|
39
|
-
"
|
|
40
|
-
"
|
|
46
|
+
"@types/node": "*",
|
|
47
|
+
"@wxn0brp/db": "^0.40.1",
|
|
48
|
+
"@wxn0brp/db-core": "^0.2.3",
|
|
49
|
+
"@wxn0brp/falcon-frame": "0.4.0",
|
|
50
|
+
"@wxn0brp/gate-warden": "^0.4.1",
|
|
51
|
+
"esbuild": "^0.25.10",
|
|
52
|
+
"tsc-alias": "*",
|
|
53
|
+
"typescript": "*"
|
|
41
54
|
},
|
|
42
55
|
"dependencies": {
|
|
43
|
-
"@wxn0brp/lucerna-log": "^0.2.
|
|
56
|
+
"@wxn0brp/lucerna-log": "^0.2.1"
|
|
44
57
|
},
|
|
45
58
|
"exports": {
|
|
46
59
|
".": {
|
|
@@ -54,4 +67,4 @@
|
|
|
54
67
|
"default": "./dist/*.js"
|
|
55
68
|
}
|
|
56
69
|
}
|
|
57
|
-
}
|
|
70
|
+
}
|
package/dist/gw.js
DELETED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|