oak-domain 3.0.2 → 3.0.4

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.
Files changed (157) hide show
  1. package/lib/actions/action.d.ts +8 -8
  2. package/lib/actions/action.js +2 -2
  3. package/lib/actions/relation.d.ts +1 -1
  4. package/lib/actions/relation.js +9 -22
  5. package/lib/base-app-domain/ActionAuth/Schema.d.ts +68 -42
  6. package/lib/base-app-domain/ActionAuth/Storage.js +12 -15
  7. package/lib/base-app-domain/ActionDefDict.d.ts +2 -3
  8. package/lib/base-app-domain/ActionDefDict.js +3 -5
  9. package/lib/base-app-domain/EntityDict.d.ts +5 -1
  10. package/lib/base-app-domain/I18n/Schema.d.ts +24 -24
  11. package/lib/base-app-domain/I18n/Storage.js +5 -5
  12. package/lib/base-app-domain/Modi/Action.d.ts +4 -4
  13. package/lib/base-app-domain/Modi/Action.js +3 -3
  14. package/lib/base-app-domain/Modi/Schema.d.ts +24 -24
  15. package/lib/base-app-domain/Modi/Storage.js +3 -3
  16. package/lib/base-app-domain/ModiEntity/Schema.d.ts +128 -55
  17. package/lib/base-app-domain/ModiEntity/Storage.js +2 -2
  18. package/lib/base-app-domain/Oper/Schema.d.ts +30 -29
  19. package/lib/base-app-domain/Oper/Storage.js +1 -1
  20. package/lib/base-app-domain/OperEntity/Schema.d.ts +126 -53
  21. package/lib/base-app-domain/OperEntity/Storage.js +2 -2
  22. package/lib/base-app-domain/Path/Schema.d.ts +149 -0
  23. package/lib/base-app-domain/Path/Schema.js +2 -0
  24. package/lib/base-app-domain/Path/Storage.d.ts +3 -0
  25. package/lib/base-app-domain/Path/Storage.js +54 -0
  26. package/lib/base-app-domain/Relation/Schema.d.ts +34 -34
  27. package/lib/base-app-domain/Relation/Storage.js +6 -6
  28. package/lib/base-app-domain/Relation.d.ts +0 -8
  29. package/lib/base-app-domain/Relation.js +1 -7
  30. package/lib/base-app-domain/RelationAuth/Schema.d.ts +74 -40
  31. package/lib/base-app-domain/RelationAuth/Storage.js +9 -11
  32. package/lib/base-app-domain/Storage.js +20 -16
  33. package/lib/base-app-domain/User/Action.d.ts +4 -4
  34. package/lib/base-app-domain/User/Action.js +3 -3
  35. package/lib/base-app-domain/User/Schema.d.ts +40 -27
  36. package/lib/base-app-domain/User/Storage.js +1 -1
  37. package/lib/base-app-domain/UserEntityClaim/Schema.d.ts +264 -0
  38. package/lib/base-app-domain/UserEntityClaim/Schema.js +2 -0
  39. package/lib/base-app-domain/UserEntityClaim/Storage.d.ts +3 -0
  40. package/lib/base-app-domain/UserEntityClaim/Storage.js +37 -0
  41. package/lib/base-app-domain/UserEntityGrant/Action.d.ts +2 -2
  42. package/lib/base-app-domain/UserEntityGrant/Schema.d.ts +55 -81
  43. package/lib/base-app-domain/UserEntityGrant/Storage.js +7 -11
  44. package/lib/base-app-domain/UserRelation/Schema.d.ts +50 -36
  45. package/lib/base-app-domain/UserRelation/Storage.js +7 -7
  46. package/lib/base-app-domain/_SubQuery.d.ts +45 -15
  47. package/lib/base-app-domain/index.js +1 -1
  48. package/lib/checkers/index.js +6 -7
  49. package/lib/compiler/env.js +16 -18
  50. package/lib/compiler/localeBuilder.js +83 -79
  51. package/lib/compiler/schemalBuilder.d.ts +16 -0
  52. package/lib/compiler/schemalBuilder.js +1160 -1378
  53. package/lib/entities/ActionAuth.d.ts +3 -5
  54. package/lib/entities/ActionAuth.js +9 -7
  55. package/lib/entities/I18n.js +1 -1
  56. package/lib/entities/Modi.js +2 -2
  57. package/lib/entities/ModiEntity.js +1 -1
  58. package/lib/entities/Oper.js +1 -1
  59. package/lib/entities/OperEntity.js +1 -1
  60. package/lib/entities/Path.d.ts +8 -0
  61. package/lib/entities/Path.js +35 -0
  62. package/lib/entities/Relation.js +1 -1
  63. package/lib/entities/RelationAuth.d.ts +2 -2
  64. package/lib/entities/RelationAuth.js +1 -1
  65. package/lib/entities/User.js +2 -2
  66. package/lib/entities/UserEntityClaim.d.ts +13 -0
  67. package/lib/entities/UserEntityClaim.js +17 -0
  68. package/lib/entities/UserEntityGrant.d.ts +5 -4
  69. package/lib/entities/UserEntityGrant.js +4 -7
  70. package/lib/entities/UserRelation.js +1 -1
  71. package/lib/index.d.ts +23 -0
  72. package/lib/index.js +37 -0
  73. package/lib/store/AsyncRowStore.d.ts +2 -1
  74. package/lib/store/AsyncRowStore.js +75 -149
  75. package/lib/store/CascadeStore.js +968 -1341
  76. package/lib/store/RelationAuth.d.ts +9 -16
  77. package/lib/store/RelationAuth.js +752 -910
  78. package/lib/store/SyncRowStore.d.ts +1 -1
  79. package/lib/store/SyncRowStore.js +27 -26
  80. package/lib/store/TriggerExecutor.d.ts +17 -10
  81. package/lib/store/TriggerExecutor.js +350 -423
  82. package/lib/store/actionAuth.js +13 -28
  83. package/lib/store/actionDef.js +142 -215
  84. package/lib/store/checker.js +225 -361
  85. package/lib/store/filter.d.ts +2 -3
  86. package/lib/store/filter.js +451 -589
  87. package/lib/store/modi.js +116 -177
  88. package/lib/store/relation.js +17 -17
  89. package/lib/timers/oper.d.ts +1 -1
  90. package/lib/timers/oper.js +44 -47
  91. package/lib/timers/vaccum.d.ts +2 -2
  92. package/lib/timers/vaccum.js +100 -165
  93. package/lib/triggers/index.js +1 -1
  94. package/lib/types/Action.d.ts +7 -7
  95. package/lib/types/AppLoader.d.ts +8 -2
  96. package/lib/types/AppLoader.js +4 -4
  97. package/lib/types/Auth.d.ts +15 -19
  98. package/lib/types/Connector.d.ts +19 -14
  99. package/lib/types/Connector.js +0 -7
  100. package/lib/types/DataType.d.ts +19 -18
  101. package/lib/types/DataType.js +1 -1
  102. package/lib/types/Demand.d.ts +25 -25
  103. package/lib/types/Endpoint.d.ts +1 -1
  104. package/lib/types/Entity.d.ts +62 -53
  105. package/lib/types/Entity.js +4 -3
  106. package/lib/types/EntityDesc.d.ts +2 -1
  107. package/lib/types/Environment.d.ts +4 -4
  108. package/lib/types/Exception.d.ts +34 -2
  109. package/lib/types/Exception.js +214 -197
  110. package/lib/types/Expression.d.ts +14 -14
  111. package/lib/types/Expression.js +54 -87
  112. package/lib/types/Geo.d.ts +6 -6
  113. package/lib/types/Locale.d.ts +5 -5
  114. package/lib/types/Polyfill.d.ts +9 -9
  115. package/lib/types/Port.d.ts +4 -4
  116. package/lib/types/RowStore.d.ts +3 -3
  117. package/lib/types/RowStore.js +18 -19
  118. package/lib/types/Storage.d.ts +5 -4
  119. package/lib/types/Style.d.ts +2 -2
  120. package/lib/types/Timer.d.ts +3 -3
  121. package/lib/types/Trigger.d.ts +30 -14
  122. package/lib/types/Trigger.js +6 -2
  123. package/lib/types/Watcher.d.ts +2 -2
  124. package/lib/types/index.d.ts +1 -0
  125. package/lib/types/index.js +2 -1
  126. package/lib/types/schema/DataTypes.d.ts +7 -7
  127. package/lib/utils/SimpleConnector.d.ts +26 -10
  128. package/lib/utils/SimpleConnector.js +167 -141
  129. package/lib/utils/assert.js +2 -2
  130. package/lib/utils/concurrent.d.ts +1 -1
  131. package/lib/utils/concurrent.js +31 -57
  132. package/lib/utils/date.js +2 -2
  133. package/lib/utils/geo.js +8 -8
  134. package/lib/utils/lodash.d.ts +3 -1
  135. package/lib/utils/lodash.js +21 -34
  136. package/lib/utils/mask.js +12 -13
  137. package/lib/utils/money.d.ts +1 -1
  138. package/lib/utils/money.js +22 -11
  139. package/lib/utils/projection.d.ts +4 -0
  140. package/lib/utils/projection.js +15 -0
  141. package/lib/utils/random/random.js +11 -16
  142. package/lib/utils/random/random.mp.js +7 -18
  143. package/lib/utils/random/random.web.js +6 -12
  144. package/lib/utils/string.d.ts +4 -4
  145. package/lib/utils/string.js +19 -32
  146. package/lib/utils/url.js +5 -4
  147. package/lib/utils/uuid.d.ts +1 -1
  148. package/lib/utils/uuid.js +46 -85
  149. package/lib/utils/validator.d.ts +4 -3
  150. package/lib/utils/validator.js +35 -32
  151. package/lib/utils/version.js +6 -6
  152. package/package.json +7 -7
  153. package/src/entities/ActionAuth.ts +10 -10
  154. package/src/entities/Path.ts +43 -0
  155. package/src/entities/RelationAuth.ts +2 -1
  156. package/src/entities/UserEntityClaim.ts +30 -0
  157. package/src/entities/UserEntityGrant.ts +9 -12
