@rytass/bpm-core-nestjs-module 0.17.8 → 0.18.0

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 (30) hide show
  1. package/CHANGELOG.md +73 -0
  2. package/README.md +40 -0
  3. package/package.json +2 -2
  4. package/src/lib/delegation/delegation.service.d.ts +41 -1
  5. package/src/lib/delegation/delegation.service.js +147 -23
  6. package/src/lib/delegation/delegation.service.js.map +1 -1
  7. package/src/lib/form/form-schema.validator.js +66 -6
  8. package/src/lib/form/form-schema.validator.js.map +1 -1
  9. package/src/lib/identity/identity.service.d.ts +6 -0
  10. package/src/lib/identity/identity.service.js +12 -0
  11. package/src/lib/identity/identity.service.js.map +1 -1
  12. package/src/lib/identity/member-base.adapter.d.ts +8 -0
  13. package/src/lib/identity/member-base.adapter.js +8 -2
  14. package/src/lib/identity/member-base.adapter.js.map +1 -1
  15. package/src/lib/identity/member-resolver.interface.d.ts +9 -0
  16. package/src/lib/workflow-engine/dto/resubmit-approval-instance.input.d.ts +7 -0
  17. package/src/lib/workflow-engine/dto/resubmit-approval-instance.input.js +7 -0
  18. package/src/lib/workflow-engine/dto/resubmit-approval-instance.input.js.map +1 -1
  19. package/src/lib/workflow-engine/task-reassignment.object.d.ts +11 -0
  20. package/src/lib/workflow-engine/task-reassignment.object.js +27 -1
  21. package/src/lib/workflow-engine/task-reassignment.object.js.map +1 -1
  22. package/src/lib/workflow-engine/text-field-pattern-test.d.ts +23 -0
  23. package/src/lib/workflow-engine/text-field-pattern-test.js +75 -0
  24. package/src/lib/workflow-engine/text-field-pattern-test.js.map +1 -0
  25. package/src/lib/workflow-engine/workflow-engine.queries.d.ts +12 -2
  26. package/src/lib/workflow-engine/workflow-engine.queries.js +45 -2
  27. package/src/lib/workflow-engine/workflow-engine.queries.js.map +1 -1
  28. package/src/lib/workflow-engine/workflow-engine.service.d.ts +32 -0
  29. package/src/lib/workflow-engine/workflow-engine.service.js +253 -29
  30. package/src/lib/workflow-engine/workflow-engine.service.js.map +1 -1
@@ -2,8 +2,11 @@
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
3
  exports.WorkflowEngineQueries = void 0;
4
4
  const tslib_1 = require("tslib");
5
+ const core_1 = require("@nestjs/core");
6
+ const unknown_element_exception_js_1 = require("@nestjs/core/errors/exceptions/unknown-element.exception.js");
5
7
  const graphql_1 = require("@nestjs/graphql");
6
8
  const bpm_auth_1 = require("../bpm-auth");
9
+ const identity_service_1 = require("../identity/identity.service");
7
10
  const task_reassignment_object_1 = require("./task-reassignment.object");
8
11
  const activity_log_entity_1 = require("./activity-log.entity");
9
12
  const adhoc_directive_entity_1 = require("./adhoc-directive.entity");
@@ -18,8 +21,9 @@ const workflow_engine_enums_1 = require("./workflow-engine.enums");
18
21
  const workflow_engine_service_1 = require("./workflow-engine.service");
19
22
  const workflow_token_entity_1 = require("./workflow-token.entity");
