oak-domain 2.4.3 → 2.5.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/lib/base-app-domain/ActionDefDict.d.ts +4 -1
- package/lib/base-app-domain/ActionDefDict.js +3 -1
- package/lib/base-app-domain/EntityDict.d.ts +2 -0
- package/lib/base-app-domain/Modi/Action.d.ts +4 -4
- package/lib/base-app-domain/ModiEntity/Schema.d.ts +31 -4
- package/lib/base-app-domain/ModiEntity/Storage.js +2 -1
- package/lib/base-app-domain/OperEntity/Schema.d.ts +31 -4
- package/lib/base-app-domain/OperEntity/Storage.js +2 -1
- package/lib/base-app-domain/Storage.js +3 -1
- package/lib/base-app-domain/User/Action.d.ts +10 -0
- package/lib/base-app-domain/User/Action.js +12 -0
- package/lib/base-app-domain/User/Schema.d.ts +60 -8
- package/lib/base-app-domain/User/Storage.js +12 -1
- package/lib/base-app-domain/UserEntityGrant/Schema.d.ts +121 -0
- package/lib/base-app-domain/UserEntityGrant/Schema.js +2 -0
- package/lib/base-app-domain/UserEntityGrant/Storage.d.ts +3 -0
- package/lib/base-app-domain/UserEntityGrant/Storage.js +28 -0
- package/lib/base-app-domain/_SubQuery.d.ts +8 -0
- package/lib/checkers/index.js +1 -0
- package/lib/compiler/schemalBuilder.js +58 -6
- package/lib/entities/User.d.ts +1 -0
- package/lib/entities/User.js +16 -0
- package/lib/entities/UserEntityGrant.d.ts +7 -0
- package/lib/entities/UserEntityGrant.js +12 -0
- package/lib/store/TriggerExecutor.js +7 -2
- package/lib/store/checker.d.ts +13 -0
- package/lib/store/checker.js +228 -1
- package/lib/store/modi.js +33 -15
- package/lib/types/Auth.d.ts +3 -3
- package/lib/types/Storage.d.ts +1 -1
- package/lib/types/Trigger.d.ts +9 -0
- package/lib/types/Trigger.js +10 -0
- package/package.json +1 -1
- package/src/entities/User.ts +26 -1
- package/src/entities/UserEntityGrant.ts +24 -0
|
@@ -3,6 +3,7 @@ import * as ModiEntity from "./ModiEntity/Schema";
|
|
|
3
3
|
import * as Oper from "./Oper/Schema";
|
|
4
4
|
import * as OperEntity from "./OperEntity/Schema";
|
|
5
5
|
import * as User from "./User/Schema";
|
|
6
|
+
import * as UserEntityGrant from "./UserEntityGrant/Schema";
|
|
6
7
|
export declare type ModiIdSubQuery = {
|
|
7
8
|
[K in "$in" | "$nin"]?: (ModiEntity.ModiIdSubQuery & {
|
|
8
9
|
entity: "modiEntity";
|
|
@@ -32,5 +33,12 @@ export declare type UserIdSubQuery = {
|
|
|
32
33
|
entity: "oper";
|
|
33
34
|
}) | (User.UserIdSubQuery & {
|
|
34
35
|
entity: "user";
|
|
36
|
+
}) | (User.UserIdSubQuery & {
|
|
37
|
+
entity: "user";
|
|
38
|
+
}) | any;
|
|
39
|
+
};
|
|
40
|
+
export declare type UserEntityGrantIdSubQuery = {
|
|
41
|
+
[K in "$in" | "$nin"]?: (UserEntityGrant.UserEntityGrantIdSubQuery & {
|
|
42
|
+
entity: "userEntityGrant";
|
|
35
43
|
}) | any;
|
|
36
44
|
};
|
package/lib/checkers/index.js
CHANGED
|
@@ -7,6 +7,7 @@ var modi_1 = require("../store/modi");
|
|
|
7
7
|
function createDynamicCheckers(schema, authDict) {
|
|
8
8
|
var checkers = [];
|
|
9
9
|
checkers.push.apply(checkers, tslib_1.__spreadArray([], tslib_1.__read((0, modi_1.createModiRelatedCheckers)(schema)), false));
|
|
10
|
+
checkers.push.apply(checkers, tslib_1.__spreadArray([], tslib_1.__read((0, checker_1.createRemoveCheckers)(schema)), false));
|
|
10
11
|
if (authDict) {
|
|
11
12
|
checkers.push.apply(checkers, tslib_1.__spreadArray([], tslib_1.__read((0, checker_1.createAuthCheckers)(schema, authDict)), false));
|
|
12
13
|
}
|
|
@@ -51,6 +51,20 @@ function addRelationship(many, one, key, notNull) {
|
|
|
51
51
|
_b));
|
|
52
52
|
}
|
|
53
53
|
}
|
|
54
|
+
/**
|
|
55
|
+
* 对relationship去重。一旦发生对象重定义这里就有可能重复
|
|
56
|
+
*/
|
|
57
|
+
function uniqRelationships() {
|
|
58
|
+
for (var entity in ManyToOne) {
|
|
59
|
+
ManyToOne[entity] = (0, lodash_1.uniqBy)(ManyToOne[entity], function (ele) { return "".concat(ele[0], "-").concat(ele[1]); });
|
|
60
|
+
}
|
|
61
|
+
for (var entity in OneToMany) {
|
|
62
|
+
OneToMany[entity] = (0, lodash_1.uniqBy)(OneToMany[entity], function (ele) { return "".concat(ele[0], "-").concat(ele[1]); });
|
|
63
|
+
}
|
|
64
|
+
for (var entity in ReversePointerRelations) {
|
|
65
|
+
OneToMany[entity] = (0, lodash_1.uniq)(OneToMany[entity]);
|
|
66
|
+
}
|
|
67
|
+
}
|
|
54
68
|
function createForeignRef(entity, foreignKey, ref) {
|
|
55
69
|
if (entity === foreignKey) {
|
|
56
70
|
return factory.createIdentifier(ref);
|
|
@@ -317,9 +331,10 @@ function analyzeEntity(filename, path, program, relativePath) {
|
|
|
317
331
|
var sourceFile = program.getSourceFile(fullPath);
|
|
318
332
|
var moduleName = filename.split('.')[0];
|
|
319
333
|
if (Schema.hasOwnProperty(moduleName)) {
|
|
320
|
-
|
|
321
|
-
|
|
322
|
-
|
|
334
|
+
delete ActionAsts[moduleName];
|
|
335
|
+
delete SchemaAsts[moduleName];
|
|
336
|
+
// removeFromRelationShip(moduleName);
|
|
337
|
+
console.warn("\u51FA\u73B0\u4E86\u540C\u540D\u7684Entity\u5B9A\u4E49\u300C".concat(moduleName, "\u300D\uFF0C\u5C06\u4F7F\u7528").concat(fullPath, "\u53D6\u4EE3\u6389\u9ED8\u8BA4\u5BF9\u8C61\uFF0C\u8BF7\u68C0\u67E5\u65B0\u7684\u5BF9\u8C61\u7ED3\u6784\u53CA\u76F8\u5173\u5E38\u91CF\u5B9A\u4E49\u4E0E\u539F\u6709\u7684\u517C\u5BB9\uFF0C\u5426\u5219\u539F\u6709\u5BF9\u8C61\u7684\u76F8\u5173\u903B\u8F91\u4F1A\u51FA\u73B0\u4E0D\u53EF\u77E5\u5F02\u5E38"));
|
|
323
338
|
}
|
|
324
339
|
var referencedSchemas = [];
|
|
325
340
|
var schemaAttrs = [];
|
|
@@ -340,7 +355,7 @@ function analyzeEntity(filename, path, program, relativePath) {
|
|
|
340
355
|
// let relationHierarchy: ts.ObjectLiteralExpression | undefined = undefined;
|
|
341
356
|
// let reverseCascadeRelationHierarchy: ts.ObjectLiteralExpression | undefined = undefined;
|
|
342
357
|
ts.forEachChild(sourceFile, function (node) {
|
|
343
|
-
var _a, _b, _c, _d;
|
|
358
|
+
var _a, _b, _c, _d, _e;
|
|
344
359
|
if (ts.isImportDeclaration(node)) {
|
|
345
360
|
var entityImported = getEntityImported(node);
|
|
346
361
|
if (entityImported) {
|
|
@@ -389,7 +404,9 @@ function analyzeEntity(filename, path, program, relativePath) {
|
|
|
389
404
|
&& referencedSchemas.includes(typeArguments[0].typeName.text), "\u300C".concat(filename, "\u300D\u975E\u6CD5\u7684\u5C5E\u6027\u5B9A\u4E49\u300C").concat(attrName, "\u300D"));
|
|
390
405
|
var reverseEntity = typeArguments[0].typeName.text;
|
|
391
406
|
if (ReversePointerRelations[reverseEntity]) {
|
|
392
|
-
ReversePointerRelations[reverseEntity].
|
|
407
|
+
if (!ReversePointerRelations[reverseEntity].includes(moduleName)) {
|
|
408
|
+
ReversePointerRelations[reverseEntity].push(moduleName);
|
|
409
|
+
}
|
|
393
410
|
}
|
|
394
411
|
else {
|
|
395
412
|
(0, lodash_1.assign)(ReversePointerRelations, (_a = {},
|
|
@@ -520,6 +537,9 @@ function analyzeEntity(filename, path, program, relativePath) {
|
|
|
520
537
|
if (hasRelationDef || moduleName === 'User') {
|
|
521
538
|
actionDefNodes.push(factory.createTypeReferenceNode('RelationAction', undefined));
|
|
522
539
|
}
|
|
540
|
+
if (process.env.COMPLING_AS_LIB) {
|
|
541
|
+
actionDefNodes.push(factory.createKeywordTypeNode(ts.SyntaxKind.StringKeyword));
|
|
542
|
+
}
|
|
523
543
|
pushStatementIntoActionAst(moduleName, factory.createTypeAliasDeclaration(undefined, [factory.createModifier(ts.SyntaxKind.ExportKeyword)], factory.createIdentifier("Action"), undefined, factory.createUnionTypeNode(actionDefNodes)), sourceFile);
|
|
524
544
|
dealWithActions(moduleName, filename, node.type, program, sourceFile, !!hasRelationDef || moduleName === 'User');
|
|
525
545
|
}
|
|
@@ -558,12 +578,35 @@ function analyzeEntity(filename, path, program, relativePath) {
|
|
|
558
578
|
_d));
|
|
559
579
|
addRelationship(relationEntityName, 'User', 'user', true);
|
|
560
580
|
addRelationship(relationEntityName, moduleName, entityLc, true);
|
|
581
|
+
// 对UserEntityGrant对象,建立相应的反指关系
|
|
582
|
+
if (ReversePointerRelations['UserEntityGrant']) {
|
|
583
|
+
if (!ReversePointerRelations['UserEntityGrant'].includes(moduleName)) {
|
|
584
|
+
ReversePointerRelations['UserEntityGrant'].push(moduleName);
|
|
585
|
+
}
|
|
586
|
+
}
|
|
587
|
+
else {
|
|
588
|
+
(0, lodash_1.assign)(ReversePointerRelations, (_e = {},
|
|
589
|
+
_e['UserEntityGrant'] = [moduleName],
|
|
590
|
+
_e));
|
|
591
|
+
}
|
|
561
592
|
hasRelationDef = node;
|
|
562
593
|
}
|
|
563
594
|
else if (node.name.text.endsWith('Action') || node.name.text.endsWith('State')) {
|
|
564
595
|
(0, assert_1.default)(!localeDef, "\u3010".concat(filename, "\u3011locale\u5B9A\u4E49\u987B\u5728Action/State\u4E4B\u540E"));
|
|
565
596
|
hasActionOrStateDef = true;
|
|
566
|
-
|
|
597
|
+
var type = node.type;
|
|
598
|
+
if (ts.isUnionTypeNode(type)) {
|
|
599
|
+
pushStatementIntoActionAst(moduleName, factory.updateTypeAliasDeclaration(node, node.decorators, [factory.createModifier(ts.SyntaxKind.ExportKeyword)], node.name, node.typeParameters, process.env.COMPLING_AS_LIB ? factory.createUnionTypeNode(tslib_1.__spreadArray(tslib_1.__spreadArray([], tslib_1.__read(type.types), false), [
|
|
600
|
+
factory.createKeywordTypeNode(ts.SyntaxKind.StringKeyword)
|
|
601
|
+
], false)) : type), sourceFile);
|
|
602
|
+
}
|
|
603
|
+
else {
|
|
604
|
+
(0, assert_1.default)(ts.isLiteralTypeNode(type) || ts.isTypeReferenceNode(type), "".concat(moduleName, " - ").concat(node.name));
|
|
605
|
+
pushStatementIntoActionAst(moduleName, factory.updateTypeAliasDeclaration(node, node.decorators, [factory.createModifier(ts.SyntaxKind.ExportKeyword)], node.name, node.typeParameters, process.env.COMPLING_AS_LIB ? factory.createUnionTypeNode([
|
|
606
|
+
type,
|
|
607
|
+
factory.createKeywordTypeNode(ts.SyntaxKind.StringKeyword)
|
|
608
|
+
]) : type), sourceFile);
|
|
609
|
+
}
|
|
567
610
|
}
|
|
568
611
|
else if (beforeSchema) {
|
|
569
612
|
// 本地规定的一些形状定义,直接使用
|
|
@@ -2871,6 +2914,14 @@ function constructAttributes(entity) {
|
|
|
2871
2914
|
attrAssignments.push(factory.createPropertyAssignment(factory.createIdentifier("type"), factory.createStringLiteral("varchar")), factory.createPropertyAssignment(factory.createIdentifier("params"), factory.createObjectLiteralExpression([
|
|
2872
2915
|
factory.createPropertyAssignment(factory.createIdentifier("length"), factory.createNumericLiteral(typeArguments[0].literal.text)),
|
|
2873
2916
|
], true)));
|
|
2917
|
+
// 如果是entity,在这里处理一下ref
|
|
2918
|
+
if (ts.isIdentifier(name) && name.text === 'entity') {
|
|
2919
|
+
var mtoRelations = ReversePointerRelations[entity];
|
|
2920
|
+
if (mtoRelations) {
|
|
2921
|
+
var mtoEntities = mtoRelations.map(function (ele) { return (0, string_1.firstLetterLowerCase)(ele); });
|
|
2922
|
+
attrAssignments.push(factory.createPropertyAssignment(factory.createIdentifier("ref"), factory.createArrayLiteralExpression(mtoEntities.map(function (ele) { return factory.createStringLiteral(ele); }), false)));
|
|
2923
|
+
}
|
|
2924
|
+
}
|
|
2874
2925
|
break;
|
|
2875
2926
|
}
|
|
2876
2927
|
case 'Text':
|
|
@@ -3283,6 +3334,7 @@ function analyzeEntities(inputDir, relativePath) {
|
|
|
3283
3334
|
analyzeEntity(filename, inputDir, program, relativePath);
|
|
3284
3335
|
});
|
|
3285
3336
|
analyzeInModi();
|
|
3337
|
+
uniqRelationships();
|
|
3286
3338
|
}
|
|
3287
3339
|
exports.analyzeEntities = analyzeEntities;
|
|
3288
3340
|
function buildSchema(outputDir) {
|
package/lib/entities/User.d.ts
CHANGED
package/lib/entities/User.js
CHANGED
|
@@ -1,12 +1,28 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
;
|
|
4
|
+
var UserActionDef = {
|
|
5
|
+
stm: {
|
|
6
|
+
mergeTo: ['normal', 'merged'],
|
|
7
|
+
},
|
|
8
|
+
};
|
|
4
9
|
var locale = {
|
|
5
10
|
zh_CN: {
|
|
6
11
|
attr: {
|
|
7
12
|
name: '姓名',
|
|
8
13
|
nickname: '昵称',
|
|
9
14
|
password: '密码',
|
|
15
|
+
ref: '指向用户',
|
|
16
|
+
userState: '状态',
|
|
17
|
+
},
|
|
18
|
+
action: {
|
|
19
|
+
mergeTo: '合并',
|
|
10
20
|
},
|
|
21
|
+
v: {
|
|
22
|
+
userState: {
|
|
23
|
+
normal: '正常',
|
|
24
|
+
merged: '已被合并',
|
|
25
|
+
},
|
|
26
|
+
}
|
|
11
27
|
},
|
|
12
28
|
};
|
|
@@ -6,6 +6,7 @@ var assert_1 = tslib_1.__importDefault(require("assert"));
|
|
|
6
6
|
var lodash_1 = require("../utils/lodash");
|
|
7
7
|
var filter_1 = require("../store/filter");
|
|
8
8
|
var Entity_1 = require("../types/Entity");
|
|
9
|
+
var Trigger_1 = require("../types/Trigger");
|
|
9
10
|
var SyncRowStore_1 = require("./SyncRowStore");
|
|
10
11
|
var checker_1 = require("./checker");
|
|
11
12
|
/**
|
|
@@ -33,10 +34,11 @@ var TriggerExecutor = /** @class */ (function () {
|
|
|
33
34
|
var entity = checker.entity, action = checker.action, type = checker.type, conditionalFilter = checker.conditionalFilter;
|
|
34
35
|
var triggerName = "".concat(String(entity)).concat(action, "\u6743\u9650\u68C0\u67E5-").concat(this.counter++);
|
|
35
36
|
var _a = (0, checker_1.translateCheckerInAsyncContext)(checker), fn = _a.fn, when = _a.when;
|
|
37
|
+
var priority = type === 'data' ? Trigger_1.DATA_CHECKER_DEFAULT_PRIORITY : Trigger_1.CHECKER_DEFAULT_PRIORITY; // checker的默认优先级最低(前面的trigger可能会赋上一些相应的值)
|
|
36
38
|
var trigger = {
|
|
37
39
|
checkerType: type,
|
|
38
40
|
name: triggerName,
|
|
39
|
-
priority: checker.priority ||
|
|
41
|
+
priority: checker.priority || priority,
|
|
40
42
|
entity: entity,
|
|
41
43
|
action: action,
|
|
42
44
|
fn: fn,
|
|
@@ -59,7 +61,10 @@ var TriggerExecutor = /** @class */ (function () {
|
|
|
59
61
|
throw new Error("\u4E0D\u53EF\u6709\u540C\u540D\u7684\u89E6\u53D1\u5668\u300C".concat(trigger.name, "\u300D"));
|
|
60
62
|
}
|
|
61
63
|
if (typeof trigger.priority !== 'number') {
|
|
62
|
-
trigger.priority =
|
|
64
|
+
trigger.priority = Trigger_1.TRIGGER_DEFAULT_PRIORITY; // 默认值
|
|
65
|
+
}
|
|
66
|
+
else {
|
|
67
|
+
(0, assert_1.default)(trigger.priority <= Trigger_1.TRIGGER_MAX_PRIORITY && trigger.priority >= Trigger_1.TRIGGER_MIN_PRIORITY, "trigger\u300C".concat(trigger.name, "\u300D\u7684\u4F18\u5148\u7EA7\u5B9A\u4E49\u8D8A\u754C\uFF0C\u5E94\u8BE5\u5728").concat(Trigger_1.TRIGGER_MIN_PRIORITY, "\u5230").concat(Trigger_1.TRIGGER_MAX_PRIORITY, "\u4E4B\u95F4"));
|
|
63
68
|
}
|
|
64
69
|
if (trigger.filter) {
|
|
65
70
|
(0, assert_1.default)(typeof trigger.action === 'string' && trigger.action !== 'create'
|
package/lib/store/checker.d.ts
CHANGED
|
@@ -10,4 +10,17 @@ export declare function translateCheckerInSyncContext<ED extends EntityDict & Ba
|
|
|
10
10
|
fn: (operation: ED[T]['Operation'], context: Cxt, option: OperateOption | SelectOption) => void;
|
|
11
11
|
when: 'before' | 'after';
|
|
12
12
|
};
|
|
13
|
+
/**
|
|
14
|
+
* 根据权限定义,创建出相应的checker
|
|
15
|
+
* @param schema
|
|
16
|
+
* @param authDict
|
|
17
|
+
* @returns
|
|
18
|
+
*/
|
|
13
19
|
export declare function createAuthCheckers<ED extends EntityDict & BaseEntityDict, Cxt extends AsyncContext<ED> | SyncContext<ED>>(schema: StorageSchema<ED>, authDict: AuthDefDict<ED>): Checker<ED, keyof ED, Cxt>[];
|
|
20
|
+
/**
|
|
21
|
+
* 对对象的删除,检查其是否会产生其他行上的空指针,不允许这种情况的出现
|
|
22
|
+
* @param schema
|
|
23
|
+
* @returns
|
|
24
|
+
* 如果有的对象允许删除,需要使用trigger来处理其相关联的外键对象,这些trigger写作before,则会在checker之前执行,仍然可以删除成功
|
|
25
|
+
*/
|
|
26
|
+
export declare function createRemoveCheckers<ED extends EntityDict & BaseEntityDict, Cxt extends AsyncContext<ED> | SyncContext<ED>>(schema: StorageSchema<ED>): Checker<ED, keyof ED, Cxt>[];
|
package/lib/store/checker.js
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
"use strict";
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
|
-
exports.createAuthCheckers = exports.translateCheckerInSyncContext = exports.translateCheckerInAsyncContext = void 0;
|
|
3
|
+
exports.createRemoveCheckers = exports.createAuthCheckers = exports.translateCheckerInSyncContext = exports.translateCheckerInAsyncContext = void 0;
|
|
4
4
|
var tslib_1 = require("tslib");
|
|
5
5
|
var assert_1 = tslib_1.__importDefault(require("assert"));
|
|
6
6
|
var filter_1 = require("../store/filter");
|
|
@@ -392,6 +392,12 @@ function translateActionAuthFilterMaker(schema, relationItem, entity) {
|
|
|
392
392
|
var filterMaker = translateCascadeRelationFilterMaker(schema, relationItem, entity);
|
|
393
393
|
return function (userId) { return filterMaker(userId); };
|
|
394
394
|
}
|
|
395
|
+
/**
|
|
396
|
+
* 根据权限定义,创建出相应的checker
|
|
397
|
+
* @param schema
|
|
398
|
+
* @param authDict
|
|
399
|
+
* @returns
|
|
400
|
+
*/
|
|
395
401
|
function createAuthCheckers(schema, authDict) {
|
|
396
402
|
var checkers = [];
|
|
397
403
|
var _loop_1 = function (entity) {
|
|
@@ -496,3 +502,224 @@ function createAuthCheckers(schema, authDict) {
|
|
|
496
502
|
return checkers;
|
|
497
503
|
}
|
|
498
504
|
exports.createAuthCheckers = createAuthCheckers;
|
|
505
|
+
/**
|
|
506
|
+
* 对对象的删除,检查其是否会产生其他行上的空指针,不允许这种情况的出现
|
|
507
|
+
* @param schema
|
|
508
|
+
* @returns
|
|
509
|
+
* 如果有的对象允许删除,需要使用trigger来处理其相关联的外键对象,这些trigger写作before,则会在checker之前执行,仍然可以删除成功
|
|
510
|
+
*/
|
|
511
|
+
function createRemoveCheckers(schema) {
|
|
512
|
+
var e_1, _a;
|
|
513
|
+
var checkers = [];
|
|
514
|
+
// 先建立所有的一对多的关系
|
|
515
|
+
var OneToManyMatrix = {};
|
|
516
|
+
var OneToManyOnEntityMatrix = {};
|
|
517
|
+
var addToMto = function (e, f, attr) {
|
|
518
|
+
var _a;
|
|
519
|
+
if (OneToManyMatrix[f]) {
|
|
520
|
+
(_a = OneToManyMatrix[f]) === null || _a === void 0 ? void 0 : _a.push([e, attr]);
|
|
521
|
+
}
|
|
522
|
+
else {
|
|
523
|
+
OneToManyMatrix[f] = [[e, attr]];
|
|
524
|
+
}
|
|
525
|
+
};
|
|
526
|
+
var addToMtoEntity = function (e, fs) {
|
|
527
|
+
var e_2, _a;
|
|
528
|
+
var _b;
|
|
529
|
+
try {
|
|
530
|
+
for (var fs_1 = tslib_1.__values(fs), fs_1_1 = fs_1.next(); !fs_1_1.done; fs_1_1 = fs_1.next()) {
|
|
531
|
+
var f = fs_1_1.value;
|
|
532
|
+
if (!OneToManyOnEntityMatrix[f]) {
|
|
533
|
+
OneToManyOnEntityMatrix[f] = [e];
|
|
534
|
+
}
|
|
535
|
+
else {
|
|
536
|
+
(_b = OneToManyOnEntityMatrix[f]) === null || _b === void 0 ? void 0 : _b.push(e);
|
|
537
|
+
}
|
|
538
|
+
}
|
|
539
|
+
}
|
|
540
|
+
catch (e_2_1) { e_2 = { error: e_2_1 }; }
|
|
541
|
+
finally {
|
|
542
|
+
try {
|
|
543
|
+
if (fs_1_1 && !fs_1_1.done && (_a = fs_1.return)) _a.call(fs_1);
|
|
544
|
+
}
|
|
545
|
+
finally { if (e_2) throw e_2.error; }
|
|
546
|
+
}
|
|
547
|
+
};
|
|
548
|
+
for (var entity in schema) {
|
|
549
|
+
if (['operEntity', 'modiEntity', 'userEntityGrant'].includes(entity)) {
|
|
550
|
+
continue; // 系统功能性数据,不用处理
|
|
551
|
+
}
|
|
552
|
+
var attributes = schema[entity].attributes;
|
|
553
|
+
for (var attr in attributes) {
|
|
554
|
+
if (attributes[attr].type === 'ref') {
|
|
555
|
+
addToMto(entity, attributes[attr].ref, attr);
|
|
556
|
+
}
|
|
557
|
+
else if (attr === 'entity') {
|
|
558
|
+
if (attributes[attr].ref) {
|
|
559
|
+
addToMtoEntity(entity, attributes[attr].ref);
|
|
560
|
+
}
|
|
561
|
+
else if (process.env.NODE_ENV === 'development') {
|
|
562
|
+
console.warn("".concat(entity, "\u7684entity\u53CD\u6307\u6307\u9488\u627E\u4E0D\u5230\u6709\u6548\u7684\u5BF9\u8C61"));
|
|
563
|
+
}
|
|
564
|
+
}
|
|
565
|
+
}
|
|
566
|
+
}
|
|
567
|
+
// 当删除一时,要确认多上面没有指向一的数据
|
|
568
|
+
var entities = (0, lodash_1.union)(Object.keys(OneToManyMatrix), Object.keys(OneToManyOnEntityMatrix));
|
|
569
|
+
var _loop_3 = function (entity) {
|
|
570
|
+
checkers.push({
|
|
571
|
+
entity: entity,
|
|
572
|
+
action: 'remove',
|
|
573
|
+
type: 'logical',
|
|
574
|
+
checker: function (operation, context, option) {
|
|
575
|
+
var e_3, _a, e_4, _b;
|
|
576
|
+
var promises = [];
|
|
577
|
+
if (OneToManyMatrix[entity]) {
|
|
578
|
+
var _loop_4 = function (otm) {
|
|
579
|
+
var _g, _h, _j, _k;
|
|
580
|
+
var _l = tslib_1.__read(otm, 2), e = _l[0], attr = _l[1];
|
|
581
|
+
var proj = (_g = {
|
|
582
|
+
id: 1
|
|
583
|
+
},
|
|
584
|
+
_g[attr] = 1,
|
|
585
|
+
_g);
|
|
586
|
+
var filter = operation.filter && (_h = {},
|
|
587
|
+
_h[attr.slice(0, attr.length - 2)] = operation.filter,
|
|
588
|
+
_h);
|
|
589
|
+
var result = context.select(e, {
|
|
590
|
+
data: proj,
|
|
591
|
+
filter: filter,
|
|
592
|
+
indexFrom: 0,
|
|
593
|
+
count: 1
|
|
594
|
+
}, { dontCollect: true });
|
|
595
|
+
if (result instanceof Promise) {
|
|
596
|
+
promises.push(result.then(function (_a) {
|
|
597
|
+
var _b, _c;
|
|
598
|
+
var _d = tslib_1.__read(_a, 1), row = _d[0];
|
|
599
|
+
if (row) {
|
|
600
|
+
var record = {
|
|
601
|
+
a: 's',
|
|
602
|
+
d: (_b = {},
|
|
603
|
+
_b[e] = (_c = {},
|
|
604
|
+
_c[row.id] = row,
|
|
605
|
+
_c),
|
|
606
|
+
_b)
|
|
607
|
+
};
|
|
608
|
+
throw new Exception_1.OakRowInconsistencyException(record, "\u60A8\u65E0\u6CD5\u5220\u9664\u5B58\u5728\u6709\u6548\u6570\u636E\u300C".concat(e, "\u300D\u5173\u8054\u7684\u884C"));
|
|
609
|
+
}
|
|
610
|
+
}));
|
|
611
|
+
}
|
|
612
|
+
else {
|
|
613
|
+
var _m = tslib_1.__read(result, 1), row = _m[0];
|
|
614
|
+
if (row) {
|
|
615
|
+
var record = {
|
|
616
|
+
a: 's',
|
|
617
|
+
d: (_j = {},
|
|
618
|
+
_j[e] = (_k = {},
|
|
619
|
+
_k[row.id] = row,
|
|
620
|
+
_k),
|
|
621
|
+
_j)
|
|
622
|
+
};
|
|
623
|
+
throw new Exception_1.OakRowInconsistencyException(record, "\u60A8\u65E0\u6CD5\u5220\u9664\u5B58\u5728\u6709\u6548\u6570\u636E\u300C".concat(e, "\u300D\u5173\u8054\u7684\u884C"));
|
|
624
|
+
}
|
|
625
|
+
}
|
|
626
|
+
};
|
|
627
|
+
try {
|
|
628
|
+
for (var _c = (e_3 = void 0, tslib_1.__values(OneToManyMatrix[entity])), _d = _c.next(); !_d.done; _d = _c.next()) {
|
|
629
|
+
var otm = _d.value;
|
|
630
|
+
_loop_4(otm);
|
|
631
|
+
}
|
|
632
|
+
}
|
|
633
|
+
catch (e_3_1) { e_3 = { error: e_3_1 }; }
|
|
634
|
+
finally {
|
|
635
|
+
try {
|
|
636
|
+
if (_d && !_d.done && (_a = _c.return)) _a.call(_c);
|
|
637
|
+
}
|
|
638
|
+
finally { if (e_3) throw e_3.error; }
|
|
639
|
+
}
|
|
640
|
+
}
|
|
641
|
+
if (OneToManyOnEntityMatrix[entity]) {
|
|
642
|
+
var _loop_5 = function (otm) {
|
|
643
|
+
var _o, _p, _q;
|
|
644
|
+
var proj = {
|
|
645
|
+
id: 1,
|
|
646
|
+
entity: 1,
|
|
647
|
+
entityId: 1,
|
|
648
|
+
};
|
|
649
|
+
var filter = operation.filter && (_o = {},
|
|
650
|
+
_o[entity] = operation.filter,
|
|
651
|
+
_o);
|
|
652
|
+
var result = context.select(otm, {
|
|
653
|
+
data: proj,
|
|
654
|
+
filter: filter,
|
|
655
|
+
indexFrom: 0,
|
|
656
|
+
count: 1
|
|
657
|
+
}, { dontCollect: true });
|
|
658
|
+
if (result instanceof Promise) {
|
|
659
|
+
promises.push(result.then(function (_a) {
|
|
660
|
+
var _b, _c;
|
|
661
|
+
var _d = tslib_1.__read(_a, 1), row = _d[0];
|
|
662
|
+
if (row) {
|
|
663
|
+
var record = {
|
|
664
|
+
a: 's',
|
|
665
|
+
d: (_b = {},
|
|
666
|
+
_b[otm] = (_c = {},
|
|
667
|
+
_c[row.id] = row,
|
|
668
|
+
_c),
|
|
669
|
+
_b)
|
|
670
|
+
};
|
|
671
|
+
throw new Exception_1.OakRowInconsistencyException(record, "\u60A8\u65E0\u6CD5\u5220\u9664\u5B58\u5728\u6709\u6548\u6570\u636E\u300C".concat(otm, "\u300D\u5173\u8054\u7684\u884C"));
|
|
672
|
+
}
|
|
673
|
+
}));
|
|
674
|
+
}
|
|
675
|
+
else {
|
|
676
|
+
var _r = tslib_1.__read(result, 1), row = _r[0];
|
|
677
|
+
if (row) {
|
|
678
|
+
var record = {
|
|
679
|
+
a: 's',
|
|
680
|
+
d: (_p = {},
|
|
681
|
+
_p[otm] = (_q = {},
|
|
682
|
+
_q[row.id] = row,
|
|
683
|
+
_q),
|
|
684
|
+
_p)
|
|
685
|
+
};
|
|
686
|
+
throw new Exception_1.OakRowInconsistencyException(record, "\u60A8\u65E0\u6CD5\u5220\u9664\u5B58\u5728\u6709\u6548\u6570\u636E\u300C".concat(otm, "\u300D\u5173\u8054\u7684\u884C"));
|
|
687
|
+
}
|
|
688
|
+
}
|
|
689
|
+
};
|
|
690
|
+
try {
|
|
691
|
+
for (var _e = (e_4 = void 0, tslib_1.__values(OneToManyOnEntityMatrix[entity])), _f = _e.next(); !_f.done; _f = _e.next()) {
|
|
692
|
+
var otm = _f.value;
|
|
693
|
+
_loop_5(otm);
|
|
694
|
+
}
|
|
695
|
+
}
|
|
696
|
+
catch (e_4_1) { e_4 = { error: e_4_1 }; }
|
|
697
|
+
finally {
|
|
698
|
+
try {
|
|
699
|
+
if (_f && !_f.done && (_b = _e.return)) _b.call(_e);
|
|
700
|
+
}
|
|
701
|
+
finally { if (e_4) throw e_4.error; }
|
|
702
|
+
}
|
|
703
|
+
}
|
|
704
|
+
if (promises.length > 0) {
|
|
705
|
+
return Promise.all(promises).then(function () { return undefined; });
|
|
706
|
+
}
|
|
707
|
+
}
|
|
708
|
+
});
|
|
709
|
+
};
|
|
710
|
+
try {
|
|
711
|
+
for (var entities_1 = tslib_1.__values(entities), entities_1_1 = entities_1.next(); !entities_1_1.done; entities_1_1 = entities_1.next()) {
|
|
712
|
+
var entity = entities_1_1.value;
|
|
713
|
+
_loop_3(entity);
|
|
714
|
+
}
|
|
715
|
+
}
|
|
716
|
+
catch (e_1_1) { e_1 = { error: e_1_1 }; }
|
|
717
|
+
finally {
|
|
718
|
+
try {
|
|
719
|
+
if (entities_1_1 && !entities_1_1.done && (_a = entities_1.return)) _a.call(entities_1);
|
|
720
|
+
}
|
|
721
|
+
finally { if (e_1) throw e_1.error; }
|
|
722
|
+
}
|
|
723
|
+
return checkers;
|
|
724
|
+
}
|
|
725
|
+
exports.createRemoveCheckers = createRemoveCheckers;
|
package/lib/store/modi.js
CHANGED
|
@@ -2,6 +2,7 @@
|
|
|
2
2
|
Object.defineProperty(exports, "__esModule", { value: true });
|
|
3
3
|
exports.createModiRelatedTriggers = exports.createModiRelatedCheckers = exports.abandonModis = exports.applyModis = exports.createOperationsFromModies = void 0;
|
|
4
4
|
var tslib_1 = require("tslib");
|
|
5
|
+
var types_1 = require("../types");
|
|
5
6
|
var action_1 = require("../actions/action");
|
|
6
7
|
var lodash_1 = require("../utils/lodash");
|
|
7
8
|
var uuid_1 = require("../utils/uuid");
|
|
@@ -154,35 +155,52 @@ function createModiRelatedTriggers(schema) {
|
|
|
154
155
|
if (inModi) {
|
|
155
156
|
// 当关联modi的对象被删除时,对应的modi也删除
|
|
156
157
|
triggers.push({
|
|
157
|
-
name: "\u5F53\u5220\u9664".concat(entity, "\u5BF9\u8C61\u65F6\uFF0C\u5220\u9664\u76F8\u5173\u8054\
|
|
158
|
+
name: "\u5F53\u5220\u9664".concat(entity, "\u5BF9\u8C61\u65F6\uFF0C\u5220\u9664\u76F8\u5173\u8054\u7684modi\u7684modiEntity"),
|
|
158
159
|
action: 'remove',
|
|
159
160
|
entity: entity,
|
|
160
161
|
when: 'after',
|
|
162
|
+
priority: types_1.REMOVE_CASCADE_PRIORITY,
|
|
161
163
|
fn: function (_a, context, option) {
|
|
162
164
|
var operation = _a.operation;
|
|
163
165
|
return tslib_1.__awaiter(_this, void 0, void 0, function () {
|
|
164
|
-
var data, id, _b, _c, _d;
|
|
165
|
-
var
|
|
166
|
-
return tslib_1.__generator(this, function (
|
|
167
|
-
switch (
|
|
166
|
+
var data, id, _b, _c, _d, _e, _f, _g;
|
|
167
|
+
var _h, _j;
|
|
168
|
+
return tslib_1.__generator(this, function (_k) {
|
|
169
|
+
switch (_k.label) {
|
|
168
170
|
case 0:
|
|
169
171
|
data = operation.data;
|
|
170
172
|
id = data.id;
|
|
171
173
|
_c = (_b = context).operate;
|
|
172
|
-
_d = ['
|
|
173
|
-
|
|
174
|
+
_d = ['modiEntity'];
|
|
175
|
+
_h = {};
|
|
174
176
|
return [4 /*yield*/, (0, uuid_1.generateNewIdAsync)()];
|
|
175
|
-
case 1: return [4 /*yield*/, _c.apply(_b, _d.concat([(
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
177
|
+
case 1: return [4 /*yield*/, _c.apply(_b, _d.concat([(_h.id = _k.sent(),
|
|
178
|
+
_h.action = 'remove',
|
|
179
|
+
_h.data = {},
|
|
180
|
+
_h.filter = {
|
|
181
|
+
modi: {
|
|
182
|
+
entity: entity,
|
|
183
|
+
entityId: id,
|
|
184
|
+
},
|
|
185
|
+
},
|
|
186
|
+
_h), { dontCollect: true }]))];
|
|
187
|
+
case 2:
|
|
188
|
+
_k.sent();
|
|
189
|
+
_f = (_e = context).operate;
|
|
190
|
+
_g = ['modi'];
|
|
191
|
+
_j = {};
|
|
192
|
+
return [4 /*yield*/, (0, uuid_1.generateNewIdAsync)()];
|
|
193
|
+
case 3: return [4 /*yield*/, _f.apply(_e, _g.concat([(_j.id = _k.sent(),
|
|
194
|
+
_j.action = 'remove',
|
|
195
|
+
_j.data = {},
|
|
196
|
+
_j.filter = {
|
|
179
197
|
entity: entity,
|
|
180
198
|
entityId: id,
|
|
181
199
|
},
|
|
182
|
-
|
|
183
|
-
case
|
|
184
|
-
|
|
185
|
-
return [2 /*return*/,
|
|
200
|
+
_j), { dontCollect: true }]))];
|
|
201
|
+
case 4:
|
|
202
|
+
_k.sent();
|
|
203
|
+
return [2 /*return*/, 0];
|
|
186
204
|
}
|
|
187
205
|
});
|
|
188
206
|
});
|
package/lib/types/Auth.d.ts
CHANGED
|
@@ -12,7 +12,7 @@ export declare type DataChecker<ED extends EntityDict, T extends keyof ED, Cxt e
|
|
|
12
12
|
type: 'data';
|
|
13
13
|
entity: T;
|
|
14
14
|
action: Omit<ED[T]['Action'], 'remove'> | Array<Omit<ED[T]['Action'], 'remove'>>;
|
|
15
|
-
checker: (data: ED[T]['Create']['data'] | ED[T]['Update']['data'], context: Cxt) =>
|
|
15
|
+
checker: (data: ED[T]['Create']['data'] | ED[T]['Update']['data'], context: Cxt) => any | Promise<any>;
|
|
16
16
|
conditionalFilter?: ED[T]['Update']['filter'] | ((operation: ED[T]['Operation'], context: Cxt, option: OperateOption) => ED[T]['Update']['filter'] | Promise<ED[T]['Selection']['filter']>);
|
|
17
17
|
};
|
|
18
18
|
export declare type RowChecker<ED extends EntityDict, T extends keyof ED, Cxt extends AsyncContext<ED> | SyncContext<ED>> = {
|
|
@@ -44,7 +44,7 @@ export declare type LogicalChecker<ED extends EntityDict, T extends keyof ED, Cx
|
|
|
44
44
|
when?: 'after';
|
|
45
45
|
entity: T;
|
|
46
46
|
action: ED[T]['Action'] | Array<ED[T]['Action']>;
|
|
47
|
-
checker: (operation: ED[T]['Operation'] | ED[T]['Selection'], context: Cxt, option: OperateOption | SelectOption) =>
|
|
47
|
+
checker: (operation: ED[T]['Operation'] | ED[T]['Selection'], context: Cxt, option: OperateOption | SelectOption) => any | Promise<any>;
|
|
48
48
|
conditionalFilter?: ED[T]['Update']['filter'] | ((operation: ED[T]['Operation'], context: Cxt, option: OperateOption) => ED[T]['Update']['filter']);
|
|
49
49
|
};
|
|
50
50
|
export declare type LogicalRelationChecker<ED extends EntityDict, T extends keyof ED, Cxt extends AsyncContext<ED> | SyncContext<ED>> = {
|
|
@@ -53,7 +53,7 @@ export declare type LogicalRelationChecker<ED extends EntityDict, T extends keyo
|
|
|
53
53
|
when?: 'after';
|
|
54
54
|
entity: T;
|
|
55
55
|
action: ED[T]['Action'] | Array<ED[T]['Action']>;
|
|
56
|
-
checker: (operation: ED[T]['Operation'] | ED[T]['Selection'], context: Cxt, option: OperateOption | SelectOption) =>
|
|
56
|
+
checker: (operation: ED[T]['Operation'] | ED[T]['Selection'], context: Cxt, option: OperateOption | SelectOption) => any | Promise<any>;
|
|
57
57
|
conditionalFilter?: ED[T]['Update']['filter'] | ((operation: ED[T]['Operation'], context: Cxt, option: OperateOption) => ED[T]['Update']['filter']);
|
|
58
58
|
};
|
|
59
59
|
export declare type Checker<ED extends EntityDict, T extends keyof ED, Cxt extends AsyncContext<ED> | SyncContext<ED>> = DataChecker<ED, T, Cxt> | RowChecker<ED, T, Cxt> | RelationChecker<ED, T, Cxt> | LogicalChecker<ED, T, Cxt> | LogicalRelationChecker<ED, T, Cxt>;
|
package/lib/types/Storage.d.ts
CHANGED
|
@@ -20,7 +20,7 @@ export interface Index<SH extends EntityShape> {
|
|
|
20
20
|
export interface Attribute {
|
|
21
21
|
type: DataType | Ref;
|
|
22
22
|
params?: DataTypeParams;
|
|
23
|
-
ref?: string;
|
|
23
|
+
ref?: string | string[];
|
|
24
24
|
onRefDelete?: 'delete' | 'setNull' | 'ignore';
|
|
25
25
|
default?: string | number | boolean;
|
|
26
26
|
notNull?: boolean;
|
package/lib/types/Trigger.d.ts
CHANGED
|
@@ -4,6 +4,15 @@ import { AsyncContext } from "../store/AsyncRowStore";
|
|
|
4
4
|
import { SyncContext } from "../store/SyncRowStore";
|
|
5
5
|
import { EntityDict, OperateOption } from "../types/Entity";
|
|
6
6
|
import { EntityShape } from "../types/Entity";
|
|
7
|
+
/**
|
|
8
|
+
* 优先级越小,越早执行。定义在1~99之间
|
|
9
|
+
*/
|
|
10
|
+
export declare const TRIGGER_DEFAULT_PRIORITY = 50;
|
|
11
|
+
export declare const TRIGGER_MIN_PRIORITY = 1;
|
|
12
|
+
export declare const TRIGGER_MAX_PRIORITY = 99;
|
|
13
|
+
export declare const DATA_CHECKER_DEFAULT_PRIORITY = 60;
|
|
14
|
+
export declare const CHECKER_DEFAULT_PRIORITY = 99;
|
|
15
|
+
export declare const REMOVE_CASCADE_PRIORITY = 70;
|
|
7
16
|
interface TriggerBase<ED extends EntityDict, T extends keyof ED> {
|
|
8
17
|
checkerType?: CheckerType;
|
|
9
18
|
entity: T;
|