@@ -1,139 +1,145 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.getUserRelationsByActions = exports.RelationAuth = void 0;
4
- var tslib_1 = require("tslib");
5
- var assert_1 = tslib_1.__importDefault(require("assert"));
6
- var types_1 = require("../types");
7
- var AsyncRowStore_1 = require("./AsyncRowStore");
8
- var filter_1 = require("./filter");
9
- var relation_1 = require("./relation");
10
- var action_1 = require("../actions/action");
11
- var lodash_1 = require("../utils/lodash");
12
- var env_1 = require("../compiler/env");
13
- var RelationAuth = /** @class */ (function () {
14
- function RelationAuth(schema, actionCascadePathGraph, relationCascadePathGraph, authDeduceRelationMap, selectFreeEntities, createFreeEntities, updateFreeEntities) {
15
- this.actionCascadePathGraph = actionCascadePathGraph;
16
- this.relationCascadePathGraph = relationCascadePathGraph;
4
+ const tslib_1 = require("tslib");
5
+ const assert_1 = tslib_1.__importDefault(require("assert"));
6
+ const types_1 = require("../types");
7
+ const AsyncRowStore_1 = require("./AsyncRowStore");
8
+ const filter_1 = require("./filter");
9
+ const relation_1 = require("./relation");
10
+ const action_1 = require("../actions/action");
11
+ const lodash_1 = require("../utils/lodash");
12
+ const env_1 = require("../compiler/env");
13
+ class RelationAuth {
14
+ authDeduceRelationMap;
15
+ schema;
16
+ static SPECIAL_ENTITIES = env_1.SYSTEM_RESERVE_ENTITIES;
17
+ selectFreeEntities;
18
+ updateFreeDict;
19
+ constructor(schema, authDeduceRelationMap, selectFreeEntities, updateFreeDict) {
17
20
  this.schema = schema;
18
21
  this.selectFreeEntities = selectFreeEntities || [];
19
- this.createFreeEntities = createFreeEntities || [];
20
- this.updateFreeEntities = updateFreeEntities || [];
22
+ this.updateFreeDict = updateFreeDict || {};
21
23
  this.authDeduceRelationMap = Object.assign({}, authDeduceRelationMap, {
22
24
  modi: 'entity',
23
25
  });
24
26
  }
25
27
  // 前台检查filter是否满足relation约束
26
- RelationAuth.prototype.checkRelationSync = function (entity, operation, context) {
28
+ checkRelationSync(entity, operation, context) {
27
29
  if (context.isRoot()) {
28
30
  return;
29
31
  }
30
32
  this.checkActions2(entity, operation, context);
31
- };
32
- /**
33
- * 查询当前用户在对应entity上可以操作的relationIds
34
- * @param entity
35
- * @param entityId
36
- * @param context
37
- * @returns
38
- */
39
- RelationAuth.prototype.getGrantedRelationIds = function (entity, entityId, context) {
40
- var result = context.select('relationAuth', {
33
+ }
34
+ // 后台检查filter是否满足relation约束
35
+ async checkRelationAsync(entity, operation, context) {
36
+ if (context.isRoot()) {
37
+ return;
38
+ }
39
+ await this.checkActions2(entity, operation, context);
40
+ }
41
+ checkUserRelation(context, action, filter) {
42
+ const userId = context.getCurrentUserId();
43
+ let filter2 = {
44
+ destRelation: {
45
+ userRelation$relation: filter,
46
+ },
47
+ };
48
+ if (action === 'create') {
49
+ const { entity, entityId, relationId } = filter;
50
+ if (relationId) {
51
+ // 如果指定relation,则测试该relation上是否可行
52
+ filter2 = {
53
+ destRelationId: relationId,
54
+ };
55
+ }
56
+ else {
57
+ // 否则为测试“能否”有权限管理的资格,此时只要有一个就可以
58
+ (0, assert_1.default)(entity);
59
+ filter2 = {
60
+ destRelation: {
61
+ entity,
62
+ }
63
+ };
64
+ }
65
+ }
66
+ else {
67
+ (0, assert_1.default)(action === 'remove');
68
+ // 如果一次删除多个userRelation,接下来的流程判断是只有一个relationAuth满足就会通过,这样可能会有错判 by Xc 20231019
69
+ (0, assert_1.default)(typeof filter.id === 'string', '当前只支持指定id的用户关系删除');
70
+ }
71
+ const relationAuths = context.select('relationAuth', {
41
72
  data: {
42
73
  id: 1,
74
+ path: {
75
+ id: 1,
76
+ sourceEntity: 1,
77
+ destEntity: 1,
78
+ value: 1,
79
+ recursive: 1,
80
+ },
81
+ sourceRelationId: 1,
82
+ sourceRelation: {
83
+ id: 1,
84
+ entity: 1,
85
+ entityId: 1,
86
+ },
43
87
  destRelationId: 1,
44
88
  destRelation: {
45
89
  id: 1,
46
- name: 1,
47
90
  entity: 1,
48
91
  entityId: 1,
49
- display: 1,
50
92
  },
51
93
  },
52
- filter: {
53
- sourceRelation: {
54
- userRelation$relation: {
55
- userId: context.getCurrentUserId(),
56
- }
57
- },
58
- destRelation: {
59
- entity: entity,
60
- $or: [
61
- {
62
- entityId: entityId,
63
- },
64
- {
65
- entityId: {
66
- $exists: false,
67
- },
68
- }
69
- ],
94
+ filter: filter2,
95
+ }, { dontCollect: true });
96
+ const checkRelationAuth = (relationAuth) => {
97
+ const { destRelation, sourceRelationId, path } = relationAuth;
98
+ let destEntityFilter = this.makePathFilter(destRelation.entity, path, this.schema, {
99
+ userRelation$entity: {
100
+ userId,
101
+ relationId: sourceRelationId,
70
102
  },
71
- },
72
- }, {});
73
- if (result instanceof Promise) {
74
- return result.then(function (r2) { return r2.map(function (ele) { return ele.destRelation; }); });
75
- }
76
- return result.map(function (ele) { return ele.destRelation; });
77
- };
78
- // 后台检查filter是否满足relation约束
79
- RelationAuth.prototype.checkRelationAsync = function (entity, operation, context) {
80
- return tslib_1.__awaiter(this, void 0, void 0, function () {
81
- return tslib_1.__generator(this, function (_a) {
82
- switch (_a.label) {
83
- case 0:
84
- if (context.isRoot()) {
85
- return [2 /*return*/];
86
- }
87
- return [4 /*yield*/, this.checkActions2(entity, operation, context)];
88
- case 1:
89
- _a.sent();
90
- return [2 /*return*/];
91
- }
92
103
  });
93
- });
94
- };
95
- RelationAuth.prototype.checkOperateSpecialEntities2 = function (entity2, action, filter, context) {
96
- switch (entity2) {
97
- case 'userRelation': {
98
- (0, assert_1.default)(!(filter instanceof Array));
99
- (0, assert_1.default)(['create', 'remove'].includes(action));
100
- if (action === 'create') {
101
- (0, assert_1.default)(!(filter instanceof Array));
102
- var _a = filter, entity = _a.entity, entityId = _a.entityId, relationId_1 = _a.relationId;
103
- // 创建userRelation如果是领取动作,先暂使用root身份通过
104
- var destRelations = this.getGrantedRelationIds(entity, entityId, context);
105
- if (destRelations instanceof Promise) {
106
- return destRelations.then(function (r2) {
107
- if (relationId_1 && !r2.find(function (ele) { return ele.id === relationId_1; }) || r2.length === 0) {
108
- return false;
109
- }
110
- return true;
111
- });
112
- }
113
- // 若指定了要create的relation,则必须有该relationId存在,否则只要有任意可授权的relation即可
114
- if (relationId_1 && !destRelations.find(function (ele) { return ele.id === relationId_1; }) || destRelations.length === 0) {
115
- return false;
116
- }
117
- return true;
104
+ if (action === 'create') {
105
+ const { entity, entityId } = filter;
106
+ (0, assert_1.default)(entity && typeof entity === 'string');
107
+ if (entityId) {
108
+ Object.assign(destEntityFilter, {
109
+ id: entityId,
110
+ });
118
111
  }
119
112
  else {
120
- (0, assert_1.default)(action === 'remove');
121
- var userId = context.getCurrentUserId();
122
- (0, assert_1.default)(filter);
123
- var contained = {
124
- relation: {
125
- relationAuth$destRelation: {
126
- sourceRelation: {
127
- userRelation$relation: {
128
- userId: userId,
129
- },
130
- },
131
- },
132
- },
133
- };
134
- return (0, filter_1.checkFilterContains)(entity2, context, contained, filter, true);
113
+ // userEntityGrant会有这种情况,限定某个对象的范围进行授权
114
+ const { [entity]: entityFilter } = filter;
115
+ (0, assert_1.default)(entityFilter);
116
+ destEntityFilter = (0, filter_1.combineFilters)(entity, this.schema, [destEntityFilter, entityFilter]);
135
117
  }
136
118
  }
119
+ else {
120
+ destEntityFilter = (0, filter_1.combineFilters)(destRelation.entity, this.schema, [destEntityFilter, {
121
+ userRelation$entity: filter,
122
+ }]);
123
+ }
124
+ return context.count(destRelation.entity, {
125
+ filter: destEntityFilter,
126
+ }, { ignoreAttrMiss: true });
127
+ };
128
+ if (relationAuths instanceof Promise) {
129
+ return relationAuths.then((ras) => Promise.all(ras.map(ra => checkRelationAuth(ra)))).then((result) => !!result.find(ele => {
130
+ (0, assert_1.default)(typeof ele === 'number');
131
+ return ele > 0;
132
+ }));
133
+ }
134
+ const result = relationAuths.map(ra => checkRelationAuth(ra));
135
+ return !!result.find(ele => ele > 0);
136
+ }
137
+ checkOperateSpecialEntities2(entity2, action, filter, context) {
138
+ switch (entity2) {
139
+ case 'userRelation': {
140
+ (0, assert_1.default)(!(filter instanceof Array));
141
+ return this.checkUserRelation(context, action, filter);
142
+ }
137
143
  case 'user': {
138
144
  // 对用户的操作由应用自己去管理权限,这里只检查grant/revoke
139
145
  if (['grant', 'revoke'].includes(action)) {
@@ -147,8 +153,19 @@ var RelationAuth = /** @class */ (function () {
147
153
  }
148
154
  }
149
155
  case 'modi': {
150
- // modi的操作权限都是由触发器触发,不用再检测了
151
- return true;
156
+ /** 正常情况下对modi的生成是在触发器下openRootMode,不会走到这里
157
+ * 但是有些例外,如extraFile如果在modi中创建,上传成功之后需要显式生成一条modi,这时对modi的
158
+ * 检查可以转化为对其父entity的update权限检查
159
+ */
160
+ (0, assert_1.default)(action === 'create');
161
+ const { entity, entityId } = filter;
162
+ return this.checkOperation(entity, {
163
+ action: 'update',
164
+ data: {},
165
+ filter: {
166
+ id: entityId,
167
+ },
168
+ }, context);
152
169
  }
153
170
  case 'relation': {
154
171
  // 创建relation目前不支持,以后再说
@@ -158,7 +175,14 @@ var RelationAuth = /** @class */ (function () {
158
175
  // userEntityGrant的创建相当于授权,领取相当于赋权
159
176
  if (['create', 'update', 'remove'].includes(action)) {
160
177
  if (action === 'create') {
161
- return this.checkOperateSpecialEntities2('userRelation', 'create', filter, context);
178
+ const { relationEntity, relationEntityFilter, relationIds } = filter;
179
+ return this.checkOperateSpecialEntities2('userRelation', 'create', {
180
+ entity: relationEntity,
181
+ [relationEntity]: relationEntityFilter,
182
+ relationId: {
183
+ $in: relationIds,
184
+ },
185
+ }, context);
162
186
  }
163
187
  return this.checkOperateSpecialEntities2('userRelation', 'action', {
164
188
  relation: {
@@ -166,71 +190,58 @@ var RelationAuth = /** @class */ (function () {
166
190
  },
167
191
  }, context);
168
192
  }
169
- // 领取和读取动作公开
170
193
  return true;
171
194
  }
172
195
  default: {
173
- (0, assert_1.default)(false, "\u5BF9\u8C61".concat(entity2, "\u7684\u6743\u9650\u63A7\u5236\u6CA1\u6709\u52A0\u4EE5\u63A7\u5236"));
196
+ (0, assert_1.default)(false, `对象${entity2}的权限控制没有加以控制`);
174
197
  }
175
198
  }
176
- };
177
- RelationAuth.prototype.getDeducedEntityFilters = function (entity, filter, actions, context) {
178
- var e_1, _a;
179
- var _this = this;
180
- var entityFilters = [
199
+ }
200
+ getDeducedEntityFilters(entity, filter, actions, context) {
201
+ const entityFilters = [
181
202
  {
182
- entity: entity,
183
- filter: filter,
184
- actions: actions,
203
+ entity,
204
+ filter,
205
+ actions,
185
206
  }
186
207
  ];
187
208
  if (this.authDeduceRelationMap[entity]) {
188
209
  (0, assert_1.default)(this.authDeduceRelationMap[entity] === 'entity');
189
- var _b = filter, deduceEntity = _b.entity, deduceEntityId_1 = _b.entityId;
190
- var deduceFilter = {};
191
- if (deduceEntity && deduceEntityId_1) {
192
- deduceFilter = { id: deduceEntityId_1 };
210
+ let { entity: deduceEntity, entityId: deduceEntityId } = filter;
211
+ let deduceFilter = {};
212
+ if (deduceEntity && deduceEntityId) {
213
+ deduceFilter = { id: deduceEntityId };
193
214
  }
194
215
  else {
195
216
  // 也可能是用cascade方式进行查找,这里有时候filter上会带有两个不同的entity目标,尚未处理(todo!)
196
- var ref = this.schema[entity].attributes.entity.ref;
217
+ const { ref } = this.schema[entity].attributes.entity;
197
218
  (0, assert_1.default)(ref instanceof Array);
198
- try {
199
- for (var ref_1 = tslib_1.__values(ref), ref_1_1 = ref_1.next(); !ref_1_1.done; ref_1_1 = ref_1.next()) {
200
- var refEntity = ref_1_1.value;
201
- if (filter[refEntity]) {
202
- deduceEntity = refEntity;
203
- deduceFilter = filter[refEntity];
204
- break;
205
- }
206
- }
207
- }
208
- catch (e_1_1) { e_1 = { error: e_1_1 }; }
209
- finally {
210
- try {
211
- if (ref_1_1 && !ref_1_1.done && (_a = ref_1.return)) _a.call(ref_1);
219
+ for (const refEntity of ref) {
220
+ if (filter[refEntity]) {
221
+ deduceEntity = refEntity;
222
+ deduceFilter = filter[refEntity];
223
+ break;
212
224
  }
213
- finally { if (e_1) throw e_1.error; }
214
225
  }
215
226
  }
216
- var getRecursiveDeducedFilters_1 = function (deduceEntity, deduceFilter) {
217
- var excludeActions = action_1.readOnlyActions.concat([ /* 'create', 'remove' */]);
218
- var updateActions = _this.schema[deduceEntity].actions.filter(function (a) { return !excludeActions.includes(a); });
227
+ const getRecursiveDeducedFilters = (deduceEntity, deduceFilter) => {
228
+ const excludeActions = action_1.readOnlyActions.concat([ /* 'create', 'remove' */]);
229
+ const updateActions = this.schema[deduceEntity].actions.filter((a) => !excludeActions.includes(a));
219
230
  /* if (!RelationAuth.SPECIAL_ENTITIES.includes(deduceEntity as string)) {
220
231
  return this.getDeducedEntityFilters(deduceEntity, deduceFilter, actions[0] === 'select' ? actions : updateActions, context);
221
232
  }
222
233
  return []; */
223
- return _this.getDeducedEntityFilters(deduceEntity, deduceFilter, actions[0] === 'select' ? actions : updateActions, context);
234
+ return this.getDeducedEntityFilters(deduceEntity, deduceFilter, actions[0] === 'select' ? actions : updateActions, context);
224
235
  };
225
236
  if (deduceEntity && deduceFilter) {
226
- var deducedSelections = getRecursiveDeducedFilters_1(deduceEntity, deduceFilter);
237
+ const deducedSelections = getRecursiveDeducedFilters(deduceEntity, deduceFilter);
227
238
  if (deducedSelections instanceof Promise) {
228
- return deducedSelections.then(function (ds) {
229
- entityFilters.push.apply(entityFilters, tslib_1.__spreadArray([], tslib_1.__read(ds), false));
239
+ return deducedSelections.then((ds) => {
240
+ entityFilters.push(...ds);
230
241
  return entityFilters;
231
242
  });
232
243
  }
233
- entityFilters.push.apply(entityFilters, tslib_1.__spreadArray([], tslib_1.__read(deducedSelections), false));
244
+ entityFilters.push(...deducedSelections);
234
245
  return entityFilters;
235
246
  }
236
247
  else {
@@ -239,89 +250,87 @@ var RelationAuth = /** @class */ (function () {
239
250
  * 这种情况一般发生在entity1 -> entity2上,此时entity2应该是一个固定id查询的filter
240
251
  * 在这里先假设如果碰到了list类型的filter,直接不使用deduce路径上的对象来推导
241
252
  */
242
- var rows2 = context.select(entity, {
253
+ const rows2 = context.select(entity, {
243
254
  data: {
244
255
  id: 1,
245
256
  entity: 1,
246
257
  entityId: 1,
247
258
  },
248
- filter: filter,
259
+ filter,
249
260
  indexFrom: 0,
250
261
  count: 10,
251
262
  }, { dontCollect: true, blockTrigger: true });
252
- var dealWithData_1 = function (rows) {
263
+ const dealWithData = (rows) => {
253
264
  // 这里如果entity指向不同的实体,一般出现这样的查询,则其权限应当不由这条deduce路径处理
254
265
  // 同上,如果找到的行数大于1行,说明deduce路径上的对象不确定,也暂不处理 by Xc 20230725
255
266
  if (rows.length > 1 || rows.length === 0) {
256
267
  if (process.env.NODE_ENV === 'development') {
257
- console.warn("\u8FDB\u884Cdeduce\u63A8\u5BFC\u65F6\u627E\u5230\u4E86".concat(rows.length, "\u884C").concat(entity, "\u6570\u636E"));
268
+ console.warn(`进行deduce推导时找到了${rows.length}行${entity}数据`);
258
269
  }
259
270
  return entityFilters;
260
271
  }
261
- var _a = rows[0], deducedEntity = _a.entity, deducedEntityId = _a.entityId;
272
+ const { entity: deducedEntity, entityId: deducedEntityId } = rows[0];
262
273
  if (!deducedEntity || !deducedEntityId) {
263
274
  // 这种情况会出现在前台缓存里
264
275
  return entityFilters;
265
276
  }
266
- var result = getRecursiveDeducedFilters_1(deducedEntity, {
267
- id: deduceEntityId_1,
277
+ const result = getRecursiveDeducedFilters(deducedEntity, {
278
+ id: deducedEntityId,
268
279
  });
269
280
  if (result instanceof Promise) {
270
- return result.then(function (r2) {
271
- entityFilters.push.apply(entityFilters, tslib_1.__spreadArray([], tslib_1.__read(r2), false));
281
+ return result.then((r2) => {
282
+ entityFilters.push(...r2);
272
283
  return entityFilters;
273
284
  });
274
285
  }
275
- entityFilters.push.apply(entityFilters, tslib_1.__spreadArray([], tslib_1.__read(result), false));
286
+ entityFilters.push(...result);
276
287
  return entityFilters;
277
288
  };
278
289
  if (rows2 instanceof Promise) {
279
- return rows2.then(function (r2) { return dealWithData_1(r2); });
290
+ return rows2.then((r2) => dealWithData(r2));
280
291
  }
281
- return dealWithData_1(rows2);
292
+ return dealWithData(rows2);
282
293
  }
283
294
  }
284
295
  return entityFilters;
285
- };
296
+ }
286
297
  /**
287
298
  * 对于selection,解构出最底层的对象,如果最底层的对象可以被访问,则父对象一定可以
288
299
  * 但对于deduce的子对象,不必再向底层查看(假设deduce对象一般都位于树的最底层附近)
289
300
  * @param entity
290
301
  * @param operation
291
302
  */
292
- RelationAuth.prototype.destructSelection = function (entity, selection) {
293
- var _this = this;
294
- var leafSelections = [];
295
- var destructInner = function (entity2, selection2) {
296
- var _a, _b;
297
- var data = selection2.data, filter = selection2.filter;
298
- var hasOneToMany = false;
299
- for (var attr in data) {
300
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity2, attr);
303
+ destructSelection(entity, selection) {
304
+ const leafSelections = [];
305
+ const destructInner = (entity2, selection2) => {
306
+ const { data, filter } = selection2;
307
+ let hasOneToMany = false;
308
+ for (const attr in data) {
309
+ const rel = (0, relation_1.judgeRelation)(this.schema, entity2, attr);
301
310
  if (rel instanceof Array) {
302
- var _c = tslib_1.__read(rel, 2), e = _c[0], foreignKey = _c[1];
311
+ const [e, foreignKey] = rel;
303
312
  if (foreignKey) {
304
- (0, assert_1.default)(!_this.authDeduceRelationMap[e]);
313
+ (0, assert_1.default)(!this.authDeduceRelationMap[e]);
305
314
  hasOneToMany = true;
306
315
  destructInner(e, {
307
316
  data: data[attr].data,
308
- filter: (0, filter_1.combineFilters)(e, _this.schema, [(_a = {},
309
- _a[foreignKey.slice(0, foreignKey.length - 2)] = filter,
310
- _a), data[attr].filter || {}]),
317
+ filter: (0, filter_1.combineFilters)(e, this.schema, [{
318
+ [foreignKey.slice(0, foreignKey.length - 2)]: filter,
319
+ }, data[attr].filter || {}]),
311
320
  });
312
321
  }
313
322
  else {
314
- if (!_this.authDeduceRelationMap[e]) {
323
+ if (!this.authDeduceRelationMap[e]) {
315
324
  hasOneToMany = true;
316
325
  destructInner(e, {
317
326
  data: data[attr].data,
318
- filter: (0, filter_1.combineFilters)(e, _this.schema, [(_b = {},
319
- _b[entity2] = filter,
320
- _b), data[attr].filter || {}]),
327
+ filter: (0, filter_1.combineFilters)(e, this.schema, [{
328
+ [entity2]: filter,
329
+ }, data[attr].filter || {}]),
321
330
  });
322
331
  }
323
332
  else {
324
- (0, assert_1.default)(_this.authDeduceRelationMap[e] === 'entity');
333
+ (0, assert_1.default)(this.authDeduceRelationMap[e] === 'entity');
325
334
  }
326
335
  }
327
336
  }
@@ -329,37 +338,39 @@ var RelationAuth = /** @class */ (function () {
329
338
  if (!hasOneToMany) {
330
339
  leafSelections.push({
331
340
  entity: entity2,
332
- filter: filter,
341
+ filter,
333
342
  });
334
343
  }
335
344
  };
336
345
  destructInner(entity, (0, lodash_1.cloneDeep)(selection));
337
346
  return leafSelections;
338
- };
347
+ }
339
348
  /**
340
349
  * 对于operation,解构出一个树形结构,以方便自顶向下的进行访问
341
350
  * 但对于deduce的子对象,不必再向底层查看
342
351
  * @param entity
343
352
  * @param selection
344
353
  */
345
- RelationAuth.prototype.destructOperation = function (entity2, operation2, userId) {
346
- var _this = this;
354
+ destructOperation(entity2, operation2, userId) {
347
355
  /**
348
356
  * 对create动作,把data中的cascade部分剔除后作为filter参与后续的检验
349
357
  * @param operation
350
358
  * @returns
351
359
  */
352
- var makeCreateFilter = function (entity, operation) {
353
- var _a;
354
- var data = operation.data, filter = operation.filter;
360
+ const makeCreateFilter = (entity, operation) => {
361
+ const { data, filter } = operation;
355
362
  (0, assert_1.default)(!(data instanceof Array));
356
363
  if (data) {
357
- var data2 = {};
358
- for (var attr in data) {
359
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity, attr);
364
+ const data2 = {};
365
+ for (const attr in data) {
366
+ const rel = (0, relation_1.judgeRelation)(this.schema, entity, attr);
360
367
  if (rel === 1) {
361
368
  // 只需要记住id和各种外键属性,不这样处理有些古怪的属性比如coordinate,其作为createdata和作为filter并不同构
362
- if ((['id', 'entity', 'entityId'].includes(attr) || ((_a = _this.schema[entity].attributes[attr]) === null || _a === void 0 ? void 0 : _a.type) === 'ref') && typeof data[attr] === 'string') {
369
+ /* if ((['id', 'entity', 'entityId'].includes(attr) || this.schema[entity].attributes[attr as any]?.type === 'ref') && typeof data[attr] === 'string') {
370
+ data2[attr] = data[attr];
371
+ } */
372
+ // 假设不再成立,userEntityGrant需要relationEntity这样的属性
373
+ if (!['geometry', 'geography', 'st_geometry', 'st_point'].includes(this.schema[entity].attributes[attr]?.type)) {
363
374
  data2[attr] = data[attr];
364
375
  }
365
376
  }
@@ -368,12 +379,11 @@ var RelationAuth = /** @class */ (function () {
368
379
  }
369
380
  return filter;
370
381
  };
371
- var addChild = function (node, path, child) {
372
- var _a;
382
+ const addChild = (node, path, child) => {
373
383
  // 在这里要把可以被node deduce出来的child处理掉
374
- var paths = path.split('$');
384
+ const paths = path.split('$');
375
385
  (0, assert_1.default)(paths.length >= 2);
376
- if (_this.authDeduceRelationMap[child.entity] === paths[1]) {
386
+ if (this.authDeduceRelationMap[child.entity] === paths[1]) {
377
387
  (0, assert_1.default)(paths[1] === 'entity', '当前只支持entity外键上的deduce');
378
388
  return false;
379
389
  }
@@ -386,86 +396,152 @@ var RelationAuth = /** @class */ (function () {
386
396
  }
387
397
  }
388
398
  else {
389
- Object.assign(node.children, (_a = {},
390
- _a[path] = child,
391
- _a));
399
+ Object.assign(node.children, {
400
+ [path]: child,
401
+ });
392
402
  }
393
403
  return true;
394
404
  };
395
- var destructInner = function (entity, operation,
405
+ const destructInner = (entity, operation,
396
406
  // extraFilter?: ED[T2]['Selection']['filter'],
397
- path, child, hasParent) {
398
- var action = operation.action, data = operation.data, filter = operation.filter;
399
- var filter2 = action === 'create' ? makeCreateFilter(entity, operation) : filter;
407
+ path, child, hasParent, extraFilter) => {
408
+ const { action, data, filter } = operation;
409
+ const filter2 = action === 'create' ? makeCreateFilter(entity, operation) : (0, lodash_1.cloneDeep)(filter);
400
410
  (0, assert_1.default)(filter2);
411
+ if (extraFilter) {
412
+ Object.assign(filter2, extraFilter);
413
+ }
401
414
  // const filter3 = extraFilter ? combineFilters(entity, schema, [filter2, extraFilter]) : filter2;
402
- var me = {
415
+ const me = {
403
416
  entity: entity,
404
417
  filter: filter2,
405
418
  children: {},
406
- action: action,
419
+ action,
407
420
  };
408
- var root = me;
421
+ let root = me;
409
422
  // 如果当前对象是一个toModi的,意味着它的cascadeUpdate会全部被变为modi去缓存,因此不需要再向下检查了
410
423
  // modi被apply时,这些modi产生的更新才会被实际检查
411
- var isModiUpdate = _this.schema[entity].toModi && action !== 'remove';
424
+ // 这里可能有问题,再思考思考 by Xc 20231111
425
+ const isModiUpdate = this.schema[entity].toModi && action !== 'remove';
412
426
  if (child) {
413
427
  (0, assert_1.default)(path);
414
428
  addChild(me, path, child);
415
429
  }
416
- var _loop_1 = function (attr) {
417
- var rel = (0, relation_1.judgeRelation)(_this.schema, entity, attr);
430
+ (0, assert_1.default)(!(data instanceof Array));
431
+ for (const attr in data) {
432
+ const rel = (0, relation_1.judgeRelation)(this.schema, entity, attr);
418
433
  if (rel === 2 && !isModiUpdate) {
419
434
  (0, assert_1.default)(root === me && !hasParent, 'cascadeUpdate必须是树结构,避免森林');
420
- root = destructInner(attr, data[attr], "".concat(entity, "$entity"), me);
435
+ const mtoOperation = data[attr];
436
+ root = destructInner(attr, mtoOperation, `${entity}$entity`, me);
421
437
  }
422
438
  else if (typeof rel === 'string' && !isModiUpdate) {
423
439
  (0, assert_1.default)(root === me && !hasParent, 'cascadeUpdate必须是树结构,避免森林');
424
- root = destructInner(rel, data[attr], "".concat(entity, "$").concat(attr), me);
440
+ root = destructInner(rel, data[attr], `${entity}$${attr}`, me);
425
441
  }
426
442
  else if (rel instanceof Array && !isModiUpdate) {
427
- var _a = tslib_1.__read(rel, 2), e_2 = _a[0], f = _a[1];
428
- var otmOperations = data[attr];
429
- if (e_2 === 'userRelation' && entity !== 'user') {
443
+ const [e, f] = rel;
444
+ const otmOperations = data[attr];
445
+ /**
446
+ * 这里目前在cascadeUpdate的过程中,只有当一对多个userRelation的操作需要将entity和entityId复制到子对象上
447
+ * 因为对userRelation的判断是走的特殊路径,无法利用父对象的actionAuth
448
+ * 其它对象情况不需要复制,因为应用中必须要能保证(前台传来的)父对象的filter不依赖于子对象的条件
449
+ */
450
+ let extraFilter = undefined;
451
+ if (e === 'userRelation' && entity !== 'user') {
430
452
  me.userRelations = [];
431
- var dealWithUserRelation_1 = function (userRelation) {
432
- var _a;
433
- var action = userRelation.action, data = userRelation.data;
434
- (0, assert_1.default)(action === 'create', 'cascade更新中只允许创建userRelation');
435
- var attrs = Object.keys(data);
436
- (0, assert_1.default)((0, lodash_1.difference)(attrs, Object.keys(_this.schema.userRelation.attributes).concat('id')).length === 0);
437
- if (data.userId === userId) {
438
- (_a = me.userRelations) === null || _a === void 0 ? void 0 : _a.push(data);
453
+ extraFilter = {
454
+ entity,
455
+ entityId: filter2.id,
456
+ };
457
+ const dealWithUserRelation = (userRelation) => {
458
+ const { action, data } = userRelation;
459
+ if (action === 'create') {
460
+ const attrs = Object.keys(data);
461
+ (0, assert_1.default)((0, lodash_1.difference)(attrs, Object.keys(this.schema.userRelation.attributes).concat('id')).length === 0);
462
+ if (data.userId === userId) {
463
+ me.userRelations?.push(data);
464
+ }
465
+ (0, assert_1.default)(filter2.id);
439
466
  }
440
467
  };
441
468
  if (otmOperations instanceof Array) {
442
- otmOperations.forEach(function (otmOperation) { return dealWithUserRelation_1(otmOperation); });
469
+ otmOperations.forEach((otmOperation) => dealWithUserRelation(otmOperation));
443
470
  }
444
471
  else {
445
- dealWithUserRelation_1(otmOperations);
472
+ dealWithUserRelation(otmOperations);
446
473
  }
447
474
  }
448
- else {
449
- if (otmOperations instanceof Array) {
450
- otmOperations.forEach(function (otmOperation) {
451
- var son = destructInner(e_2, otmOperation, undefined, undefined, true);
452
- addChild(me, attr, son);
453
- });
454
- }
455
- else {
456
- var son = destructInner(e_2, otmOperations, undefined, undefined, true);
475
+ if (otmOperations instanceof Array) {
476
+ otmOperations.forEach((otmOperation) => {
477
+ const son = destructInner(e, otmOperation, undefined, undefined, true, extraFilter);
457
478
  addChild(me, attr, son);
458
- }
479
+ });
480
+ }
481
+ else {
482
+ const son = destructInner(e, otmOperations, undefined, undefined, true, extraFilter);
483
+ addChild(me, attr, son);
459
484
  }
460
485
  }
461
- };
462
- for (var attr in data) {
463
- _loop_1(attr);
464
486
  }
465
487
  return root;
466
488
  };
467
- return destructInner(entity2, (0, lodash_1.cloneDeep)(operation2));
468
- };
489
+ return destructInner(entity2, operation2);
490
+ }
491
+ makePathFilter(entity, path, schema, filter) {
492
+ const { value, recursive } = path;
493
+ if (value === '') {
494
+ (0, assert_1.default)(!recursive);
495
+ return filter;
496
+ }
497
+ const paths = value.split('.');
498
+ const makeRecursiveFilter = (recursiveDepth) => {
499
+ if (recursiveDepth > 0) {
500
+ return {
501
+ $or: [
502
+ filter,
503
+ {
504
+ parent: makeRecursiveFilter(recursiveDepth - 1)
505
+ }
506
+ ]
507
+ };
508
+ }
509
+ return filter;
510
+ };
511
+ const makeInner = (idx, e2) => {
512
+ const attr = paths[idx];
513
+ if (idx === paths.length) {
514
+ if (!recursive) {
515
+ return filter;
516
+ }
517
+ else {
518
+ // 在最后一个对象上存在递归,用or连接处理
519
+ const { recursiveDepth } = schema[e2];
520
+ (0, assert_1.default)(recursiveDepth > 0);
521
+ return makeRecursiveFilter(recursiveDepth);
522
+ }
523
+ }
524
+ else {
525
+ const rel = (0, relation_1.judgeRelation)(schema, e2, attr);
526
+ let e3;
527
+ if (rel === 2) {
528
+ e3 = attr;
529
+ }
530
+ else if (typeof rel === 'string') {
531
+ e3 = rel;
532
+ }
533
+ else {
534
+ (0, assert_1.default)(rel instanceof Array);
535
+ e3 = rel[0];
536
+ }
537
+ const f = makeInner(idx + 1, e3);
538
+ return {
539
+ [attr]: f,
540
+ };
541
+ }
542
+ };
543
+ return makeInner(0, entity);
544
+ }
469
545
  /**
470
546
  * 对所有满足操作要求的actionAuth加以判断,找到可以满足当前用户身份的actionAuth
471
547
  * @param entity
@@ -474,41 +550,30 @@ var RelationAuth = /** @class */ (function () {
474
550
  * @param context
475
551
  * @return
476
552
  */
477
- RelationAuth.prototype.filterActionAuths = function (entity, filter, actionAuths, context) {
478
- var result = actionAuths.map(function (ele) {
479
- var paths = ele.paths, relation = ele.relation, relationId = ele.relationId;
553
+ filterActionAuths(entity, filter, actionAuths, context) {
554
+ const result = actionAuths.map((ele) => {
555
+ const { path, relation, relationId } = ele;
480
556
  // 在cache中,可能出现relation外键指向的对象为null的情况,要容错
481
557
  if (relationId) {
482
558
  if (relation) {
483
- var userRelations = relation.userRelation$relation;
559
+ const { userRelation$relation: userRelations } = relation;
484
560
  if (userRelations.length > 0) {
485
- var entityIds = (0, lodash_1.uniq)(userRelations.map(function (ele) { return ele.entityId; }));
486
- var idFilter_1 = entityIds.length > 1 ? {
487
- $in: entityIds,
488
- } : entityIds[0];
489
- (0, assert_1.default)(idFilter_1);
490
- var pathFilters_1 = paths.map(function (path) {
491
- if (path) {
492
- return (0, lodash_1.set)({}, path, {
493
- id: idFilter_1,
494
- });
495
- }
496
- return {
497
- id: idFilter_1,
498
- };
561
+ const entityIds = (0, lodash_1.uniq)(userRelations.map(ele => ele.entityId));
562
+ const pathFilter = this.makePathFilter(entity, path, this.schema, {
563
+ id: entityIds.length > 0 ? {
564
+ $in: entityIds,
565
+ } : entityIds[0],
499
566
  });
500
- // 这里是或关系,只要对象落在任意一条路径上就可以
501
- var contained_1 = (0, filter_1.combineFilters)(entity, context.getSchema(), pathFilters_1, true);
502
- var contains_1 = (0, filter_1.checkFilterContains)(entity, context, contained_1, filter, true);
503
- if (contains_1 instanceof Promise) {
504
- return contains_1.then(function (c) {
567
+ const contains = (0, filter_1.checkFilterContains)(entity, context, pathFilter, filter, true);
568
+ if (contains instanceof Promise) {
569
+ return contains.then((c) => {
505
570
  if (c) {
506
571
  return ele;
507
572
  }
508
573
  return;
509
574
  });
510
575
  }
511
- if (contains_1) {
576
+ if (contains) {
512
577
  return ele;
513
578
  }
514
579
  return;
@@ -517,11 +582,12 @@ var RelationAuth = /** @class */ (function () {
517
582
  return;
518
583
  }
519
584
  // 说明是通过userId关联
520
- var pathFilters = paths.map(function (path) { return (0, lodash_1.set)({}, "".concat(path, ".id"), context.getCurrentUserId()); });
521
- var contained = (0, filter_1.combineFilters)(entity, context.getSchema(), pathFilters, true);
522
- var contains = (0, filter_1.checkFilterContains)(entity, context, contained, filter, true);
585
+ const pathFilter = this.makePathFilter(entity, path, this.schema, {
586
+ id: context.getCurrentUserId(),
587
+ });
588
+ const contains = (0, filter_1.checkFilterContains)(entity, context, pathFilter, filter, true);
523
589
  if (contains instanceof Promise) {
524
- return contains.then(function (c) {
590
+ return contains.then((c) => {
525
591
  if (c) {
526
592
  return ele;
527
593
  }
@@ -532,11 +598,11 @@ var RelationAuth = /** @class */ (function () {
532
598
  return ele;
533
599
  }
534
600
  });
535
- if (result.find(function (ele) { return ele instanceof Promise; })) {
536
- return Promise.all(result).then(function (r2) { return r2.filter(function (ele) { return !!ele; }); });
601
+ if (result.find(ele => ele instanceof Promise)) {
602
+ return Promise.all(result).then((r2) => r2.filter(ele => !!ele));
537
603
  }
538
- return result.filter(function (ele) { return !!ele; });
539
- };
604
+ return result.filter(ele => !!ele);
605
+ }
540
606
  /**
541
607
  * 对于有些特殊的查询(带很多$or的查询,多发生在系统级别),单个actionAuth无法满足,需要共同加以判定
542
608
  * @param entity
@@ -545,51 +611,40 @@ var RelationAuth = /** @class */ (function () {
545
611
  * @param context
546
612
  * @param actions
547
613
  */
548
- RelationAuth.prototype.checkActionAuthInGroup = function (entity, filter, actionAuths, context) {
549
- var filters = actionAuths.filter(function (ele) { return ele.destEntity === entity; }).map(function (ele) {
550
- var paths = ele.paths, relation = ele.relation, relationId = ele.relationId;
614
+ checkActionAuthInGroup(entity, filter, actionAuths, context) {
615
+ const filters = actionAuths.filter(ele => ele.path.destEntity === entity).map((ele) => {
616
+ const { path, relation, relationId } = ele;
551
617
  if (relationId) {
552
618
  (0, assert_1.default)(relation);
553
- var userRelations = relation.userRelation$relation;
619
+ const { userRelation$relation: userRelations } = relation;
554
620
  (0, assert_1.default)(userRelations.length > 0);
555
- var entityIds = (0, lodash_1.uniq)(userRelations.map(function (ele) { return ele.entityId; }));
556
- var idFilter_2 = entityIds.length > 1 ? {
557
- $in: entityIds,
558
- } : entityIds[0];
559
- (0, assert_1.default)(idFilter_2);
560
- var pathFilters = paths.map(function (path) {
561
- if (path) {
562
- return (0, lodash_1.set)({}, path, {
563
- id: idFilter_2,
564
- });
565
- }
566
- return {
567
- id: idFilter_2
568
- };
621
+ const entityIds = (0, lodash_1.uniq)(userRelations.map(ele => ele.entityId));
622
+ const pathFilter = this.makePathFilter(entity, path, this.schema, {
623
+ id: entityIds.length > 0 ? {
624
+ $in: entityIds,
625
+ } : entityIds[0],
569
626
  });
570
- return pathFilters;
627
+ return pathFilter;
571
628
  }
572
629
  // 说明是通过userId关联
573
- return paths.map(function (path) { return (0, lodash_1.set)({}, "".concat(path, ".id"), context.getCurrentUserId()); });
630
+ return this.makePathFilter(entity, path, this.schema, {
631
+ id: context.getCurrentUserId(),
632
+ });
574
633
  });
575
- var groupFilter = (0, filter_1.combineFilters)(entity, this.schema, filters.flat(), true);
634
+ const groupFilter = (0, filter_1.combineFilters)(entity, this.schema, filters, true);
576
635
  if (groupFilter) {
577
636
  return (0, filter_1.checkFilterContains)(entity, context, groupFilter, filter, true);
578
637
  }
579
638
  return false;
580
- };
581
- RelationAuth.prototype.checkSelection = function (entity, selection, context) {
582
- var _this = this;
583
- var leafSelections = this.destructSelection(entity, selection);
584
- var deducedLeafSelections = leafSelections.map(function (_a) {
585
- var entity = _a.entity, filter = _a.filter;
586
- return _this.getDeducedEntityFilters(entity, filter, ['select'], context);
587
- });
588
- var checkDeducedLeafSelections = function (dlSelections2) {
589
- var dlSelections = dlSelections2.filter(function (ele) {
590
- var entities = ele.map(function (ele2) { return ele2.entity; });
639
+ }
640
+ checkSelection(entity, selection, context) {
641
+ const leafSelections = this.destructSelection(entity, selection);
642
+ const deducedLeafSelections = leafSelections.map(({ entity, filter }) => this.getDeducedEntityFilters(entity, filter, ['select'], context));
643
+ const checkDeducedLeafSelections = (dlSelections2) => {
644
+ const dlSelections = dlSelections2.filter((ele) => {
645
+ const entities = ele.map(ele2 => ele2.entity);
591
646
  // 同一个leaf的deducedSelections中只要有一个能通过就足够了
592
- if ((0, lodash_1.intersection)(_this.selectFreeEntities, entities).length > 0) {
647
+ if ((0, lodash_1.intersection)(this.selectFreeEntities, entities).length > 0) {
593
648
  return false;
594
649
  }
595
650
  if ((0, lodash_1.intersection)(RelationAuth.SPECIAL_ENTITIES, entities).length > 0) {
@@ -604,16 +659,20 @@ var RelationAuth = /** @class */ (function () {
604
659
  if (!context.getCurrentUserId()) {
605
660
  throw new types_1.OakUnloggedInException();
606
661
  }
607
- var allEntities = [];
608
- dlSelections.forEach(function (ele) { return ele.forEach(function (_a) {
609
- var entity = _a.entity;
662
+ const allEntities = [];
663
+ dlSelections.forEach((ele) => ele.forEach(({ entity }) => {
610
664
  allEntities.push(entity);
611
- }); });
612
- var actionAuths = context.select('actionAuth', {
665
+ }));
666
+ const actionAuths = context.select('actionAuth', {
613
667
  data: {
614
668
  id: 1,
615
- paths: 1,
616
- destEntity: 1,
669
+ path: {
670
+ id: 1,
671
+ value: 1,
672
+ sourceEntity: 1,
673
+ destEntity: 1,
674
+ recursive: 1,
675
+ },
617
676
  deActions: 1,
618
677
  relation: {
619
678
  id: 1,
@@ -634,8 +693,10 @@ var RelationAuth = /** @class */ (function () {
634
693
  deActions: {
635
694
  $contains: 'select',
636
695
  },
637
- destEntity: {
638
- $in: allEntities,
696
+ path: {
697
+ destEntity: {
698
+ $in: allEntities,
699
+ },
639
700
  },
640
701
  $or: [
641
702
  {
@@ -652,48 +713,37 @@ var RelationAuth = /** @class */ (function () {
652
713
  }
653
714
  ]
654
715
  }
655
- }, { dontCollect: true, ignoreForeignKeyMiss: true });
716
+ }, { dontCollect: true, ignoreAttrMiss: true });
656
717
  /**
657
718
  * 返回的结果中,第一层为leafNode,必须全通过,第二层为单个leafNode上的deduce,通过一个就可以
658
719
  * @param result
659
720
  * @returns
660
721
  */
661
- var checkResult = function (result) {
662
- var e_3, _a;
663
- var idx = 0;
664
- try {
665
- for (var result_1 = tslib_1.__values(result), result_1_1 = result_1.next(); !result_1_1.done; result_1_1 = result_1.next()) {
666
- var r1 = result_1_1.value;
667
- var r2 = r1.find(function (ele) { return ele === true; });
668
- if (!r2) {
669
- if (process.env.NODE_ENV === 'development') {
670
- console.warn('对象的select权限被否决,请检查', dlSelections[idx]);
671
- }
672
- return false;
722
+ const checkResult = (result) => {
723
+ let idx = 0;
724
+ for (const r1 of result) {
725
+ const r2 = r1.find(ele => ele === true);
726
+ if (!r2) {
727
+ if (process.env.NODE_ENV === 'development') {
728
+ console.warn('对象的select权限被否决,请检查', dlSelections[idx]);
673
729
  }
730
+ return false;
674
731
  }
675
732
  }
676
- catch (e_3_1) { e_3 = { error: e_3_1 }; }
677
- finally {
678
- try {
679
- if (result_1_1 && !result_1_1.done && (_a = result_1.return)) _a.call(result_1);
680
- }
681
- finally { if (e_3) throw e_3.error; }
682
- }
683
733
  return true;
684
734
  };
685
735
  if (actionAuths instanceof Promise) {
686
736
  (0, assert_1.default)(context instanceof AsyncRowStore_1.AsyncContext);
687
- return actionAuths.then(function (aas) { return Promise.all(dlSelections.map(function (ele) { return Promise.all(ele.map(function (ele2) { return _this.checkActionAuthInGroup(ele2.entity, ele2.filter, aas, context); })); })).then(function (result) { return checkResult(result); }); });
737
+ return actionAuths.then((aas) => Promise.all(dlSelections.map((ele) => Promise.all(ele.map((ele2) => this.checkActionAuthInGroup(ele2.entity, ele2.filter, aas, context))))).then((result) => checkResult(result)));
688
738
  }
689
- return checkResult(dlSelections.map(function (ele) { return ele.map(function (ele2) { return _this.checkActionAuthInGroup(ele2.entity, ele2.filter, actionAuths, context); }); }));
739
+ return checkResult(dlSelections.map(ele => ele.map(ele2 => this.checkActionAuthInGroup(ele2.entity, ele2.filter, actionAuths, context))));
690
740
  };
691
741
  if (deducedLeafSelections[0] instanceof Promise) {
692
742
  return Promise.all(deducedLeafSelections)
693
- .then(function (dls) { return checkDeducedLeafSelections(dls); });
743
+ .then((dls) => checkDeducedLeafSelections(dls));
694
744
  }
695
745
  return checkDeducedLeafSelections(deducedLeafSelections);
696
- };
746
+ }
697
747
  /**
698
748
  * 此函数判定一个结点是否能通过权限检测,同时寻找该结点本身对象上成立的actionAuth,用于本结点子孙结点的快速检测
699
749
  * 如果结点因其deduce的对象通过了检测,其被推断对象的actionAuth无法用于更低对象的权限检测
@@ -701,41 +751,44 @@ var RelationAuth = /** @class */ (function () {
701
751
  * @param context
702
752
  * @returns
703
753
  */
704
- RelationAuth.prototype.findActionAuthsOnNode = function (node, context) {
705
- var _this = this;
706
- var entity = node.entity, filter = node.filter, action = node.action, userRelations = node.userRelations;
707
- var deducedEntityFilters2 = this.getDeducedEntityFilters(entity, filter, [action], context);
754
+ findActionAuthsOnNode(node, context) {
755
+ const { entity, filter, action, userRelations } = node;
756
+ const deducedEntityFilters2 = this.getDeducedEntityFilters(entity, filter, [action], context);
708
757
  /**
709
758
  * 搜索判定是否允许自建对象,自建的条件是 path = '',destEntity === entity
710
759
  * @param actionAuths
711
760
  * @returns
712
761
  */
713
- var findOwnCreateUserRelation = function (actionAuths) {
762
+ const findOwnCreateUserRelation = (actionAuths) => {
714
763
  if (userRelations && userRelations.length > 0) {
715
- (0, assert_1.default)(action === 'create');
716
- var ars = actionAuths.filter(function (ar) { return !!userRelations.find(function (ur) { return ur.relationId === ar.relationId; }) && ar.paths.includes('') && ar.destEntity === entity; });
764
+ const ars = actionAuths.filter((ar) => !!userRelations.find((ur) => ur.relationId === ar.relationId) && ar.path.value === '' && ar.path.destEntity === entity);
717
765
  if (ars.length > 0) {
718
766
  return ars;
719
767
  }
720
768
  }
721
769
  };
722
- var actionAuthOnEntities = [];
723
- var dealWithDeducedEntityFilters = function (deducedEntityFilters) {
724
- var specialEntities = deducedEntityFilters.filter(function (ele) { return RelationAuth.SPECIAL_ENTITIES.includes(ele.entity); });
725
- var unspecicalEntities = deducedEntityFilters.filter(function (ele) { return !RelationAuth.SPECIAL_ENTITIES.includes(ele.entity); });
726
- var result = [];
770
+ const actionAuthOnEntities = [];
771
+ const dealWithDeducedEntityFilters = (deducedEntityFilters) => {
772
+ const specialEntities = deducedEntityFilters.filter(ele => RelationAuth.SPECIAL_ENTITIES.includes(ele.entity));
773
+ const unspecicalEntities = deducedEntityFilters.filter(ele => !RelationAuth.SPECIAL_ENTITIES.includes(ele.entity));
774
+ const result = [];
727
775
  if (specialEntities.length > 0) {
728
776
  // 对于deduce出来的special对象,直接判定create应该问题不大,否则写起来太烦琐(具体情况遇到了再调试)
729
- result.push.apply(result, tslib_1.__spreadArray([], tslib_1.__read(specialEntities.map(function (ele) { return _this.checkOperateSpecialEntities2(ele.entity, ele.entity === entity ? node.action : 'create', ele.filter, context); })), false));
777
+ result.push(...specialEntities.map(ele => this.checkOperateSpecialEntities2(ele.entity, ele.entity === entity ? node.action : 'create', ele.filter, context)));
730
778
  }
731
779
  if (unspecicalEntities.length > 0) {
732
- var allEntities = unspecicalEntities.map(function (ele) { return ele.entity; });
733
- var allActions = (0, lodash_1.uniq)(unspecicalEntities.map(function (ele) { return ele.actions; }).flat());
734
- var actionAuths2 = context.select('actionAuth', {
780
+ const allEntities = unspecicalEntities.map(ele => ele.entity);
781
+ const allActions = (0, lodash_1.uniq)(unspecicalEntities.map(ele => ele.actions).flat());
782
+ const actionAuths2 = context.select('actionAuth', {
735
783
  data: {
736
784
  id: 1,
737
- paths: 1,
738
- destEntity: 1,
785
+ path: {
786
+ id: 1,
787
+ destEntity: 1,
788
+ sourceEntity: 1,
789
+ value: 1,
790
+ recursive: 1,
791
+ },
739
792
  deActions: 1,
740
793
  relation: {
741
794
  id: 1,
@@ -753,52 +806,54 @@ var RelationAuth = /** @class */ (function () {
753
806
  },
754
807
  },
755
808
  filter: {
756
- destEntity: {
757
- $in: allEntities,
809
+ path: {
810
+ destEntity: {
811
+ $in: allEntities,
812
+ }
758
813
  },
759
814
  deActions: {
760
815
  $overlaps: allActions,
761
816
  },
762
817
  }
763
- }, { dontCollect: true, ignoreForeignKeyMiss: true });
764
- var checkActionAuths_1 = function (actionAuths) {
765
- var created = findOwnCreateUserRelation(actionAuths);
818
+ }, { dontCollect: true, ignoreAttrMiss: true });
819
+ const checkActionAuths = (actionAuths) => {
820
+ const created = findOwnCreateUserRelation(actionAuths);
766
821
  if (created) {
767
- actionAuthOnEntities.push.apply(actionAuthOnEntities, tslib_1.__spreadArray([], tslib_1.__read(created), false));
822
+ actionAuthOnEntities.push(...created);
768
823
  return true;
769
824
  }
770
- var result = deducedEntityFilters.map(function (ele) {
771
- var ars2 = actionAuths.filter(function (ele2) { return ele2.destEntity === ele.entity && (0, lodash_1.intersection)(ele2.deActions, ele.actions).length > 0; } // 这里只要overlap就可以了
825
+ const result = deducedEntityFilters.map((ele) => {
826
+ const ars2 = actionAuths.filter(ele2 => ele2.path.destEntity === ele.entity && (0, lodash_1.intersection)(ele2.deActions, ele.actions).length > 0 // 这里只要overlap就可以了
772
827
  );
773
- var ars3 = _this.filterActionAuths(ele.entity, ele.filter, ars2, context);
774
- var checkFilteredArs = function (actionAuths2) {
828
+ const ars3 = this.filterActionAuths(ele.entity, ele.filter, ars2, context);
829
+ const checkFilteredArs = (actionAuths2) => {
775
830
  if (actionAuths2.length > 0) {
776
831
  if (ele.entity === entity) {
777
- actionAuthOnEntities.push.apply(actionAuthOnEntities, tslib_1.__spreadArray([], tslib_1.__read(actionAuths2), false));
832
+ actionAuthOnEntities.push(...actionAuths2);
778
833
  }
779
834
  return true;
780
835
  }
781
836
  return false;
782
837
  };
783
838
  if (ars3 instanceof Promise) {
784
- return ars3.then(function (ars4) { return checkFilteredArs(ars4); });
839
+ return ars3.then((ars4) => checkFilteredArs(ars4));
785
840
  }
786
841
  return checkFilteredArs(ars3);
787
842
  });
788
- if (result.find(function (ele) { return ele instanceof Promise; })) {
789
- return Promise.all(result).then(function (r2) { return r2.includes(true); });
843
+ if (result.find(ele => ele instanceof Promise)) {
844
+ return Promise.all(result).then((r2) => r2.includes(true));
790
845
  }
791
846
  return result.includes(true);
792
847
  };
793
848
  if (actionAuths2 instanceof Promise) {
794
- result.push(actionAuths2.then(function (ars2) { return checkActionAuths_1(ars2); }));
849
+ result.push(actionAuths2.then((ars2) => checkActionAuths(ars2)));
795
850
  }
796
851
  else {
797
- result.push(checkActionAuths_1(actionAuths2));
852
+ result.push(checkActionAuths(actionAuths2));
798
853
  }
799
854
  }
800
- if (result.find(function (ele) { return ele instanceof Promise; })) {
801
- return Promise.all(result).then(function (r2) {
855
+ if (result.find(ele => ele instanceof Promise)) {
856
+ return Promise.all(result).then((r2) => {
802
857
  // r2中只有一个通过就能通过
803
858
  if (r2.includes(true)) {
804
859
  return actionAuthOnEntities;
@@ -812,47 +867,46 @@ var RelationAuth = /** @class */ (function () {
812
867
  return false;
813
868
  };
814
869
  if (deducedEntityFilters2 instanceof Promise) {
815
- return deducedEntityFilters2.then(function (def2) { return dealWithDeducedEntityFilters(def2); });
870
+ return deducedEntityFilters2.then((def2) => dealWithDeducedEntityFilters(def2));
816
871
  }
817
872
  return dealWithDeducedEntityFilters(deducedEntityFilters2);
818
- };
819
- RelationAuth.prototype.checkOperationTree2 = function (tree, context) {
820
- var _this = this;
821
- var checkNode = function (node, actionAuths) {
822
- var checkChildren = function (legalPaths) {
823
- var children = node.children;
824
- var childPath = Object.keys(children);
873
+ }
874
+ checkOperationTree2(tree, context) {
875
+ const checkNode = (node, actionAuths) => {
876
+ const checkChildren = (legalPaths) => {
877
+ const { children } = node;
878
+ const childPath = Object.keys(children);
825
879
  if (childPath.length === 0) {
826
880
  return true;
827
881
  }
828
- var childResult = childPath.map(function (childPath) {
829
- var child = children[childPath];
830
- var childEntity = child instanceof Array ? child[0].entity : child.entity;
882
+ const childResult = childPath.map((childPath) => {
883
+ const child = children[childPath];
884
+ const childEntity = child instanceof Array ? child[0].entity : child.entity;
831
885
  // 这里如果该子结点能deduce到父,则直接通过
832
- if (_this.authDeduceRelationMap[childEntity]) {
833
- (0, assert_1.default)(_this.authDeduceRelationMap[childEntity] === 'entity');
834
- var rel = (0, relation_1.judgeRelation)(_this.schema, childEntity, childPath);
886
+ if (this.authDeduceRelationMap[childEntity]) {
887
+ (0, assert_1.default)(this.authDeduceRelationMap[childEntity] === 'entity');
888
+ const rel = (0, relation_1.judgeRelation)(this.schema, childEntity, childPath);
835
889
  if (rel === 2) {
836
890
  return true;
837
891
  }
838
892
  }
839
- var pathToParent = childPath.endsWith('$entity') ? node.entity : childPath.split('$')[1];
893
+ const pathToParent = childPath.endsWith('$entity') ? node.entity : childPath.split('$')[1];
840
894
  if (child instanceof Array) {
841
- var childActions_1 = child.map(function (ele) { return ele.action; });
842
- var childLegalAuths_1 = legalPaths.map(function (ele) {
843
- var paths = ele.paths, relationId = ele.relationId;
844
- var paths2 = paths.map(function (path) { return path ? "".concat(pathToParent, ".").concat(path) : pathToParent; });
895
+ const childActions = child.map(ele => ele.action);
896
+ const childLegalAuths = legalPaths.map((ele) => {
897
+ const { path: { value: pv }, relationId } = ele;
898
+ const pv2 = pv ? `${pathToParent}.${pv}` : pathToParent;
845
899
  return context.select('actionAuth', {
846
900
  data: {
847
901
  id: 1,
848
902
  },
849
903
  filter: {
850
- paths: {
851
- $overlaps: paths2,
904
+ path: {
905
+ value: pv2,
906
+ destEntity: childEntity,
852
907
  },
853
- destEntity: childEntity,
854
908
  deActions: {
855
- $overlaps: childActions_1,
909
+ $overlaps: childActions,
856
910
  },
857
911
  relationId: relationId || {
858
912
  $exists: false,
@@ -860,23 +914,23 @@ var RelationAuth = /** @class */ (function () {
860
914
  }
861
915
  }, { dontCollect: true });
862
916
  }).flat();
863
- if (childLegalAuths_1[0] instanceof Promise) {
864
- return Promise.all(childLegalAuths_1).then(function (clas) { return child.map(function (c) { return checkNode(c, clas); }); });
917
+ if (childLegalAuths[0] instanceof Promise) {
918
+ return Promise.all(childLegalAuths).then((clas) => child.map((c) => checkNode(c, clas)));
865
919
  }
866
- return child.map(function (c) { return checkNode(c, childLegalAuths_1); });
920
+ return child.map((c) => checkNode(c, childLegalAuths));
867
921
  }
868
- var childLegalAuths = legalPaths.map(function (ele) {
869
- var paths = ele.paths, relationId = ele.relationId;
870
- var paths2 = paths.map(function (path) { return path ? "".concat(pathToParent, ".").concat(path) : pathToParent; });
922
+ const childLegalAuths = legalPaths.map((ele) => {
923
+ const { path: { value: pv }, relationId } = ele;
924
+ const pv2 = pv ? `${pathToParent}.${pv}` : pathToParent;
871
925
  return context.select('actionAuth', {
872
926
  data: {
873
927
  id: 1,
874
928
  },
875
929
  filter: {
876
- paths: {
877
- $overlaps: paths2,
930
+ path: {
931
+ value: pv2,
932
+ destEntity: childEntity,
878
933
  },
879
- destEntity: childEntity,
880
934
  deActions: {
881
935
  $overlaps: child.action,
882
936
  },
@@ -887,12 +941,12 @@ var RelationAuth = /** @class */ (function () {
887
941
  }, { dontCollect: true });
888
942
  }).flat();
889
943
  if (childLegalAuths[0] instanceof Promise) {
890
- return Promise.all(childLegalAuths).then(function (clas) { return checkNode(child, clas.flat()); });
944
+ return Promise.all(childLegalAuths).then((clas) => checkNode(child, clas.flat()));
891
945
  }
892
946
  return checkNode(child, childLegalAuths);
893
947
  }).flat();
894
948
  if (childResult[0] instanceof Promise) {
895
- return Promise.all(childResult).then(function (r) { return !r.includes(false); });
949
+ return Promise.all(childResult).then((r) => !r.includes(false));
896
950
  }
897
951
  return !childResult.includes(false);
898
952
  };
@@ -902,8 +956,8 @@ var RelationAuth = /** @class */ (function () {
902
956
  return checkChildren(actionAuths);
903
957
  }
904
958
  // 没有能根据父亲传下来的actionAuth判定,只能自己找
905
- var result = _this.findActionAuthsOnNode(node, context);
906
- var checkResult = function (result2) {
959
+ const result = this.findActionAuthsOnNode(node, context);
960
+ const checkResult = (result2) => {
907
961
  if (result2 === false) {
908
962
  return false;
909
963
  }
@@ -911,224 +965,38 @@ var RelationAuth = /** @class */ (function () {
911
965
  if (node.entity === 'user') {
912
966
  result2.push({
913
967
  id: 'temp',
914
- paths: [''],
968
+ pathId: 'path_temp',
969
+ path: {
970
+ id: 'path_temp',
971
+ destEntity: 'user',
972
+ sourceEntity: 'any',
973
+ value: '',
974
+ $$createAt$$: 1,
975
+ $$updateAt$$: 1,
976
+ $$seq$$: 'temp',
977
+ recursive: false,
978
+ },
915
979
  $$createAt$$: 1,
916
980
  $$updateAt$$: 1,
917
981
  $$seq$$: 'temp',
918
- destEntity: 'user',
919
982
  deActions: [node.action],
920
983
  });
921
984
  }
922
985
  return checkChildren(result2);
923
986
  };
924
987
  if (result instanceof Promise) {
925
- return result.then(function (r2) { return checkResult(r2); });
988
+ return result.then((r2) => checkResult(r2));
926
989
  }
927
990
  return checkResult(result);
928
991
  };
929
992
  return checkNode(tree);
930
- };
931
- /* private checkOperationTree<Cxt extends AsyncContext<ED> | SyncContext<ED>>(tree: OperationTree<ED>, context: Cxt) {
932
- const actionAuths2 = this.findActionAuthsOnNode(tree, context);
933
-
934
- const checkChildNode = (actionAuths: ED['actionAuth']['Schema'][] | Promise<ED['actionAuth']['Schema'][]>, node: OperationTree<ED>): boolean | Promise<boolean> => {
935
- const checkChildNodeInner = (legalAuths: ED['actionAuth']['Schema'][]) => {
936
- // 因为如果children是数组的话,会把数组中所有的action并起来查询,所以在这里还要再确认一次
937
-
938
- const realLegalPaths = legalAuths.filter(
939
- (ele) => {
940
- if (ele.destEntity === node.entity && ele.deActions.includes(node.action)) {
941
- return true;
942
- }
943
- // 有一种例外情况,是在tree的根结点findActionAuthsOnNode时,deduce出了另外一个对象的权限,此时肯定可以通过,但不能再使用这条路径对children进行进一步判断了
944
- if (node === tree) {
945
- return true;
946
- }
947
- return false;
948
- }
949
- );
950
- const checkChildren = () => {
951
- const { children } = node;
952
- const childPath = Object.keys(children);
953
- if (childPath.length === 0) {
954
- return true;
955
- }
956
-
957
- const selfLegalPaths = realLegalPaths.filter(
958
- (ele) => {
959
- if (ele.destEntity === node.entity && ele.deActions.includes(node.action)) {
960
- return true;
961
- }
962
- return false;
963
- }
964
- );
965
- // assert(selfLegalPaths.length > 0, `对象${node.entity as string}的权限检查是用deduce的对象通过的,无法再进一步对子对象加以判断`);
966
- const childResult = childPath.map(
967
- (childPath) => {
968
- const child = children[childPath];
969
- const childEntity = child instanceof Array ? child[0].entity : child.entity;
970
- // 这里如果该子结点能deduce到父,则直接通过
971
- if (this.authDeduceRelationMap[childEntity]) {
972
- assert(this.authDeduceRelationMap[childEntity] === 'entity');
973
- const rel = judgeRelation(this.schema, childEntity, childPath);
974
- if (rel === 2) {
975
- return true;
976
- }
977
- }
978
-
979
- const pathToParent = childPath.endsWith('$entity') ? node.entity as string : childPath.split('$')[1];
980
- if (child instanceof Array) {
981
- const childActions = child.map(ele => ele.action);
982
- const childLegalAuths = selfLegalPaths.map(
983
- (ele) => {
984
- const { paths, relationId } = ele;
985
- const paths2 = paths.map(
986
- (path) => path ? `${pathToParent}.${path}` : pathToParent
987
- );
988
- return context.select('actionAuth', {
989
- data: {
990
- id: 1,
991
- },
992
- filter: {
993
- paths: {
994
- $overlaps: paths2,
995
- },
996
- destEntity: childEntity as string,
997
- deActions: {
998
- $overlaps: childActions,
999
- },
1000
- relationId: relationId || {
1001
- $exists: false,
1002
- },
1003
- }
1004
- }, { dontCollect: true })
1005
- }
1006
- ).flat() as ED['actionAuth']['Schema'][] | Promise<ED['actionAuth']['Schema']>[];
1007
- if (childLegalAuths[0] instanceof Promise) {
1008
- return Promise.all(childLegalAuths).then(
1009
- (clas) => child.map(
1010
- (c) => checkChildNode(clas, c)
1011
- )
1012
- )
1013
- }
1014
- return child.map(
1015
- (c) => checkChildNode(childLegalAuths as ED['actionAuth']['Schema'][], c)
1016
- );
1017
- }
1018
-
1019
- const childLegalAuths = realLegalPaths.map(
1020
- (ele) => {
1021
- const { paths, relationId } = ele;
1022
- const paths2 = paths.map(
1023
- (path) => path ? `${pathToParent}.${path}` : pathToParent
1024
- );
1025
- return context.select('actionAuth', {
1026
- data: {
1027
- id: 1,
1028
- },
1029
- filter: {
1030
- paths: {
1031
- $overlaps: paths2,
1032
- },
1033
- destEntity: childEntity as string,
1034
- deActions: {
1035
- $overlaps: child.action,
1036
- },
1037
- relationId: relationId || {
1038
- $exists: false,
1039
- },
1040
- }
1041
- }, { dontCollect: true })
1042
- }
1043
- ).flat() as ED['actionAuth']['Schema'][] | Promise<ED['actionAuth']['Schema']>[];
1044
-
1045
- if (childLegalAuths[0] instanceof Promise) {
1046
- return Promise.all(childLegalAuths).then(
1047
- (clas) => checkChildNode(clas.flat(), child)
1048
- );
1049
- }
1050
- return checkChildNode(childLegalAuths as ED['actionAuth']['Schema'][], child);
1051
- }
1052
- ).flat();
1053
-
1054
- if (childResult[0] instanceof Promise) {
1055
- return Promise.all(childResult).then(
1056
- (r) => !r.includes(false)
1057
- );
1058
- }
1059
- return !childResult.includes(false);
1060
- };
1061
-
1062
- if (RelationAuth.SPECIAL_ENTITIES.includes(node.entity as string)) {
1063
- // 特殊entity走特别的路径判断
1064
- const result = this.checkOperateSpecialEntities2(node.entity, node.action, node.filter, context);
1065
-
1066
- if (result instanceof Promise) {
1067
- return result.then(
1068
- (r) => {
1069
- if (r) {
1070
- return checkChildren();
1071
- }
1072
- return false;
1073
- }
1074
- );
1075
- }
1076
- if (result) {
1077
- if (node.entity === 'user') {
1078
- // 如果当前是对user对象操作,需要加上一个指向它自身的actionAuth,否则剩下的子对象会判定不过
1079
- // user的操作权限由应用自己决定,如果user的操作最终过不去,这里放过也没关系
1080
- assert(node === tree && realLegalPaths.length === 0); // user不可能是非根结点
1081
- realLegalPaths.push({
1082
- id: 'temp',
1083
- paths: [''],
1084
- $$createAt$$: 1,
1085
- $$updateAt$$: 1,
1086
- $$seq$$: 'temp',
1087
- destEntity: 'user',
1088
- deActions: [node.action],
1089
- });
1090
- }
1091
- return checkChildren();
1092
- }
1093
- if (process.env.NODE_ENV === 'development') {
1094
- console.warn('对象operate权限检查不通过', node);
1095
- }
1096
- return false;
1097
- }
1098
-
1099
- if (realLegalPaths.length === 0) {
1100
- if (node === tree) {
1101
- if (process.env.NODE_ENV === 'development') {
1102
- console.warn('对象operate权限检查不通过', node);
1103
- }
1104
- return false;
1105
- }
1106
- // 如果不是tree的根结点,相对路径上的actionAuth找不到,还可以尝试从自身的filter去重试其它路径
1107
- return this.checkOperationTree(node, context);
1108
- }
1109
-
1110
- return checkChildren();
1111
- };
1112
-
1113
- if (actionAuths instanceof Promise) {
1114
- return actionAuths.then(
1115
- (aars) => checkChildNodeInner(aars)
1116
- );
1117
- }
1118
- return checkChildNodeInner(actionAuths);
1119
- };
1120
-
1121
- return checkChildNode(actionAuths2, tree);
1122
- } */
1123
- RelationAuth.prototype.checkOperation = function (entity, operation, context) {
1124
- var action = operation.action, filter = operation.filter, data = operation.data;
1125
- if (action === 'create' && this.createFreeEntities.includes(entity)) {
1126
- return true;
1127
- }
1128
- else if (action === 'update' && this.updateFreeEntities.includes(entity)) {
993
+ }
994
+ checkOperation(entity, operation, context) {
995
+ const { action, filter, data } = operation;
996
+ if (this.updateFreeDict[entity] && this.updateFreeDict[entity].includes(action)) {
1129
997
  return true;
1130
998
  }
1131
- var userId = context.getCurrentUserId();
999
+ const userId = context.getCurrentUserId();
1132
1000
  if (!userId) {
1133
1001
  throw new types_1.OakUnloggedInException();
1134
1002
  }
@@ -1138,9 +1006,9 @@ var RelationAuth = /** @class */ (function () {
1138
1006
  }
1139
1007
  return false;
1140
1008
  }
1141
- var updateTree = this.destructOperation(entity, operation, userId);
1009
+ const updateTree = this.destructOperation(entity, operation, userId);
1142
1010
  return this.checkOperationTree2(updateTree, context);
1143
- };
1011
+ }
1144
1012
  /**
1145
1013
  * 检查一个operation是否能被通过权限测试
1146
1014
  * 一个cascadeOperation是一棵树形结构:
@@ -1153,25 +1021,25 @@ var RelationAuth = /** @class */ (function () {
1153
1021
  * @param actions
1154
1022
  * @returns
1155
1023
  */
1156
- RelationAuth.prototype.checkActions2 = function (entity, operation, context, actions) {
1157
- var action = operation.action;
1024
+ checkActions2(entity, operation, context, actions) {
1025
+ const { action } = operation;
1158
1026
  if (!action || action_1.readOnlyActions.includes(action)) {
1159
- var result = this.checkSelection(entity, operation, context);
1027
+ const result = this.checkSelection(entity, operation, context);
1160
1028
  if (result instanceof Promise) {
1161
- return result.then(function (r) {
1029
+ return result.then((r) => {
1162
1030
  if (!r) {
1163
- throw new types_1.OakUserUnpermittedException();
1031
+ throw new types_1.OakUserInvisibleException();
1164
1032
  }
1165
1033
  });
1166
1034
  }
1167
1035
  if (!result) {
1168
- throw new types_1.OakUserUnpermittedException();
1036
+ throw new types_1.OakUserInvisibleException();
1169
1037
  }
1170
1038
  }
1171
1039
  else {
1172
- var result = this.checkOperation(entity, operation, context);
1040
+ const result = this.checkOperation(entity, operation, context);
1173
1041
  if (result instanceof Promise) {
1174
- return result.then(function (r) {
1042
+ return result.then((r) => {
1175
1043
  if (!r) {
1176
1044
  throw new types_1.OakUserUnpermittedException();
1177
1045
  }
@@ -1181,10 +1049,8 @@ var RelationAuth = /** @class */ (function () {
1181
1049
  throw new types_1.OakUserUnpermittedException();
1182
1050
  }
1183
1051
  }
1184
- };
1185
- RelationAuth.SPECIAL_ENTITIES = env_1.SYSTEM_RESERVE_ENTITIES;
1186
- return RelationAuth;
1187
- }());
1052
+ }
1053
+ }
1188
1054
  exports.RelationAuth = RelationAuth;
1189
1055
  ;
1190
1056
  /**
@@ -1193,300 +1059,276 @@ exports.RelationAuth = RelationAuth;
1193
1059
  * @param context
1194
1060
  * todo paths改成复数以后这里还未充分测试过
1195
1061
  */
1196
- function getUserRelationsByActions(params, context) {
1197
- return tslib_1.__awaiter(this, void 0, void 0, function () {
1198
- var entity, filter, actions, overlap, actionAuthfilter, actionAuths, getUserRelations, getDirectUserEntities, urAuths2, directAuths2, _a, userRelations, userEntities;
1199
- var _this = this;
1200
- return tslib_1.__generator(this, function (_b) {
1201
- switch (_b.label) {
1202
- case 0:
1203
- entity = params.entity, filter = params.filter, actions = params.actions, overlap = params.overlap;
1204
- actionAuthfilter = {
1205
- destEntity: entity,
1206
- };
1207
- if (overlap) {
1208
- Object.assign(actionAuthfilter, {
1209
- deActions: {
1210
- $overlaps: actions,
1211
- },
1212
- });
1213
- }
1214
- else {
1215
- Object.assign(actionAuthfilter, {
1216
- deActions: {
1217
- $contains: actions,
1218
- },
1219
- });
1220
- }
1221
- return [4 /*yield*/, context.select('actionAuth', {
1062
+ async function getUserRelationsByActions(params, context) {
1063
+ const { entity, filter, actions, overlap } = params;
1064
+ const actionAuthfilter = {
1065
+ path: {
1066
+ destEntity: entity,
1067
+ },
1068
+ };
1069
+ if (overlap) {
1070
+ Object.assign(actionAuthfilter, {
1071
+ deActions: {
1072
+ $overlaps: actions,
1073
+ },
1074
+ });
1075
+ }
1076
+ else {
1077
+ Object.assign(actionAuthfilter, {
1078
+ deActions: {
1079
+ $contains: actions,
1080
+ },
1081
+ });
1082
+ }
1083
+ const actionAuths = await context.select('actionAuth', {
1084
+ data: {
1085
+ id: 1,
1086
+ path: {
1087
+ id: 1,
1088
+ value: 1,
1089
+ destEntity: 1,
1090
+ recursive: 1,
1091
+ },
1092
+ relationId: 1,
1093
+ relation: {
1094
+ id: 1,
1095
+ entity: 1,
1096
+ },
1097
+ },
1098
+ filter: actionAuthfilter,
1099
+ }, { dontCollect: true });
1100
+ const getUserRelations = async (urAuths) => {
1101
+ const makeRelationIterator = (path, relationIds, recursive) => {
1102
+ (0, assert_1.default)(!recursive, 'recursive的情况还没处理,等跑出来再说, by Xc');
1103
+ if (path === '') {
1104
+ return {
1105
+ projection: {
1106
+ id: 1,
1107
+ userRelation$entity: {
1108
+ $entity: 'userRelation',
1222
1109
  data: {
1223
1110
  id: 1,
1224
- paths: 1,
1225
1111
  relationId: 1,
1226
1112
  relation: {
1227
1113
  id: 1,
1228
- entity: 1,
1114
+ name: 1,
1229
1115
  },
1116
+ entity: 1,
1117
+ entityId: 1,
1118
+ userId: 1,
1230
1119
  },
1231
- filter: actionAuthfilter,
1232
- }, { dontCollect: true })];
1233
- case 1:
1234
- actionAuths = _b.sent();
1235
- getUserRelations = function (urAuths) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
1236
- var makeRelationIterator, urAuthDict2, userRelations;
1237
- var _this = this;
1238
- return tslib_1.__generator(this, function (_a) {
1239
- switch (_a.label) {
1240
- case 0:
1241
- makeRelationIterator = function (path, relationIds) {
1242
- var paths = path.split('.');
1243
- var makeIter = function (e, idx) {
1244
- var _a, _b, _c;
1245
- if (idx === paths.length) {
1246
- return {
1247
- projection: {
1248
- id: 1,
1249
- userRelation$entity: {
1250
- $entity: 'userRelation',
1251
- data: {
1252
- id: 1,
1253
- relationId: 1,
1254
- relation: {
1255
- id: 1,
1256
- name: 1,
1257
- },
1258
- entity: 1,
1259
- entityId: 1,
1260
- userId: 1,
1261
- },
1262
- filter: {
1263
- relationId: {
1264
- $in: relationIds,
1265
- },
1266
- },
1267
- }
1268
- },
1269
- getData: function (d) {
1270
- return d.userRelation$entity;
1271
- },
1272
- };
1273
- }
1274
- var attr = paths[idx];
1275
- var rel = (0, relation_1.judgeRelation)(context.getSchema(), e, attr);
1276
- if (rel === 2) {
1277
- var _d = makeIter(attr, idx + 1), projection = _d.projection, getData_1 = _d.getData;
1278
- return {
1279
- projection: (_a = {
1280
- id: 1
1281
- },
1282
- _a[attr] = projection,
1283
- _a),
1284
- getData: function (d) { return d[attr] && getData_1(d[attr]); },
1285
- };
1286
- }
1287
- else if (typeof rel === 'string') {
1288
- var _e = makeIter(rel, idx + 1), projection = _e.projection, getData_2 = _e.getData;
1289
- return {
1290
- projection: (_b = {
1291
- id: 1
1292
- },
1293
- _b[attr] = projection,
1294
- _b),
1295
- getData: function (d) { return d[attr] && getData_2(d[attr]); },
1296
- };
1297
- }
1298
- else {
1299
- (0, assert_1.default)(rel instanceof Array);
1300
- var _f = tslib_1.__read(rel, 2), e2 = _f[0], fk = _f[1];
1301
- var _g = makeIter(e2, idx + 1), projection = _g.projection, getData_3 = _g.getData;
1302
- return {
1303
- projection: (_c = {
1304
- id: 1
1305
- },
1306
- _c[attr] = {
1307
- $entity: e2,
1308
- data: projection,
1309
- },
1310
- _c),
1311
- getData: function (d) { return d[attr] && d[attr].map(function (ele) { return getData_3(ele); }); },
1312
- };
1313
- }
1314
- };
1315
- return makeIter(entity, 0);
1316
- };
1317
- urAuthDict2 = {};
1318
- urAuths.forEach(function (auth) {
1319
- var paths = auth.paths, relationId = auth.relationId;
1320
- paths.forEach(function (path) {
1321
- if (!urAuthDict2[path]) {
1322
- urAuthDict2[path] = [relationId];
1323
- }
1324
- else if (!urAuthDict2[path].includes(relationId)) {
1325
- urAuthDict2[path].push(relationId);
1326
- }
1327
- });
1328
- });
1329
- return [4 /*yield*/, Promise.all(Object.keys(urAuthDict2).map(function (path) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
1330
- var relationIds, _a, projection, getData, rows, urs;
1331
- return tslib_1.__generator(this, function (_b) {
1332
- switch (_b.label) {
1333
- case 0:
1334
- relationIds = urAuthDict2[path];
1335
- _a = makeRelationIterator(path, relationIds), projection = _a.projection, getData = _a.getData;
1336
- return [4 /*yield*/, context.select(entity, {
1337
- data: projection,
1338
- filter: filter,
1339
- }, { dontCollect: true })];
1340
- case 1:
1341
- rows = _b.sent();
1342
- urs = rows.map(function (ele) { return getData(ele); }).flat().filter(function (ele) { return !!ele; });
1343
- return [2 /*return*/, urs];
1344
- }
1345
- });
1346
- }); }))];
1347
- case 1:
1348
- userRelations = _a.sent();
1349
- return [2 /*return*/, userRelations.flat()];
1350
- }
1351
- });
1352
- }); };
1353
- getDirectUserEntities = function (directAuths) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
1354
- var makeRelationIterator, userEntities;
1355
- var _this = this;
1356
- return tslib_1.__generator(this, function (_a) {
1357
- switch (_a.label) {
1358
- case 0:
1359
- makeRelationIterator = function (path) {
1360
- var paths = path.split('.');
1361
- var makeIter = function (e, idx) {
1362
- var _a, _b, _c, _d;
1363
- var attr = paths[idx];
1364
- var rel = (0, relation_1.judgeRelation)(context.getSchema(), e, attr);
1365
- if (idx === paths.length - 1) {
1366
- if (rel === 2) {
1367
- (0, assert_1.default)(attr === 'user');
1368
- return {
1369
- projection: {
1370
- id: 1,
1371
- entity: 1,
1372
- entityId: 1,
1373
- },
1374
- getData: function (d) {
1375
- if (d) {
1376
- return {
1377
- entity: e,
1378
- entityId: d.id,
1379
- userId: d.entityId,
1380
- };
1381
- }
1382
- },
1383
- };
1384
- }
1385
- else {
1386
- (0, assert_1.default)(rel === 'user');
1387
- return {
1388
- projection: (_a = {
1389
- id: 1
1390
- },
1391
- _a["".concat(attr, "Id")] = 1,
1392
- _a),
1393
- getData: function (d) {
1394
- if (d) {
1395
- return {
1396
- entity: e,
1397
- entityId: d.id,
1398
- userId: d["".concat(attr, "Id")]
1399
- };
1400
- }
1401
- },
1402
- };
1403
- }
1404
- }
1405
- if (rel === 2) {
1406
- var _e = makeIter(attr, idx + 1), projection = _e.projection, getData_4 = _e.getData;
1407
- return {
1408
- projection: (_b = {
1409
- id: 1
1410
- },
1411
- _b[attr] = projection,
1412
- _b),
1413
- getData: function (d) { return d[attr] && getData_4(d[attr]); },
1414
- };
1415
- }
1416
- else if (typeof rel === 'string') {
1417
- var _f = makeIter(rel, idx + 1), projection = _f.projection, getData_5 = _f.getData;
1418
- return {
1419
- projection: (_c = {
1420
- id: 1
1421
- },
1422
- _c[attr] = projection,
1423
- _c),
1424
- getData: function (d) { return d[attr] && getData_5(d[attr]); },
1425
- };
1426
- }
1427
- else {
1428
- (0, assert_1.default)(rel instanceof Array);
1429
- var _g = tslib_1.__read(rel, 2), e2 = _g[0], fk = _g[1];
1430
- var _h = makeIter(e2, idx + 1), projection = _h.projection, getData_6 = _h.getData;
1431
- return {
1432
- projection: (_d = {
1433
- id: 1
1434
- },
1435
- _d[attr] = {
1436
- $entity: e2,
1437
- data: projection,
1438
- },
1439
- _d),
1440
- getData: function (d) { return d[attr] && d[attr].map(function (ele) { return getData_6(ele); }); },
1441
- };
1442
- }
1443
- };
1444
- return makeIter(entity, 0);
1445
- };
1446
- return [4 /*yield*/, Promise.all(directAuths.map(function (_a) {
1447
- var paths = _a.paths;
1448
- return tslib_1.__awaiter(_this, void 0, void 0, function () {
1449
- var _this = this;
1450
- return tslib_1.__generator(this, function (_b) {
1451
- return [2 /*return*/, paths.map(function (path) { return tslib_1.__awaiter(_this, void 0, void 0, function () {
1452
- var _a, getData, projection, rows, userEntities;
1453
- return tslib_1.__generator(this, function (_b) {
1454
- switch (_b.label) {
1455
- case 0:
1456
- _a = makeRelationIterator(path), getData = _a.getData, projection = _a.projection;
1457
- return [4 /*yield*/, context.select(entity, {
1458
- data: projection,
1459
- filter: filter,
1460
- }, { dontCollect: true })];
1461
- case 1:
1462
- rows = _b.sent();
1463
- userEntities = rows.map(function (ele) { return getData(ele); }).flat().filter(function (ele) { return !!ele; });
1464
- return [2 /*return*/, userEntities];
1465
- }
1466
- });
1467
- }); })];
1468
- });
1469
- });
1470
- }))];
1471
- case 1:
1472
- userEntities = _a.sent();
1473
- return [2 /*return*/, userEntities.flat()];
1120
+ filter: {
1121
+ relationId: {
1122
+ $in: relationIds,
1123
+ },
1124
+ },
1125
+ },
1126
+ },
1127
+ getData: (d) => {
1128
+ return d.userRelation$entity;
1129
+ },
1130
+ };
1131
+ }
1132
+ const paths = path.split('.');
1133
+ const makeIter = (e, idx) => {
1134
+ if (idx === paths.length) {
1135
+ return {
1136
+ projection: {
1137
+ id: 1,
1138
+ userRelation$entity: {
1139
+ $entity: 'userRelation',
1140
+ data: {
1141
+ id: 1,
1142
+ relationId: 1,
1143
+ relation: {
1144
+ id: 1,
1145
+ name: 1,
1146
+ },
1147
+ entity: 1,
1148
+ entityId: 1,
1149
+ userId: 1,
1150
+ },
1151
+ filter: {
1152
+ relationId: {
1153
+ $in: relationIds,
1154
+ },
1155
+ },
1474
1156
  }
1475
- });
1476
- }); };
1477
- urAuths2 = actionAuths.filter(function (ele) { return !!ele.relationId; } // 有relation说明通过userRelation关联
1478
- );
1479
- directAuths2 = actionAuths.filter(function (ele) { return !ele.relationId; } // 没relation说明通过user关联
1480
- );
1481
- return [4 /*yield*/, Promise.all([getUserRelations(urAuths2), getDirectUserEntities(directAuths2)])];
1482
- case 2:
1483
- _a = tslib_1.__read.apply(void 0, [_b.sent(), 2]), userRelations = _a[0], userEntities = _a[1];
1484
- return [2 /*return*/, {
1485
- userRelations: userRelations,
1486
- userEntities: userEntities,
1487
- }];
1157
+ },
1158
+ getData: (d) => {
1159
+ return d.userRelation$entity;
1160
+ },
1161
+ };
1162
+ }
1163
+ const attr = paths[idx];
1164
+ const rel = (0, relation_1.judgeRelation)(context.getSchema(), e, attr);
1165
+ if (rel === 2) {
1166
+ const { projection, getData } = makeIter(attr, idx + 1);
1167
+ return {
1168
+ projection: {
1169
+ id: 1,
1170
+ [attr]: projection,
1171
+ },
1172
+ getData: (d) => d[attr] && getData(d[attr]),
1173
+ };
1174
+ }
1175
+ else if (typeof rel === 'string') {
1176
+ const { projection, getData } = makeIter(rel, idx + 1);
1177
+ return {
1178
+ projection: {
1179
+ id: 1,
1180
+ [attr]: projection,
1181
+ },
1182
+ getData: (d) => d[attr] && getData(d[attr]),
1183
+ };
1184
+ }
1185
+ else {
1186
+ (0, assert_1.default)(rel instanceof Array);
1187
+ const [e2, fk] = rel;
1188
+ const { projection, getData } = makeIter(e2, idx + 1);
1189
+ return {
1190
+ projection: {
1191
+ id: 1,
1192
+ [attr]: {
1193
+ $entity: e2,
1194
+ data: projection,
1195
+ },
1196
+ },
1197
+ getData: (d) => d[attr] && d[attr].map((ele) => getData(ele)),
1198
+ };
1199
+ }
1200
+ };
1201
+ return makeIter(entity, 0);
1202
+ };
1203
+ // 相同的path可以groupBy掉
1204
+ const urAuthDict2 = {};
1205
+ urAuths.forEach((auth) => {
1206
+ const { path, relationId } = auth;
1207
+ const { value, recursive } = path;
1208
+ if (!urAuthDict2[value]) {
1209
+ urAuthDict2[value] = [[relationId], recursive];
1210
+ }
1211
+ else if (!urAuthDict2[value][0].includes(relationId)) {
1212
+ (0, assert_1.default)(urAuthDict2[value][1] === recursive);
1213
+ urAuthDict2[value][0].push(relationId);
1488
1214
  }
1489
1215
  });
1490
- });
1216
+ const userRelations = await Promise.all(Object.keys(urAuthDict2).map(async (path) => {
1217
+ const [relationIds, recursive] = urAuthDict2[path];
1218
+ const { projection, getData } = makeRelationIterator(path, relationIds, recursive);
1219
+ const rows = await context.select(entity, {
1220
+ data: projection,
1221
+ filter,
1222
+ }, { dontCollect: true });
1223
+ const urs = rows.map(ele => getData(ele)).flat().filter(ele => !!ele);
1224
+ return urs;
1225
+ }));
1226
+ return userRelations.flat();
1227
+ };
1228
+ const getDirectUserEntities = async (directAuths) => {
1229
+ const makeRelationIterator = (path) => {
1230
+ const paths = path.split('.');
1231
+ const makeIter = (e, idx) => {
1232
+ const attr = paths[idx];
1233
+ const rel = (0, relation_1.judgeRelation)(context.getSchema(), e, attr);
1234
+ if (idx === paths.length - 1) {
1235
+ if (rel === 2) {
1236
+ (0, assert_1.default)(attr === 'user');
1237
+ return {
1238
+ projection: {
1239
+ id: 1,
1240
+ entity: 1,
1241
+ entityId: 1,
1242
+ },
1243
+ getData: (d) => {
1244
+ if (d) {
1245
+ return {
1246
+ entity: e,
1247
+ entityId: d.id,
1248
+ userId: d.entityId,
1249
+ };
1250
+ }
1251
+ },
1252
+ };
1253
+ }
1254
+ else {
1255
+ (0, assert_1.default)(rel === 'user');
1256
+ return {
1257
+ projection: {
1258
+ id: 1,
1259
+ [`${attr}Id`]: 1,
1260
+ },
1261
+ getData: (d) => {
1262
+ if (d) {
1263
+ return {
1264
+ entity: e,
1265
+ entityId: d.id,
1266
+ userId: d[`${attr}Id`]
1267
+ };
1268
+ }
1269
+ },
1270
+ };
1271
+ }
1272
+ }
1273
+ if (rel === 2) {
1274
+ const { projection, getData } = makeIter(attr, idx + 1);
1275
+ return {
1276
+ projection: {
1277
+ id: 1,
1278
+ [attr]: projection,
1279
+ },
1280
+ getData: (d) => d[attr] && getData(d[attr]),
1281
+ };
1282
+ }
1283
+ else if (typeof rel === 'string') {
1284
+ const { projection, getData } = makeIter(rel, idx + 1);
1285
+ return {
1286
+ projection: {
1287
+ id: 1,
1288
+ [attr]: projection,
1289
+ },
1290
+ getData: (d) => d[attr] && getData(d[attr]),
1291
+ };
1292
+ }
1293
+ else {
1294
+ (0, assert_1.default)(rel instanceof Array);
1295
+ const [e2, fk] = rel;
1296
+ const { projection, getData } = makeIter(e2, idx + 1);
1297
+ return {
1298
+ projection: {
1299
+ id: 1,
1300
+ [attr]: {
1301
+ $entity: e2,
1302
+ data: projection,
1303
+ },
1304
+ },
1305
+ getData: (d) => d[attr] && d[attr].map((ele) => getData(ele)),
1306
+ };
1307
+ }
1308
+ };
1309
+ return makeIter(entity, 0);
1310
+ };
1311
+ const userEntities = await Promise.all(directAuths.map(async ({ path }) => {
1312
+ const { value, recursive } = path;
1313
+ (0, assert_1.default)(!recursive);
1314
+ const { getData, projection } = makeRelationIterator(value);
1315
+ const rows = await context.select(entity, {
1316
+ data: projection,
1317
+ filter,
1318
+ }, { dontCollect: true });
1319
+ const userEntities = rows.map(ele => getData(ele)).flat().filter(ele => !!ele);
1320
+ return userEntities;
1321
+ }));
1322
+ return userEntities.flat();
1323
+ };
1324
+ const urAuths2 = actionAuths.filter(ele => !!ele.relationId // 有relation说明通过userRelation关联
1325
+ );
1326
+ const directAuths2 = actionAuths.filter(ele => !ele.relationId // 没relation说明通过user关联
1327
+ );
1328
+ const [userRelations, userEntities] = await Promise.all([getUserRelations(urAuths2), getDirectUserEntities(directAuths2)]);
1329
+ return {
1330
+ userRelations,
1331
+ userEntities,
1332
+ };
1491
1333
  }
1492
1334
  exports.getUserRelationsByActions = getUserRelationsByActions;