20
23
  let WorkflowEngineQueries = class WorkflowEngineQueries {
21
- constructor(workflowEngineService) {
24
+ constructor(workflowEngineService, moduleRef) {
22
25
  this.workflowEngineService = workflowEngineService;
26
+ this.moduleRef = moduleRef;
23
27
  }
24
28
  async approvalInstances(view, searchText, state, templateId, page, pageSize, currentAuthContext) {
25
29
  return this.workflowEngineService.listApprovalInstances(currentAuthContext, {
@@ -73,6 +77,13 @@ let WorkflowEngineQueries = class WorkflowEngineQueries {
73
77
  async memberOpenTasks(memberId) {
74
78
  return this.workflowEngineService.listMemberOpenTasks(memberId);
75
79
  }
80
+ async inactiveMembersWithOpenTasks() {
81
+ const identityService = this.readIdentityService();
82
+ if (!identityService) {
83
+ return [];
84
+ }
85
+ return this.workflowEngineService.listInactiveMembersWithOpenTasks((memberIds) => identityService.resolveInactiveMembers(memberIds));
86
+ }
76
87
  async launchableApprovalTemplates(currentMemberId) {
77
88
  return this.workflowEngineService.listLaunchableApprovalTemplates(currentMemberId);
78
89
  }
@@ -88,6 +99,25 @@ let WorkflowEngineQueries = class WorkflowEngineQueries {
88
99
  async activityLogs(instanceId, currentAuthContext) {
89
100
  return this.workflowEngineService.listActivityLogs(instanceId, currentAuthContext);
90
101
  }
102
+ /**
103
+ * Looked up at call time rather than injected: `IdentityModule` is a dynamic
104
+ * module the root configures with the host's options, so this module cannot
105
+ * import it. A host that wires the engine without it gets an empty list, the
106
+ * same answer as a member resolver without `resolveInactive`.
107
+ */
108
+ readIdentityService() {
109
+ try {
110
+ return this.moduleRef.get(identity_service_1.IdentityService, { strict: false });
111
+ }
112
+ catch (error) {
113
+ // Only "not registered" means no identity module; anything else is a
114
+ // real failure and must not pass for an empty list.
115
+ if (error instanceof unknown_element_exception_js_1.UnknownElementException) {
116
+ return null;
117
+ }
118
+ throw error;
119
+ }
120
+ }
91
121
  };
92
122
  exports.WorkflowEngineQueries = WorkflowEngineQueries;
93
123
  tslib_1.__decorate([
@@ -205,6 +235,18 @@ tslib_1.__decorate([
205
235
  tslib_1.__metadata("design:paramtypes", [String]),
206
236
  tslib_1.__metadata("design:returntype", Promise)
207
237
  ], WorkflowEngineQueries.prototype, "memberOpenTasks", null);
238
+ tslib_1.__decorate([
239
+ (0, graphql_1.Query)(() => [task_reassignment_object_1.InactiveMemberWithOpenTasksObject], {
240
+ description: 'Administrator: members the host reports as deactivated who still hold ' +
241
+ 'open tasks, with the count memberOpenTasks would list. Always empty ' +
242
+ 'when the host member resolver does not implement resolveInactive, or ' +
243
+ 'when the engine is wired without the identity module.',
244
+ }),
245
+ (0, bpm_auth_1.BPMAdminOnly)(),
246
+ tslib_1.__metadata("design:type", Function),
247
+ tslib_1.__metadata("design:paramtypes", []),
248
+ tslib_1.__metadata("design:returntype", Promise)
249
+ ], WorkflowEngineQueries.prototype, "inactiveMembersWithOpenTasks", null);
208
250
  tslib_1.__decorate([
209
251
  (0, graphql_1.Query)(() => [approval_template_entity_1.ApprovalTemplateEntity]),
210
252
  tslib_1.__param(0, (0, bpm_auth_1.BPMCurrentMemberId)()),
@@ -247,6 +289,7 @@ tslib_1.__decorate([
247
289
  exports.WorkflowEngineQueries = WorkflowEngineQueries = tslib_1.__decorate([
248
290
  (0, graphql_1.Resolver)(),
249
291
  (0, bpm_auth_1.BPMAuthenticated)(),
250
- tslib_1.__metadata("design:paramtypes", [workflow_engine_service_1.WorkflowEngineService])
292
+ tslib_1.__metadata("design:paramtypes", [workflow_engine_service_1.WorkflowEngineService,
293
+ core_1.ModuleRef])
251
294
  ], WorkflowEngineQueries);
252
295
  //# sourceMappingURL=workflow-engine.queries.js.map
@@ -1 +1 @@
1
- {"version":3,"file":"workflow-engine.queries.js","sourceRoot":"","sources":["../../../../../../libs/bpm-core/src/lib/workflow-engine/workflow-engine.queries.ts"],"names":[],"mappings":"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"}
1
+ {"version":3,"file":"workflow-engine.queries.js","sourceRoot":"","sources":["../../../../../../libs/bpm-core/src/lib/workflow-engine/workflow-engine.queries.ts"],"names":[],"mappings":";;;;AAAA,uCAAyC;AACzC,8GAAsG;AAEtG,6CAAiE;AACjE,0CAMqB;AACrB,mEAA+D;AAC/D,yEAGoC;AAKpC,+DAA0D;AAC1D,qEAAgE;AAChE,yEAAoE;AACpE,6FAAsF;AACtF,mFAA8E;AAC9E,mEAA8D;AAC9D,iEAA4D;AAC5D,+CAA2C;AAC3C,2FAAqF;AACrF,mEAGiC;AACjC,uEAAkE;AAClE,mEAA8D;AAIvD,IAAM,qBAAqB,GAA3B,MAAM,qBAAqB;IAChC,YACmB,qBAA4C,EAC5C,SAAoB;QADpB,0BAAqB,GAArB,qBAAqB,CAAuB;QAC5C,cAAS,GAAT,SAAS,CAAW;IACpC,CAAC;IAGE,AAAN,KAAK,CAAC,iBAAiB,CAKrB,IAAyC,EAEzC,UAAyB,EAKzB,KAAkD,EAElD,UAAyB,EAEzB,IAAmB,EAEnB,QAAuB,EACE,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,qBAAqB,CACrD,kBAAkB,EAClB;YACE,IAAI,EAAE,IAAI,IAAI,SAAS;YACvB,QAAQ,EAAE,QAAQ,IAAI,SAAS;YAC/B,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,KAAK,EAAE,KAAK,IAAI,SAAS;YACzB,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,IAAI,EAAE,IAAI,IAAI,SAAS;SACxB,CACF,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,qBAAqB,CAKzB,IAAyC,EAEzC,UAAyB,EAKzB,KAAkD,EAElD,UAAyB,EACA,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,sBAAsB,CACtD,kBAAkB,EAClB;YACE,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,KAAK,EAAE,KAAK,IAAI,SAAS;YACzB,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,IAAI,EAAE,IAAI,IAAI,SAAS;SACxB,CACF,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,wBAAwB,CAK5B,IAAyC,EAEzC,UAAyB,EAKzB,KAAkD,EAElD,UAAyB,EAEzB,IAAmB,EAEnB,QAAuB,EACE,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,4BAA4B,CAC5D,kBAAkB,EAClB;YACE,IAAI,EAAE,IAAI,IAAI,SAAS;YACvB,QAAQ,EAAE,QAAQ,IAAI,SAAS;YAC/B,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,KAAK,EAAE,KAAK,IAAI,SAAS;YACzB,UAAU,EAAE,UAAU,IAAI,SAAS;YACnC,IAAI,EAAE,IAAI,IAAI,SAAS;SACxB,CACF,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,wBAAwB,CACwB,IAAiB,EACnB,EAAe,EACxC,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,4BAA4B,CAC5D,kBAAkB,EAClB;YACE,IAAI,EAAE,IAAI,IAAI,SAAS;YACvB,EAAE,EAAE,EAAE,IAAI,SAAS;SACpB,CACF,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,gBAAgB,CACgB,EAAU,EACrB,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,mBAAmB,CACnD,EAAE,EACF,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,cAAc,CAC0B,UAAkB,EACrC,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,kBAAkB,CAClD,UAAU,EACV,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,KAAK,CACmC,UAAkB,EACrC,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,SAAS,CAAC,UAAU,EAAE,kBAAkB,CAAC,CAAC;IAC9E,CAAC;IAGK,AAAN,KAAK,CAAC,UAAU,CACoC,gBAAwB,EACpD,eAAuB;QAE7C,OAAO,IAAI,CAAC,qBAAqB,CAAC,cAAc,CAAC,eAAe,CAAC,CAAC;IACpE,CAAC;IAGK,AAAN,KAAK,CAAC,oBAAoB,CAC0B,gBAAwB,EACpD,eAAuB;QAE7C,OAAO,IAAI,CAAC,qBAAqB,CAAC,wBAAwB,CAAC,eAAe,CAAC,CAAC;IAC9E,CAAC;IAQK,AAAN,KAAK,CAAC,eAAe,CACmB,QAAgB;QAEtD,OAAO,IAAI,CAAC,qBAAqB,CAAC,mBAAmB,CAAC,QAAQ,CAAC,CAAC;IAClE,CAAC;IAUK,AAAN,KAAK,CAAC,4BAA4B;QAGhC,MAAM,eAAe,GAAG,IAAI,CAAC,mBAAmB,EAAE,CAAC;QAEnD,IAAI,CAAC,eAAe,EAAE,CAAC;YACrB,OAAO,EAAE,CAAC;QACZ,CAAC;QAED,OAAO,IAAI,CAAC,qBAAqB,CAAC,gCAAgC,CAChE,CAAC,SAAS,EAAsC,EAAE,CAChD,eAAe,CAAC,sBAAsB,CAAC,SAAS,CAAC,CACpD,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,2BAA2B,CACT,eAAuB;QAE7C,OAAO,IAAI,CAAC,qBAAqB,CAAC,+BAA+B,CAC/D,eAAe,CAChB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,aAAa,CACuB,MAAc,EAC7B,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,iBAAiB,CACjD,MAAM,EACN,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,cAAc,CACsB,MAAc,EAC7B,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,kBAAkB,CAClD,MAAM,EACN,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,eAAe,CACyB,UAAkB,EACrC,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,mBAAmB,CACnD,UAAU,EACV,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAGK,AAAN,KAAK,CAAC,YAAY,CAC4B,UAAkB,EACrC,kBAAkC;QAE3D,OAAO,IAAI,CAAC,qBAAqB,CAAC,gBAAgB,CAChD,UAAU,EACV,kBAAkB,CACnB,CAAC;IACJ,CAAC;IAED;;;;;OAKG;IACK,mBAAmB;QACzB,IAAI,CAAC;YACH,OAAO,IAAI,CAAC,SAAS,CAAC,GAAG,CAAC,kCAAe,EAAE,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,CAAC;QAChE,CAAC;QAAC,OAAO,KAAK,EAAE,CAAC;YACf,qEAAqE;YACrE,oDAAoD;YACpD,IAAI,KAAK,YAAY,sDAAuB,EAAE,CAAC;gBAC7C,OAAO,IAAI,CAAC;YACd,CAAC;YAED,MAAM,KAAK,CAAC;QACd,CAAC;IACH,CAAC;CACF,CAAA;AAjRY,sDAAqB;AAO1B;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,iDAAsB,CAAC,CAAC;IAEnC,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE;QACZ,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,oDAA4B;KACzC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,cAAI,EAAC,OAAO,EAAE;QACb,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC,iDAAyB,CAAC;KACxC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,aAAG,EAAE,CAAC,CAAA;IAEjD,mBAAA,IAAA,cAAI,EAAC,UAAU,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,aAAG,EAAE,CAAC,CAAA;IAErD,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;8DAazB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,aAAG,CAAC;IAEd,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE;QACZ,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,oDAA4B;KACzC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,cAAI,EAAC,OAAO,EAAE;QACb,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC,iDAAyB,CAAC;KACxC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;kEAWzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,mEAA8B,CAAC;IAEzC,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE;QACZ,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,oDAA4B;KACzC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,cAAI,EAAC,OAAO,EAAE;QACb,QAAQ,EAAE,IAAI;QACd,IAAI,EAAE,GAAG,EAAE,CAAC,CAAC,iDAAyB,CAAC;KACxC,CAAC,CAAA;IAED,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAE1D,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,aAAG,EAAE,CAAC,CAAA;IAEjD,mBAAA,IAAA,cAAI,EAAC,UAAU,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,aAAG,EAAE,CAAC,CAAA;IAErD,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;qEAazB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,kEAA8B,CAAC;IAEzC,mBAAA,IAAA,cAAI,EAAC,MAAM,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAA;IAClD,mBAAA,IAAA,cAAI,EAAC,IAAI,EAAE,EAAE,QAAQ,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,IAAI,EAAE,CAAC,CAAA;IAChD,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;qEASzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,iDAAsB,CAAC;IAEjC,mBAAA,IAAA,cAAI,EAAC,IAAI,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAClC,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;6DAMzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,2CAAmB,CAAC,CAAC;IAEhC,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAC1C,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;2DAMzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,wBAAU,CAAC,CAAC;IAEvB,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAC1C,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;kDAGzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,wBAAU,CAAC,CAAC;IAEvB,mBAAA,IAAA,cAAI,EAAC,kBAAkB,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAChD,mBAAA,IAAA,6BAAkB,GAAE,CAAA;;;;uDAGtB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,wBAAU,CAAC,CAAC;IAEvB,mBAAA,IAAA,cAAI,EAAC,kBAAkB,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAChD,mBAAA,IAAA,6BAAkB,GAAE,CAAA;;;;iEAGtB;AAQK;IANL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,+CAAoB,CAAC,EAAE;QACnC,WAAW,EACT,wEAAwE;YACxE,0DAA0D;KAC7D,CAAC;IACD,IAAA,uBAAY,GAAE;IAEZ,mBAAA,IAAA,cAAI,EAAC,UAAU,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,YAAE,EAAE,CAAC,CAAA;;;;4DAGtC;AAUK;IARL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,4DAAiC,CAAC,EAAE;QAChD,WAAW,EACT,wEAAwE;YACxE,sEAAsE;YACtE,uEAAuE;YACvE,uDAAuD;KAC1D,CAAC;IACD,IAAA,uBAAY,GAAE;;;;yEAcd;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,iDAAsB,CAAC,CAAC;IAEnC,mBAAA,IAAA,6BAAkB,GAAE,CAAA;;;;wEAKtB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,yCAAkB,CAAC,CAAC;IAE/B,mBAAA,IAAA,cAAI,EAAC,QAAQ,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IACtC,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;0DAMzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,2CAAmB,CAAC,CAAC;IAEhC,mBAAA,IAAA,cAAI,EAAC,QAAQ,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IACtC,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;2DAMzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,6CAAoB,CAAC,CAAC;IAEjC,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAC1C,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;4DAMzB;AAGK;IADL,IAAA,eAAK,EAAC,GAAG,EAAE,CAAC,CAAC,uCAAiB,CAAC,CAAC;IAE9B,mBAAA,IAAA,cAAI,EAAC,YAAY,EAAE,EAAE,IAAI,EAAE,GAAG,EAAE,CAAC,MAAM,EAAE,CAAC,CAAA;IAC1C,mBAAA,IAAA,gCAAqB,GAAE,CAAA;;;;yDAMzB;gCA5PU,qBAAqB;IAFjC,IAAA,kBAAQ,GAAE;IACV,IAAA,2BAAgB,GAAE;6CAGyB,+CAAqB;QACjC,gBAAS;GAH5B,qBAAqB,CAiRjC"}
@@ -1,3 +1,4 @@
1
+ import { MemberMetadata } from '@rytass/bpm-core-shared';
1
2
  import { WorkflowWebhookDeliveryService } from '../workflow-webhook/workflow-webhook-delivery.service';
2
3
  import { Repository } from 'typeorm';
3
4
  import { AttachmentService } from '../attachment/attachment.service';
@@ -105,6 +106,14 @@ export interface MemberOpenTaskRecord {
105
106
  readonly templateId: string;
106
107
  readonly templateName: string | null;
107
108
  }
109
+ /** A deactivated member who still holds open tasks, for the reassignment screen. */
110
+ export interface InactiveMemberOpenTasksRecord {
111
+ readonly email: string;
112
+ readonly memberId: string;
113
+ readonly name: string;
114
+ /** Same count as {@link WorkflowEngineService.listMemberOpenTasks} returns rows. */
115
+ readonly openTaskCount: number;
116
+ }
108
117
  /**
109
118
  * Engine-internal decision knobs that are deliberately kept out of
110
119
  * {@link DecideTaskInput} so they never reach the GraphQL schema.
@@ -392,6 +401,29 @@ export declare class WorkflowEngineService {
392
401
  * RUNNING instances.
393
402
  */
394
403
  listMemberOpenTasks(memberId: string): Promise<readonly MemberOpenTaskRecord[]>;
404
+ /**
405
+ * Deactivated members who still hold open tasks, so an administrator can find
406
+ * them: a deactivated member no longer shows up in the member search.
407
+ *
408
+ * BPM cannot tell a deactivated member from an id it never knew, so the host
409
+ * names them: `resolveInactiveMembers` gets every member id that holds an open
410
+ * seat and returns the ones it knows but has deactivated. The count per member
411
+ * is the {@link listMemberOpenTasks} count, and members left with none are
412
+ * dropped.
413
+ */
414
+ listInactiveMembersWithOpenTasks(resolveInactiveMembers: (memberIds: readonly string[]) => Promise<readonly MemberMetadata[]>): Promise<readonly InactiveMemberOpenTasksRecord[]>;
415
+ /**
416
+ * Every member id that may hold an open seat on a RUNNING instance: the
417
+ * assignee of an open task, or an open candidate row on one. Still a
418
+ * superset (a countersign voter who already decided stays the assignee);
419
+ * callers count with {@link readRunningMemberTasks}, which drops those.
420
+ *
421
+ * One query that returns only the distinct holder ids, never a row per
422
+ * task or seat: the member screen loads it every time.
423
+ */
424
+ private readOpenSeatHolderMemberIds;
425
+ /** `schema.table` of a repository's entity, escaped for raw SQL. */
426
+ private readQualifiedTableName;
395
427
  /**
396
428
  * The open tasks `memberId` holds on RUNNING instances, with the instance
397
429
  * each belongs to. The instance filter is applied here, not only in the query.
@@ -38,6 +38,7 @@ const activity_log_entity_1 = require("./activity-log.entity");
38
38
  const adhoc_directive_entity_1 = require("./adhoc-directive.entity");
39
39
  const adhoc_enums_1 = require("./adhoc.enums");
40
40
  const approval_instance_entity_1 = require("./approval-instance.entity");
41
+ const text_field_pattern_test_1 = require("./text-field-pattern-test");
41
42
  const form_data_fingerprint_1 = require("./form-data-fingerprint");
42
43
  const instance_submitter_1 = require("./instance-submitter");
43
44
  const task_decision_entity_1 = require("./task-decision.entity");
@@ -113,6 +114,15 @@ class TaskReassignmentRejectedError extends Error {
113
114
  this.errorCode = errorCode;
114
115
  }
115
116
  }
117
+ /** The administrator screens are in Traditional Chinese: names sort by stroke count. */
118
+ const INACTIVE_MEMBER_NAME_LOCALE = 'zh-Hant-TW';
119
+ /**
120
+ * How many deactivated members have their open tasks counted at once. Each
121
+ * count is a few queries, so an unbounded fan-out would put one query in
122
+ * flight per member, and claim that many pool connections at the same time, on
123
+ * every load of the member screen.
124
+ */
125
+ const INACTIVE_MEMBER_COUNT_CONCURRENCY = 5;
116
126
  const WORKFLOW_READ_ALL_PERMISSIONS = new Set([
117
127
  'bpm:*',
118
128
  'bpm.workflow.read_all',
@@ -908,6 +918,7 @@ let WorkflowEngineService = WorkflowEngineService_1 = class WorkflowEngineServic
908
918
  instanceId: instance.id,
909
919
  nodeId: null,
910
920
  payload: {
921
+ comment: input.comment?.trim() || null,
911
922
  resubmitStrategy: returnedContext?.resubmitStrategy ?? 'RESTART',
912
923
  },
913
924
  taskId: null,
@@ -3340,6 +3351,97 @@ let WorkflowEngineService = WorkflowEngineService_1 = class WorkflowEngineServic
3340
3351
  };
3341
3352
  });
3342
3353
  }
3354
+ /**
3355
+ * Deactivated members who still hold open tasks, so an administrator can find
3356
+ * them: a deactivated member no longer shows up in the member search.
3357
+ *
3358
+ * BPM cannot tell a deactivated member from an id it never knew, so the host
3359
+ * names them: `resolveInactiveMembers` gets every member id that holds an open
3360
+ * seat and returns the ones it knows but has deactivated. The count per member
3361
+ * is the {@link listMemberOpenTasks} count, and members left with none are
3362
+ * dropped.
3363
+ */
3364
+ async listInactiveMembersWithOpenTasks(resolveInactiveMembers) {
3365
+ const holderIds = await this.readOpenSeatHolderMemberIds();
3366
+ if (!holderIds.length) {
3367
+ return [];
3368
+ }
3369
+ const holderIdSet = new Set(holderIds);
3370
+ // Only the ids it was asked about are counted, each once: a member the
3371
+ // host adds would only cost task queries before the count dropped it.
3372
+ const inactiveMembers = [
3373
+ ...new Map((await resolveInactiveMembers(holderIds))
3374
+ .filter((member) => holderIdSet.has(member.memberId))
3375
+ .map((member) => [member.memberId, member])).values(),
3376
+ ];
3377
+ const counted = await chunkArray(inactiveMembers, INACTIVE_MEMBER_COUNT_CONCURRENCY).reduce(async (previous, batch) => [
3378
+ ...(await previous),
3379
+ ...(await Promise.all(batch.map(async (member) => ({
3380
+ email: member.email,
3381
+ memberId: member.memberId,
3382
+ name: member.name,
3383
+ openTaskCount: (await this.readRunningMemberTasks(member.memberId))
3384
+ .length,
3385
+ })))),
3386
+ ], Promise.resolve([]));
3387
+ return counted
3388
+ .filter((record) => record.openTaskCount > 0)
3389
+ .sort((left, right) => left.name.localeCompare(right.name, INACTIVE_MEMBER_NAME_LOCALE) ||
3390
+ // Namesakes are common; the id keeps their order stable.
3391
+ (left.memberId < right.memberId
3392
+ ? -1
3393
+ : left.memberId > right.memberId
3394
+ ? 1
3395
+ : 0));
3396
+ }
3397
+ /**
3398
+ * Every member id that may hold an open seat on a RUNNING instance: the
3399
+ * assignee of an open task, or an open candidate row on one. Still a
3400
+ * superset (a countersign voter who already decided stays the assignee);
3401
+ * callers count with {@link readRunningMemberTasks}, which drops those.
3402
+ *
3403
+ * One query that returns only the distinct holder ids, never a row per
3404
+ * task or seat: the member screen loads it every time.
3405
+ */
3406
+ async readOpenSeatHolderMemberIds() {
3407
+ const taskTable = this.readQualifiedTableName(this.taskRepository);
3408
+ const candidateTable = this.readQualifiedTableName(this.taskCandidateRepository);
3409
+ const instanceTable = this.readQualifiedTableName(this.approvalInstanceRepository);
3410
+ const rows = await this.approvalInstanceRepository.query(`SELECT holder.member_id AS "memberId"
3411
+ FROM (
3412
+ SELECT task.assignee_member_id AS member_id
3413
+ FROM ${taskTable} AS task
3414
+ JOIN ${instanceTable} AS instance
3415
+ ON instance.id = task.instance_id
3416
+ WHERE task.status = ANY($1::text[])
3417
+ AND task.assignee_member_id IS NOT NULL
3418
+ AND instance.state = $2
3419
+ UNION
3420
+ SELECT candidate.member_id
3421
+ FROM ${candidateTable} AS candidate
3422
+ JOIN ${taskTable} AS task ON task.id = candidate.task_id
3423
+ JOIN ${instanceTable} AS instance
3424
+ ON instance.id = task.instance_id
3425
+ WHERE candidate.status = ANY($3::text[])
3426
+ AND task.status = ANY($1::text[])
3427
+ AND instance.state = $2
3428
+ ) AS holder`, [
3429
+ [workflow_engine_enums_1.TaskStatusEnum.PENDING, workflow_engine_enums_1.TaskStatusEnum.IN_PROGRESS],
3430
+ workflow_engine_enums_1.ApprovalInstanceStateEnum.RUNNING,
3431
+ [...OPEN_SEAT_STATUSES],
3432
+ ]);
3433
+ // Sorted here, not in SQL: the default JS order (UTF-16 code units),
3434
+ // whatever the DB collation.
3435
+ return rows.map((row) => row.memberId).sort();
3436
+ }
3437
+ /** `schema.table` of a repository's entity, escaped for raw SQL. */
3438
+ readQualifiedTableName(repository) {
3439
+ const { driver } = this.approvalInstanceRepository.manager.connection;
3440
+ return [repository.metadata.schema, repository.metadata.tableName]
3441
+ .filter((part) => Boolean(part))
3442
+ .map((part) => driver.escape(part))
3443
+ .join('.');
3444
+ }
3343
3445
  /**
3344
3446
  * The open tasks `memberId` holds on RUNNING instances, with the instance
3345
3447
  * each belongs to. The instance filter is applied here, not only in the query.
@@ -3739,11 +3841,13 @@ let WorkflowEngineService = WorkflowEngineService_1 = class WorkflowEngineServic
3739
3841
  // Not deduplicated: a node that excludes the initiator filters first, so a
3740
3842
  // first-seen entry that must be dropped cannot shadow a legitimate one.
3741
3843
  async delegateResolvedCandidates(manager, instance, nodeId, resolvedCandidates, gradeGated) {
3742
- const context = this.buildDelegationContext(instance, nodeId);
3743
- const resolved = await Promise.all(resolvedCandidates.map(async (candidate) => ({
3844
+ // One batch for the node, so the host directory is asked once for every
3845
+ // candidate's delegation agents rather than once per candidate.
3846
+ const resolutions = await this.delegationService.resolveAssignees(resolvedCandidates.map((candidate) => candidate.memberId), this.buildDelegationContext(instance, nodeId));
3847
+ const resolved = resolvedCandidates.map((candidate, index) => ({
3744
3848
  candidate,
3745
- resolution: await this.delegationService.resolveAssignee(candidate.memberId, context),
3746
- })));
3849
+ resolution: resolutions[index],
3850
+ }));
3747
3851
  // One batch of grade lookups for the whole node, not two per delegate.
3748
3852
  const levels = gradeGated
3749
3853
  ? await this.readMemberPositionLevels(manager, resolved.flatMap(({ candidate, resolution }) => readGradeGateMemberIds(candidate.memberId, resolution)), this.readOrganizationToday())
@@ -4200,6 +4304,7 @@ let WorkflowEngineService = WorkflowEngineService_1 = class WorkflowEngineServic
4200
4304
  }
4201
4305
  if (action.type === 'SET_FORM_FIELD') {
4202
4306
  const value = this.conditionService.evaluateValue(action.value, buildWorkflowExpressionContext(instance), `workflow.nodes.${node.id}.data.action.value`);
4307
+ assertServiceTaskTextValue(instance.formDefinitionSnapshot, action.fieldPath, value, node.data.label);
4203
4308
  const updatedFormData = writeValueAtPath(instance.formData, action.fieldPath, value);
4204
4309
  // A service task runs inside this transaction, so it cannot call a host
4205
4310
  // provider to re-resolve the label. Rather than leave the previous
@@ -4651,6 +4756,34 @@ function readDataSourceFieldKeyAtPath(snapshot, fieldPath) {
4651
4756
  const field = schema.fields.find((candidate) => isRecord(candidate) && candidate.fieldKey === fieldKey);
4652
4757
  return field && (0, form_1.isFormDataSourceFieldDefinition)(field) ? field.fieldKey : null;
4653
4758
  }
4759
+ /**
4760
+ * Holds a `SET_FORM_FIELD` write to the length and format rules the form
4761
+ * applies to a filler, so a service task cannot store text the field would
4762
+ * have refused. Breaking them throws, which rolls back the submit or decision
4763
+ * that reached the node: the value is never half-written, and the node's value
4764
+ * has to be corrected. Only a top-level field can carry those rules — the
4765
+ * writer ignores an indexed path, and a nested record path names no field —
4766
+ * and an unreadable snapshot is left alone, as in
4767
+ * `readDataSourceFieldKeyAtPath`.
4768
+ */
4769
+ function assertServiceTaskTextValue(snapshot, fieldPath, value, nodeLabel) {
4770
+ const schema = snapshot?.schema;
4771
+ const segments = normalizeFormFieldPath(fieldPath);
4772
+ if (!isFormDefinitionSchema(schema) || segments.length !== 1) {
4773
+ return;
4774
+ }
4775
+ const field = schema.fields.find((candidate) => candidate.fieldKey === segments[0]);
4776
+ const errors = field
4777
+ ? readSubmittedTextValueErrors(field, value, {
4778
+ testPattern: (0, text_field_pattern_test_1.createTimedTextFieldPatternTest)(),
4779
+ })
4780
+ : [];
4781
+ if (!field || errors.length === 0) {
4782
+ return;
4783
+ }
4784
+ throw new common_1.BadRequestException(`系統節點「${nodeLabel}」要寫入欄位「${field.label || field.fieldKey}」的值不符合該欄位的規則` +
4785
+ `(${errors.join('; ')}),這次操作沒有生效;請聯絡流程管理者修正此節點的寫入值`);
4786
+ }
4654
4787
  function readSnapshotWithoutField(snapshots, fieldKey) {
4655
4788
  return Object.fromEntries(Object.entries(snapshots ?? {}).filter(([key]) => key !== fieldKey));
4656
4789
  }
@@ -4897,6 +5030,12 @@ function readReturnTargetNodeId(workflow, currentNodeId, requestedNodeId) {
4897
5030
  throw new common_1.BadRequestException('returnToNodeId is required');
4898
5031
  }
4899
5032
  readWorkflowNodeOrThrow(workflow, trimmedRequestedNodeId);
5033
+ // Only the applicant or a stage the case can already have passed: every
5034
+ // other node would skip ahead, re-run a gateway, or — the end event —
5035
+ // approve the case outright.
5036
+ if (!(0, workflow_graph_1.readSelectableReturnTargetNodeIds)(workflow, currentNodeId).includes(trimmedRequestedNodeId)) {
5037
+ throw new common_1.ConflictException(`User task ${currentNodeId} can only return to the applicant or an earlier user task, not ${trimmedRequestedNodeId}`);
5038
+ }
4900
5039
  return trimmedRequestedNodeId;
4901
5040
  }
4902
5041
  if (trimmedRequestedNodeId &&
@@ -5081,6 +5220,10 @@ function capDecisionPolicyToCandidateCount(policy, candidateCount) {
5081
5220
  ? { ...policy, threshold: Math.max(candidateCount, 1) }
5082
5221
  : policy;
5083
5222
  }
5223
+ /** Splits `items` into consecutive runs of at most `size`. */
5224
+ function chunkArray(items, size) {
5225
+ return Array.from({ length: Math.ceil(items.length / size) }, (_, index) => items.slice(index * size, (index + 1) * size));
5226
+ }
5084
5227
  function uniqueTasksById(tasks) {
5085
5228
  const seen = new Set();
5086
5229
  return tasks.filter((task) => {
@@ -5545,6 +5688,7 @@ function readCandidateStatusForClosedTask(taskStatus) {
5545
5688
  */
5546
5689
  function validateSubmittedFormData(schema, formData, options = {}) {
5547
5690
  const deferredFieldKeys = options.deferredFieldKeys ?? new Set();
5691
+ const testPattern = (0, text_field_pattern_test_1.createTimedTextFieldPatternTest)();
5548
5692
  const visibleFields = schema.fields.filter((field) => isSubmittedFormFieldVisible(field, schema.fields, formData));
5549
5693
  // Tables answer "is this filled?" by row count and report per-row problems
5550
5694
  // with an instance path, so they get their own pass instead of the flat
@@ -5555,6 +5699,25 @@ function validateSubmittedFormData(schema, formData, options = {}) {
5555
5699
  !isSubmittedFieldValuePresent(formData[field.fieldKey]));
5556
5700
  throwFirstFormDataFieldError({
5557
5701
  missingFields,
5702
+ // A field an approver fills in later is held to its rules when they fill
5703
+ // it, not here: the applicant cannot see or change it, so only its type is
5704
+ // checked, the same as a table nobody fills in.
5705
+ readTextErrors: () => [
5706
+ ...visibleFields.flatMap((field) => readSubmittedTextValueErrors(field, formData[field.fieldKey], {
5707
+ shapeOnly: deferredFieldKeys.has(field.fieldKey),
5708
+ testPattern,
5709
+ })),
5710
+ // A field nobody can fill in right now — hidden (store-only), or one
5711
+ // whose `visibleWhen` is false — keeps its submitted value, so its value
5712
+ // is checked for its type. Only the type: its length and format apply
5713
+ // once the field is shown and the filler can correct it.
5714
+ ...schema.fields
5715
+ .filter((field) => !visibleFields.includes(field))
5716
+ .flatMap((field) => readSubmittedTextValueErrors(field, formData[field.fieldKey], {
5717
+ shapeOnly: true,
5718
+ testPattern,
5719
+ })),
5720
+ ],
5558
5721
  // A `DYNAMIC_FORM` resolver reads a member value whether or not its field
5559
5722
  // is visible, so a hidden field still holding a value must be well-formed
5560
5723
  // too. Whether a hidden field is *required* stays a visibility question
@@ -5564,14 +5727,14 @@ function validateSubmittedFormData(schema, formData, options = {}) {
5564
5727
  readTableErrors: () => [
5565
5728
  ...visibleFields
5566
5729
  .filter(form_1.isTableFieldDefinition)
5567
- .flatMap((field) => validateSubmittedTableValue(field, formData[field.fieldKey], isSubmittedFormFieldRequired(field, schema.fields, formData), deferredFieldKeys.has(field.fieldKey))),
5730
+ .flatMap((field) => validateSubmittedTableValue(field, formData[field.fieldKey], isSubmittedFormFieldRequired(field, schema.fields, formData), testPattern, deferredFieldKeys.has(field.fieldKey))),
5568
5731
  // A hidden table is not "visible", but its stored value still has to be
5569
5732
  // a well-formed table under the row cap: only the required / minimum
5570
5733
  // checks are skipped, since nobody can fill the table in.
5571
5734
  ...schema.fields
5572
5735
  .filter(form_1.isTableFieldDefinition)
5573
5736
  .filter((field) => field.hidden === true)
5574
- .flatMap((field) => validateSubmittedTableValue(field, formData[field.fieldKey], false, true)),
5737
+ .flatMap((field) => validateSubmittedTableValue(field, formData[field.fieldKey], false, testPattern, true)),
5575
5738
  ],
5576
5739
  });
5577
5740
  }
@@ -5584,6 +5747,7 @@ function validateSubmittedFormData(schema, formData, options = {}) {
5584
5747
  */
5585
5748
  function validateFilledFormFields(schema, formData, fieldKeys, requiredFieldKeys) {
5586
5749
  const fields = schema.fields.filter((field) => fieldKeys.has(field.fieldKey));
5750
+ const testPattern = (0, text_field_pattern_test_1.createTimedTextFieldPatternTest)();
5587
5751
  // `readRowCellValue` is used below as an own-property reader for top-level
5588
5752
  // form keys: a key like `constructor` must not read off the prototype chain.
5589
5753
  throwFirstFormDataFieldError({
@@ -5591,23 +5755,29 @@ function validateFilledFormFields(schema, formData, fieldKeys, requiredFieldKeys
5591
5755
  missingFields: fields.filter((field) => !(0, form_1.isTableFieldDefinition)(field) &&
5592
5756
  requiredFieldKeys.has(field.fieldKey) &&
5593
5757
  (0, bpm_core_shared_1.isFormDataValueEmpty)(readRowCellValue(formData, field.fieldKey))),
5758
+ readTextErrors: () => fields.flatMap((field) => readSubmittedTextValueErrors(field, readRowCellValue(formData, field.fieldKey), { testPattern })),
5594
5759
  readMemberErrors: () => (0, form_member_value_validator_1.readSubmittedMemberValueErrors)(fields, formData),
5595
5760
  readTableErrors: () => fields
5596
5761
  .filter(form_1.isTableFieldDefinition)
5597
- .flatMap((field) => validateSubmittedTableValue(field, readRowCellValue(formData, field.fieldKey), requiredFieldKeys.has(field.fieldKey))),
5762
+ .flatMap((field) => validateSubmittedTableValue(field, readRowCellValue(formData, field.fieldKey), requiredFieldKeys.has(field.fieldKey), testPattern)),
5598
5763
  });
5599
5764
  }
5600
5765
  /**
5601
5766
  * The shared tail of submit and approver-fill validation: a missing required
5602
- * field wins over a malformed member value, which wins over a table problem,
5603
- * and the later checks are only evaluated when the earlier ones pass.
5767
+ * field wins over a text value breaking its length or format rule, which wins
5768
+ * over a malformed member value, which wins over a table problem, and the
5769
+ * later checks are only evaluated when the earlier ones pass.
5604
5770
  */
5605
- function throwFirstFormDataFieldError({ missingFields, readMemberErrors, readTableErrors, }) {
5771
+ function throwFirstFormDataFieldError({ missingFields, readMemberErrors, readTableErrors, readTextErrors, }) {
5606
5772
  if (missingFields.length > 0) {
5607
5773
  throw new common_1.BadRequestException(`Form data is missing required fields: ${missingFields
5608
5774
  .map((field) => field.label || field.fieldKey)
5609
5775
  .join(', ')}`);
5610
5776
  }
5777
+ const textErrors = readTextErrors();
5778
+ if (textErrors.length > 0) {
5779
+ throw new common_1.BadRequestException(textErrors.join('; '));
5780
+ }
5611
5781
  const memberErrors = readMemberErrors();
5612
5782
  if (memberErrors.length > 0) {
5613
5783
  throw new common_1.BadRequestException(memberErrors.join('; '));
@@ -5619,11 +5789,10 @@ function throwFirstFormDataFieldError({ missingFields, readMemberErrors, readTab
5619
5789
  }
5620
5790
  /**
5621
5791
  * Authoritative shape, row-count and per-row required checks for one table
5622
- * value (ADR 16 §3.7). Depth stops here on purpose: like the flat fields, only
5623
- * required / shape / row count are enforced server side; `minimum`, `maxLength`
5624
- * and friends stay a frontend hint.
5792
+ * value (ADR 16 §3.7), plus the length and format rules of text columns, which
5793
+ * the flat text fields share. `minimum` / `maximum` stay a frontend hint.
5625
5794
  */
5626
- function validateSubmittedTableValue(field, value, required, shapeOnly = false) {
5795
+ function validateSubmittedTableValue(field, value, required, testPattern, shapeOnly = false) {
5627
5796
  const path = `formData.${field.fieldKey}`;
5628
5797
  if (typeof value === 'undefined' || value === null) {
5629
5798
  return shapeOnly
@@ -5635,31 +5804,32 @@ function validateSubmittedTableValue(field, value, required, shapeOnly = false)
5635
5804
  if (!Array.isArray(value)) {
5636
5805
  return [`${path} must be an array of rows`];
5637
5806
  }
5638
- const rowErrors = value.flatMap((row, index) => validateSubmittedTableRow(field, row, `${path}[${index}]`, shapeOnly));
5639
- // A malformed row cannot be counted against min/max meaningfully; report the
5640
- // shape problem first so the submitter fixes the real cause.
5807
+ // Too many rows is refused before any row is checked: the rows a submitter
5808
+ // sends would otherwise decide how many cells the text patterns run on.
5809
+ const maxRows = readTableMaxRows(field);
5810
+ if (value.length > maxRows) {
5811
+ return [`${path} must include at most ${maxRows} row(s)`];
5812
+ }
5813
+ const rowErrors = value.flatMap((row, index) => validateSubmittedTableRow(field, row, `${path}[${index}]`, testPattern, shapeOnly));
5814
+ // A malformed row cannot be counted against the minimum meaningfully; report
5815
+ // the shape problem first so the submitter fixes the real cause.
5641
5816
  if (rowErrors.length > 0) {
5642
5817
  return rowErrors;
5643
5818
  }
5644
5819
  return validateSubmittedTableRowCount(field, value.length, required, path, shapeOnly);
5645
5820
  }
5821
+ /** The minimum only: the maximum is refused before any row is checked. */
5646
5822
  function validateSubmittedTableRowCount(field, rowCount, required, path, shapeOnly = false) {
5647
5823
  const minRows = shapeOnly
5648
5824
  ? 0
5649
5825
  : required
5650
5826
  ? Math.max(readTableMinRows(field), 1)
5651
5827
  : readTableMinRows(field);
5652
- const maxRows = readTableMaxRows(field);
5653
- return [
5654
- ...(rowCount < minRows
5655
- ? [`${path} must include at least ${minRows} row(s)`]
5656
- : []),
5657
- ...(rowCount > maxRows
5658
- ? [`${path} must include at most ${maxRows} row(s)`]
5659
- : []),
5660
- ];
5661
- }
5662
- function validateSubmittedTableRow(field, row, path, shapeOnly = false) {
5828
+ return rowCount < minRows
5829
+ ? [`${path} must include at least ${minRows} row(s)`]
5830
+ : [];
5831
+ }
5832
+ function validateSubmittedTableRow(field, row, path, testPattern, shapeOnly = false) {
5663
5833
  if (!isRecord(row)) {
5664
5834
  return [`${path} must be an object`];
5665
5835
  }
@@ -5676,7 +5846,61 @@ function validateSubmittedTableRow(field, row, path, shapeOnly = false) {
5676
5846
  .filter((column) => isSubmittedTableColumnRequired(column) &&
5677
5847
  !isSubmittedFieldValuePresent(readRowCellValue(row, column.fieldKey)))
5678
5848
  .map((column) => `${path}.${column.fieldKey} is required`);
5679
- return [...unknownKeyErrors, ...cellErrors, ...requiredErrors];
5849
+ // A shape-only pass covers a table nobody fills in, so the filler-facing
5850
+ // rules do not apply to it, the same as the required check above; only a
5851
+ // cell of the wrong type is still refused.
5852
+ const textErrors = field.columns.flatMap((column) => readSubmittedTextValueErrors(column, readRowCellValue(row, column.fieldKey), {
5853
+ path: `${path}.${column.fieldKey}`,
5854
+ shapeOnly,
5855
+ testPattern,
5856
+ }));
5857
+ return [...unknownKeyErrors, ...cellErrors, ...requiredErrors, ...textErrors];
5858
+ }
5859
+ /**
5860
+ * The server half of the text length and format rules: the same
5861
+ * `readTextFieldValueIssue` the renderer runs before it lets the filler send,
5862
+ * so a crafted request cannot store what the form would have refused — a
5863
+ * number or an array sent for a text field with rules included. `shapeOnly`
5864
+ * keeps only that type check, for a value nobody fills in at this step, and
5865
+ * does not run the pattern at all. `testPattern` is the validation pass's
5866
+ * timed pattern test (see `createTimedTextFieldPatternTest`); once its time
5867
+ * budget is spent, a value is reported as not checked rather than as a
5868
+ * format error.
5869
+ */
5870
+ function readSubmittedTextValueErrors(field, value, { path = `formData.${field.fieldKey}`, shapeOnly = false, testPattern, }) {
5871
+ if (field.type !== 'text' && field.type !== 'textarea') {
5872
+ return [];
5873
+ }
5874
+ const readIssue = () => {
5875
+ try {
5876
+ return (0, form_1.readTextFieldValueIssue)(field, value, {
5877
+ testPattern: shapeOnly ? () => true : testPattern,
5878
+ });
5879
+ }
5880
+ catch (error) {
5881
+ if (error instanceof text_field_pattern_test_1.TextFieldPatternTimeoutError) {
5882
+ return 'timeout';
5883
+ }
5884
+ throw error;
5885
+ }
5886
+ };
5887
+ const issue = readIssue();
5888
+ if (issue === 'timeout') {
5889
+ return [`${path} could not be checked against the required format in time`];
5890
+ }
5891
+ if (!issue || (shapeOnly && issue.kind !== 'type')) {
5892
+ return [];
5893
+ }
5894
+ if (issue.kind === 'type') {
5895
+ return [`${path} must be text`];
5896
+ }
5897
+ if (issue.kind === 'minLength') {
5898
+ return [`${path} must be at least ${issue.limit} characters`];
5899
+ }
5900
+ if (issue.kind === 'maxLength') {
5901
+ return [`${path} must be at most ${issue.limit} characters`];
5902
+ }
5903
+ return [`${path} does not match the required format`];
5680
5904
  }
5681
5905
  /**
5682
5906
  * Own-property read. `constructor`, `toString` and friends all satisfy the