bpmn-elements 17.2.2 → 18.0.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.
- package/README.md +3 -1
- package/dist/Api.js +83 -0
- package/dist/Context.js +228 -22
- package/dist/Environment.js +111 -31
- package/dist/EventBroker.js +57 -1
- package/dist/Expressions.js +3 -4
- package/dist/MessageFormatter.js +29 -16
- package/dist/Timers.js +13 -9
- package/dist/Tracker.js +1 -0
- package/dist/activity/Activity.js +458 -254
- package/dist/activity/ActivityExecution.js +113 -40
- package/dist/activity/Dummy.js +6 -1
- package/dist/activity/Escalation.js +36 -24
- package/dist/activity/ExecutionScope.js +1 -1
- package/dist/activity/Message.js +36 -24
- package/dist/activity/Signal.js +36 -24
- package/dist/activity/outbound-evaluator.js +1 -1
- package/dist/condition.js +12 -6
- package/dist/constants.js +21 -0
- package/dist/definition/Definition.js +182 -64
- package/dist/definition/DefinitionExecution.js +195 -82
- package/dist/error/BpmnError.js +12 -1
- package/dist/error/Errors.js +50 -9
- package/dist/eventDefinitions/CancelEventDefinition.js +29 -11
- package/dist/eventDefinitions/CompensateEventDefinition.js +51 -31
- package/dist/eventDefinitions/ConditionalEventDefinition.js +21 -9
- package/dist/eventDefinitions/ErrorEventDefinition.js +46 -30
- package/dist/eventDefinitions/EscalationEventDefinition.js +44 -27
- package/dist/eventDefinitions/EventDefinitionExecution.js +30 -23
- package/dist/eventDefinitions/LinkEventDefinition.js +45 -120
- package/dist/eventDefinitions/MessageEventDefinition.js +44 -29
- package/dist/eventDefinitions/SignalEventDefinition.js +46 -31
- package/dist/eventDefinitions/TerminateEventDefinition.js +10 -1
- package/dist/eventDefinitions/TimerEventDefinition.js +57 -37
- package/dist/eventDefinitions/index.js +20 -21
- package/dist/events/BoundaryEvent.js +52 -40
- package/dist/events/EndEvent.js +22 -8
- package/dist/events/IntermediateCatchEvent.js +26 -8
- package/dist/events/IntermediateThrowEvent.js +24 -9
- package/dist/events/StartEvent.js +30 -14
- package/dist/events/index.js +10 -11
- package/dist/flows/Association.js +50 -7
- package/dist/flows/MessageFlow.js +49 -10
- package/dist/flows/SequenceFlow.js +93 -22
- package/dist/flows/index.js +6 -7
- package/dist/gateways/EventBasedGateway.js +29 -15
- package/dist/gateways/ExclusiveGateway.js +20 -5
- package/dist/gateways/InclusiveGateway.js +21 -5
- package/dist/gateways/ParallelGateway.js +253 -15
- package/dist/gateways/index.js +8 -9
- package/dist/getPropertyValue.js +2 -2
- package/dist/index.js +42 -43
- package/dist/io/BpmnIO.js +15 -1
- package/dist/io/EnvironmentDataObject.js +29 -1
- package/dist/io/EnvironmentDataStore.js +24 -1
- package/dist/io/EnvironmentDataStoreReference.js +24 -1
- package/dist/io/InputOutputSpecification.js +21 -11
- package/dist/io/Properties.js +28 -17
- package/dist/messageHelper.js +41 -4
- package/dist/process/Lane.js +15 -4
- package/dist/process/Process.js +174 -76
- package/dist/process/ProcessExecution.js +362 -177
- package/dist/shared.js +2 -0
- package/dist/tasks/CallActivity.js +19 -4
- package/dist/tasks/LoopCharacteristics.js +94 -9
- package/dist/tasks/ReceiveTask.js +36 -21
- package/dist/tasks/ScriptTask.js +22 -6
- package/dist/tasks/ServiceImplementation.js +7 -4
- package/dist/tasks/ServiceTask.js +19 -4
- package/dist/tasks/SignalTask.js +19 -4
- package/dist/tasks/StandardLoopCharacteristics.js +8 -4
- package/dist/tasks/SubProcess.js +44 -29
- package/dist/tasks/Task.js +19 -4
- package/dist/tasks/Transaction.js +8 -4
- package/dist/tasks/index.js +16 -18
- package/package.json +31 -13
- package/src/Api.js +70 -0
- package/src/Context.js +200 -19
- package/src/Environment.js +99 -30
- package/src/EventBroker.js +46 -1
- package/src/Expressions.js +2 -3
- package/src/MessageFormatter.js +24 -16
- package/src/Timers.js +12 -9
- package/src/Tracker.js +1 -0
- package/src/activity/Activity.js +388 -231
- package/src/activity/ActivityExecution.js +93 -42
- package/src/activity/Dummy.js +6 -1
- package/src/activity/Escalation.js +25 -18
- package/src/activity/ExecutionScope.js +1 -1
- package/src/activity/Message.js +25 -18
- package/src/activity/Signal.js +25 -18
- package/src/activity/outbound-evaluator.js +1 -1
- package/src/condition.js +11 -5
- package/src/constants.js +15 -0
- package/src/definition/Definition.js +157 -62
- package/src/definition/DefinitionExecution.js +161 -83
- package/src/error/BpmnError.js +11 -1
- package/src/error/Errors.js +44 -5
- package/src/eventDefinitions/CancelEventDefinition.js +27 -13
- package/src/eventDefinitions/CompensateEventDefinition.js +48 -32
- package/src/eventDefinitions/ConditionalEventDefinition.js +20 -10
- package/src/eventDefinitions/ErrorEventDefinition.js +44 -33
- package/src/eventDefinitions/EscalationEventDefinition.js +39 -26
- package/src/eventDefinitions/EventDefinitionExecution.js +30 -24
- package/src/eventDefinitions/LinkEventDefinition.js +34 -120
- package/src/eventDefinitions/MessageEventDefinition.js +42 -31
- package/src/eventDefinitions/SignalEventDefinition.js +43 -32
- package/src/eventDefinitions/TerminateEventDefinition.js +9 -1
- package/src/eventDefinitions/TimerEventDefinition.js +53 -35
- package/src/eventDefinitions/index.js +10 -23
- package/src/events/BoundaryEvent.js +50 -39
- package/src/events/EndEvent.js +19 -7
- package/src/events/IntermediateCatchEvent.js +24 -8
- package/src/events/IntermediateThrowEvent.js +24 -8
- package/src/events/StartEvent.js +25 -14
- package/src/events/index.js +5 -18
- package/src/flows/Association.js +43 -9
- package/src/flows/MessageFlow.js +41 -10
- package/src/flows/SequenceFlow.js +82 -19
- package/src/flows/index.js +3 -4
- package/src/gateways/EventBasedGateway.js +27 -15
- package/src/gateways/ExclusiveGateway.js +16 -3
- package/src/gateways/InclusiveGateway.js +16 -3
- package/src/gateways/ParallelGateway.js +301 -10
- package/src/gateways/index.js +4 -4
- package/src/getPropertyValue.js +2 -2
- package/src/index.js +19 -19
- package/src/io/BpmnIO.js +13 -1
- package/src/io/EnvironmentDataObject.js +26 -1
- package/src/io/EnvironmentDataStore.js +22 -1
- package/src/io/EnvironmentDataStoreReference.js +22 -1
- package/src/io/InputOutputSpecification.js +17 -8
- package/src/io/Properties.js +23 -13
- package/src/messageHelper.js +36 -4
- package/src/process/Lane.js +14 -4
- package/src/process/Process.js +154 -72
- package/src/process/ProcessExecution.js +326 -175
- package/src/shared.js +1 -0
- package/src/tasks/CallActivity.js +16 -2
- package/src/tasks/LoopCharacteristics.js +77 -11
- package/src/tasks/ReceiveTask.js +33 -22
- package/src/tasks/ScriptTask.js +17 -3
- package/src/tasks/ServiceImplementation.js +6 -3
- package/src/tasks/ServiceTask.js +16 -2
- package/src/tasks/SignalTask.js +16 -2
- package/src/tasks/StandardLoopCharacteristics.js +7 -3
- package/src/tasks/SubProcess.js +37 -23
- package/src/tasks/Task.js +16 -2
- package/src/tasks/Transaction.js +7 -3
- package/src/tasks/index.js +8 -9
- package/types/bundle-errors.d.ts +1 -0
- package/types/bundle.d.ts +97 -0
- package/types/index.d.ts +2614 -84
- package/types/interfaces.d.ts +636 -0
- package/types/types.d.ts +0 -765
package/src/Context.js
CHANGED
|
@@ -1,25 +1,41 @@
|
|
|
1
|
-
import BpmnIO from './io/BpmnIO.js';
|
|
2
|
-
import Environment from './Environment.js';
|
|
1
|
+
import { BpmnIO } from './io/BpmnIO.js';
|
|
2
|
+
import { Environment } from './Environment.js';
|
|
3
3
|
import { getUniqueId } from './shared.js';
|
|
4
|
+
import { K_ACTIVATED } from './constants.js';
|
|
4
5
|
|
|
5
|
-
const
|
|
6
|
-
const kActivated = Symbol.for('activated');
|
|
6
|
+
const K_OWNER = Symbol.for('owner');
|
|
7
7
|
|
|
8
|
-
|
|
8
|
+
/**
|
|
9
|
+
* Build a runtime Context from a parsed BPMN definition.
|
|
10
|
+
* @param {import('moddle-context-serializer').SerializableContext} definitionContext
|
|
11
|
+
* @param {import('#types').Environment} [environment] Existing environment to clone; a fresh one is created when omitted
|
|
12
|
+
*/
|
|
13
|
+
export function Context(definitionContext, environment) {
|
|
9
14
|
environment = environment ? environment.clone() : new Environment();
|
|
10
15
|
return new ContextInstance(definitionContext, environment);
|
|
11
16
|
}
|
|
12
17
|
|
|
13
|
-
|
|
18
|
+
/**
|
|
19
|
+
* Per-execution registry that lazily upserts activities, flows, and processes from the parsed BPMN definition.
|
|
20
|
+
* @param {import('moddle-context-serializer').SerializableContext} definitionContext
|
|
21
|
+
* @param {import('#types').Environment} environment
|
|
22
|
+
* @param {import('#types').Process | import('#types').Activity} [owner] Process or sub-process activity that owns this context
|
|
23
|
+
* @param {Map<string, any>} [peersCache] Shared converging parallel gateway peer cache; created at the root and propagated to every clone
|
|
24
|
+
*/
|
|
25
|
+
export function ContextInstance(definitionContext, environment, owner, peersCache) {
|
|
14
26
|
const { id = 'Def', name, type = 'context' } = definitionContext;
|
|
15
|
-
const sid = getUniqueId(id);
|
|
16
27
|
this.id = id;
|
|
17
28
|
this.name = name;
|
|
18
29
|
this.type = type;
|
|
19
|
-
|
|
30
|
+
/** Unique instance id */
|
|
31
|
+
this.sid = getUniqueId(id);
|
|
20
32
|
this.definitionContext = definitionContext;
|
|
21
33
|
this.environment = environment;
|
|
34
|
+
/** Discovered parallel gateway peers, keyed by gateway id, shared with all clones. Runtime-only, not serialized. */
|
|
35
|
+
this.peersCache = peersCache || new Map();
|
|
36
|
+
/** @type {import('#types').IExtensionsMapper} */
|
|
22
37
|
this.extensionsMapper = new ExtensionsMapper(this);
|
|
38
|
+
/** @private */
|
|
23
39
|
this.refs = new Map([
|
|
24
40
|
['activityRefs', new Map()],
|
|
25
41
|
['sequenceFlowRefs', new Map()],
|
|
@@ -29,15 +45,21 @@ function ContextInstance(definitionContext, environment, owner) {
|
|
|
29
45
|
['dataObjectRefs', new Map()],
|
|
30
46
|
['dataStoreRefs', new Map()],
|
|
31
47
|
]);
|
|
32
|
-
this[
|
|
48
|
+
this[K_OWNER] = owner;
|
|
33
49
|
}
|
|
34
50
|
|
|
35
51
|
Object.defineProperty(ContextInstance.prototype, 'owner', {
|
|
52
|
+
/** @returns {import('#types').Process | import('#types').Activity | undefined} Process or sub-process activity that owns this context */
|
|
36
53
|
get() {
|
|
37
|
-
return this[
|
|
54
|
+
return this[K_OWNER];
|
|
38
55
|
},
|
|
39
56
|
});
|
|
40
57
|
|
|
58
|
+
/**
|
|
59
|
+
* Get or create the activity instance for the given id.
|
|
60
|
+
* @param {string} activityId
|
|
61
|
+
* @returns {import('./activity/Activity.js').Activity | null}
|
|
62
|
+
*/
|
|
41
63
|
ContextInstance.prototype.getActivityById = function getActivityById(activityId) {
|
|
42
64
|
const activityInstance = this.refs.get('activityRefs').get(activityId);
|
|
43
65
|
if (activityInstance) return activityInstance;
|
|
@@ -46,6 +68,11 @@ ContextInstance.prototype.getActivityById = function getActivityById(activityId)
|
|
|
46
68
|
return this.upsertActivity(activity);
|
|
47
69
|
};
|
|
48
70
|
|
|
71
|
+
/**
|
|
72
|
+
* Return the cached activity instance, instantiating it the first time it is referenced.
|
|
73
|
+
* @param {import('moddle-context-serializer').SerializableElement} activityDef
|
|
74
|
+
* @returns {import('./activity/Activity.js').Activity}
|
|
75
|
+
*/
|
|
49
76
|
ContextInstance.prototype.upsertActivity = function upsertActivity(activityDef) {
|
|
50
77
|
let activityInstance = this.refs.get('activityRefs').get(activityDef.id);
|
|
51
78
|
if (activityInstance) return activityInstance;
|
|
@@ -56,6 +83,11 @@ ContextInstance.prototype.upsertActivity = function upsertActivity(activityDef)
|
|
|
56
83
|
return activityInstance;
|
|
57
84
|
};
|
|
58
85
|
|
|
86
|
+
/**
|
|
87
|
+
* Get or create the sequence flow instance for the given id.
|
|
88
|
+
* @param {string} sequenceFlowId
|
|
89
|
+
* @returns {import('./flows/SequenceFlow.js').SequenceFlow | null}
|
|
90
|
+
*/
|
|
59
91
|
ContextInstance.prototype.getSequenceFlowById = function getSequenceFlowById(sequenceFlowId) {
|
|
60
92
|
const flowInstance = this.refs.get('sequenceFlowRefs').get(sequenceFlowId);
|
|
61
93
|
if (flowInstance) return flowInstance;
|
|
@@ -65,30 +97,55 @@ ContextInstance.prototype.getSequenceFlowById = function getSequenceFlowById(seq
|
|
|
65
97
|
return this.upsertSequenceFlow(flowDef);
|
|
66
98
|
};
|
|
67
99
|
|
|
100
|
+
/**
|
|
101
|
+
* @param {string} activityId
|
|
102
|
+
*/
|
|
68
103
|
ContextInstance.prototype.getInboundSequenceFlows = function getInboundSequenceFlows(activityId) {
|
|
69
104
|
return (this.definitionContext.getInboundSequenceFlows(activityId) || []).map((flow) => this.upsertSequenceFlow(flow));
|
|
70
105
|
};
|
|
71
106
|
|
|
107
|
+
/**
|
|
108
|
+
* @param {string} activityId
|
|
109
|
+
*/
|
|
72
110
|
ContextInstance.prototype.getOutboundSequenceFlows = function getOutboundSequenceFlows(activityId) {
|
|
73
111
|
return (this.definitionContext.getOutboundSequenceFlows(activityId) || []).map((flow) => this.upsertSequenceFlow(flow));
|
|
74
112
|
};
|
|
75
113
|
|
|
114
|
+
/**
|
|
115
|
+
* @param {string} activityId
|
|
116
|
+
*/
|
|
76
117
|
ContextInstance.prototype.getInboundAssociations = function getInboundAssociations(activityId) {
|
|
77
118
|
return (this.definitionContext.getInboundAssociations(activityId) || []).map((association) => this.upsertAssociation(association));
|
|
78
119
|
};
|
|
79
120
|
|
|
121
|
+
/**
|
|
122
|
+
* @param {string} activityId
|
|
123
|
+
*/
|
|
80
124
|
ContextInstance.prototype.getOutboundAssociations = function getOutboundAssociations(activityId) {
|
|
81
125
|
return (this.definitionContext.getOutboundAssociations(activityId) || []).map((association) => this.upsertAssociation(association));
|
|
82
126
|
};
|
|
83
127
|
|
|
128
|
+
/**
|
|
129
|
+
* Get every activity in the definition, optionally narrowed to a parent scope.
|
|
130
|
+
* @param {string} [scopeId] Process or sub-process id
|
|
131
|
+
*/
|
|
84
132
|
ContextInstance.prototype.getActivities = function getActivities(scopeId) {
|
|
85
133
|
return (this.definitionContext.getActivities(scopeId) || []).map((activityDef) => this.upsertActivity(activityDef));
|
|
86
134
|
};
|
|
87
135
|
|
|
136
|
+
/**
|
|
137
|
+
* Get every sequence flow in the definition, optionally narrowed to a parent scope.
|
|
138
|
+
* @param {string} [scopeId] Process or sub-process id
|
|
139
|
+
*/
|
|
88
140
|
ContextInstance.prototype.getSequenceFlows = function getSequenceFlows(scopeId) {
|
|
89
141
|
return (this.definitionContext.getSequenceFlows(scopeId) || []).map((flow) => this.upsertSequenceFlow(flow));
|
|
90
142
|
};
|
|
91
143
|
|
|
144
|
+
/**
|
|
145
|
+
* Return the cached sequence flow, instantiating it the first time it is referenced.
|
|
146
|
+
* @param {import('moddle-context-serializer').SerializableElement} flowDefinition
|
|
147
|
+
* @returns {import('./flows/SequenceFlow.js').SequenceFlow}
|
|
148
|
+
*/
|
|
92
149
|
ContextInstance.prototype.upsertSequenceFlow = function upsertSequenceFlow(flowDefinition) {
|
|
93
150
|
const sequenceFlowRefs = this.refs.get('sequenceFlowRefs');
|
|
94
151
|
let flowInstance = sequenceFlowRefs.get(flowDefinition.id);
|
|
@@ -100,10 +157,18 @@ ContextInstance.prototype.upsertSequenceFlow = function upsertSequenceFlow(flowD
|
|
|
100
157
|
return flowInstance;
|
|
101
158
|
};
|
|
102
159
|
|
|
160
|
+
/**
|
|
161
|
+
* Get association flows
|
|
162
|
+
* @param {string} [scopeId] Process or sub-process id
|
|
163
|
+
*/
|
|
103
164
|
ContextInstance.prototype.getAssociations = function getAssociations(scopeId) {
|
|
104
165
|
return (this.definitionContext.getAssociations(scopeId) || []).map((association) => this.upsertAssociation(association));
|
|
105
166
|
};
|
|
106
167
|
|
|
168
|
+
/**
|
|
169
|
+
* @param {import('moddle-context-serializer').SerializableElement} associationDefinition
|
|
170
|
+
* @returns {import('./flows/Association.js').Association}
|
|
171
|
+
*/
|
|
107
172
|
ContextInstance.prototype.upsertAssociation = function upsertAssociation(associationDefinition) {
|
|
108
173
|
const associationRefs = this.refs.get('associationRefs');
|
|
109
174
|
let instance = associationRefs.get(associationDefinition.id);
|
|
@@ -116,10 +181,38 @@ ContextInstance.prototype.upsertAssociation = function upsertAssociation(associa
|
|
|
116
181
|
return instance;
|
|
117
182
|
};
|
|
118
183
|
|
|
184
|
+
/**
|
|
185
|
+
* Create a new context that shares the parsed definition but optionally swaps environment and owner.
|
|
186
|
+
* @param {import('#types').Environment} [newEnvironment]
|
|
187
|
+
* @param {import('#types').Process | import('#types').Activity} [newOwner]
|
|
188
|
+
*/
|
|
119
189
|
ContextInstance.prototype.clone = function clone(newEnvironment, newOwner) {
|
|
120
|
-
return new ContextInstance(this.definitionContext, newEnvironment || this.environment, newOwner);
|
|
190
|
+
return new ContextInstance(this.definitionContext, newEnvironment || this.environment, newOwner, this.peersCache);
|
|
121
191
|
};
|
|
122
192
|
|
|
193
|
+
/**
|
|
194
|
+
* Cached converging parallel gateway peers discovered by an earlier shake.
|
|
195
|
+
* @param {string} gatewayId
|
|
196
|
+
* @returns {Array<[string, string[]]> | undefined}
|
|
197
|
+
*/
|
|
198
|
+
ContextInstance.prototype.getShakenPeers = function getShakenPeers(gatewayId) {
|
|
199
|
+
return this.peersCache.get(gatewayId);
|
|
200
|
+
};
|
|
201
|
+
|
|
202
|
+
/**
|
|
203
|
+
* Store converging parallel gateway peers so subsequent runs can skip the graph shake.
|
|
204
|
+
* @param {string} gatewayId
|
|
205
|
+
* @param {Array<[string, string[]]>} peers
|
|
206
|
+
*/
|
|
207
|
+
ContextInstance.prototype.setShakenPeers = function setShakenPeers(gatewayId, peers) {
|
|
208
|
+
this.peersCache.set(gatewayId, peers);
|
|
209
|
+
};
|
|
210
|
+
|
|
211
|
+
/**
|
|
212
|
+
* Get or create the process instance for the given id. Each process gets its own cloned environment.
|
|
213
|
+
* @param {string} processId
|
|
214
|
+
* @returns {import('#types').Process | null}
|
|
215
|
+
*/
|
|
123
216
|
ContextInstance.prototype.getProcessById = function getProcessById(processId) {
|
|
124
217
|
const processRefs = this.refs.get('processRefs');
|
|
125
218
|
let bp = processRefs.get(processId);
|
|
@@ -131,30 +224,48 @@ ContextInstance.prototype.getProcessById = function getProcessById(processId) {
|
|
|
131
224
|
const bpContext = this.clone(this.environment.clone());
|
|
132
225
|
bp = new processDefinition.Behaviour(processDefinition, bpContext);
|
|
133
226
|
processRefs.set(processId, bp);
|
|
134
|
-
bpContext[
|
|
227
|
+
bpContext[K_OWNER] = bp;
|
|
135
228
|
|
|
136
229
|
return bp;
|
|
137
230
|
};
|
|
138
231
|
|
|
232
|
+
/**
|
|
233
|
+
* Build a fresh, uncached process instance for the given id. Used by call activities.
|
|
234
|
+
* @param {string} processId
|
|
235
|
+
* @returns {import('#types').Process | null}
|
|
236
|
+
*/
|
|
139
237
|
ContextInstance.prototype.getNewProcessById = function getNewProcessById(processId) {
|
|
140
238
|
if (!this.getProcessById(processId)) return null;
|
|
141
239
|
const bpDef = this.definitionContext.getProcessById(processId);
|
|
142
240
|
|
|
143
241
|
const bpContext = this.clone(this.environment.clone());
|
|
144
242
|
const bp = new bpDef.Behaviour(bpDef, bpContext);
|
|
145
|
-
bpContext[
|
|
243
|
+
bpContext[K_OWNER] = bp;
|
|
146
244
|
|
|
147
245
|
return bp;
|
|
148
246
|
};
|
|
149
247
|
|
|
248
|
+
/**
|
|
249
|
+
* Get every process in the definition.
|
|
250
|
+
* @returns {import('#types').Process[]}
|
|
251
|
+
*/
|
|
150
252
|
ContextInstance.prototype.getProcesses = function getProcesses() {
|
|
151
253
|
return this.definitionContext.getProcesses().map(({ id: processId }) => this.getProcessById(processId));
|
|
152
254
|
};
|
|
153
255
|
|
|
256
|
+
/**
|
|
257
|
+
* Get processes flagged executable in the definition.
|
|
258
|
+
* @returns {import('#types').Process[]}
|
|
259
|
+
*/
|
|
154
260
|
ContextInstance.prototype.getExecutableProcesses = function getExecutableProcesses() {
|
|
155
261
|
return this.definitionContext.getExecutableProcesses().map(({ id: processId }) => this.getProcessById(processId));
|
|
156
262
|
};
|
|
157
263
|
|
|
264
|
+
/**
|
|
265
|
+
* Get message flows that originate from the given process id.
|
|
266
|
+
* @param {string} sourceId Source process id
|
|
267
|
+
* @returns {import('./flows/MessageFlow.js').MessageFlow[]}
|
|
268
|
+
*/
|
|
158
269
|
ContextInstance.prototype.getMessageFlows = function getMessageFlows(sourceId) {
|
|
159
270
|
const messageFlowRefs = this.refs.get('messageFlows');
|
|
160
271
|
|
|
@@ -176,6 +287,11 @@ ContextInstance.prototype.getMessageFlows = function getMessageFlows(sourceId) {
|
|
|
176
287
|
return result;
|
|
177
288
|
};
|
|
178
289
|
|
|
290
|
+
/**
|
|
291
|
+
* Get or create a data object instance for the given reference id.
|
|
292
|
+
* @param {string} referenceId
|
|
293
|
+
* @return {import('#types').IIOData | undefined}
|
|
294
|
+
*/
|
|
179
295
|
ContextInstance.prototype.getDataObjectById = function getDataObjectById(referenceId) {
|
|
180
296
|
const dataObjectRefs = this.refs.get('dataObjectRefs');
|
|
181
297
|
let dataObject;
|
|
@@ -190,6 +306,11 @@ ContextInstance.prototype.getDataObjectById = function getDataObjectById(referen
|
|
|
190
306
|
return dataObject;
|
|
191
307
|
};
|
|
192
308
|
|
|
309
|
+
/**
|
|
310
|
+
* Get or create a data store instance for the given reference id.
|
|
311
|
+
* @param {string} referenceId
|
|
312
|
+
* @return {import('#types').IIOData | undefined}
|
|
313
|
+
*/
|
|
193
314
|
ContextInstance.prototype.getDataStoreById = function getDataStoreById(referenceId) {
|
|
194
315
|
const dataStoreRefs = this.refs.get('dataStoreRefs');
|
|
195
316
|
let dataStore;
|
|
@@ -205,6 +326,11 @@ ContextInstance.prototype.getDataStoreById = function getDataStoreById(reference
|
|
|
205
326
|
return dataStore;
|
|
206
327
|
};
|
|
207
328
|
|
|
329
|
+
/**
|
|
330
|
+
* Get start activities, optionally filtered by referenced event definition or restricted to a parent scope.
|
|
331
|
+
* @param {import('#types').startActivityFilterOptions} [filterOptions]
|
|
332
|
+
* @param {string} [scopeId] Process or sub-process id
|
|
333
|
+
*/
|
|
208
334
|
ContextInstance.prototype.getStartActivities = function getStartActivities(filterOptions, scopeId) {
|
|
209
335
|
const referenceId = filterOptions?.referenceId;
|
|
210
336
|
const referenceType = filterOptions?.referenceType || 'unknown';
|
|
@@ -227,6 +353,56 @@ ContextInstance.prototype.getStartActivities = function getStartActivities(filte
|
|
|
227
353
|
return result;
|
|
228
354
|
};
|
|
229
355
|
|
|
356
|
+
/**
|
|
357
|
+
* Inspect an activity def for link event definitions.
|
|
358
|
+
* @param {import('moddle-context-serializer').Activity} activityDef
|
|
359
|
+
* @returns {{ linkBehaviour?: Function, linkNames?: string[] }}
|
|
360
|
+
*/
|
|
361
|
+
ContextInstance.prototype.getLinkEventDefinitionInfo = function getLinkEventDefinitionInfo(activityDef) {
|
|
362
|
+
const eds = activityDef.behaviour?.eventDefinitions;
|
|
363
|
+
if (!eds) return {};
|
|
364
|
+
let linkBehaviour;
|
|
365
|
+
const names = new Set();
|
|
366
|
+
for (const ed of eds) {
|
|
367
|
+
if (linkBehaviour ? ed.Behaviour === linkBehaviour : ed.type?.endsWith('LinkEventDefinition')) {
|
|
368
|
+
if (!linkBehaviour) linkBehaviour = ed.Behaviour;
|
|
369
|
+
if (ed.behaviour?.name) names.add(ed.behaviour.name);
|
|
370
|
+
}
|
|
371
|
+
}
|
|
372
|
+
if (!linkBehaviour || !names.size) return {};
|
|
373
|
+
return { linkBehaviour, linkNames: [...names] };
|
|
374
|
+
};
|
|
375
|
+
|
|
376
|
+
/**
|
|
377
|
+
* Get activities whose event definitions include the given Behaviour with a matching name.
|
|
378
|
+
* @param {Function} Behaviour Behaviour constructor to match against `ed.Behaviour`
|
|
379
|
+
* @param {string[] | Iterable<string>} names
|
|
380
|
+
* @param {string} [scopeId] Process or sub-process id
|
|
381
|
+
*/
|
|
382
|
+
ContextInstance.prototype.getActivitiesByEventDefinitionBehaviour = function getActivitiesByEventDefinitionBehaviour(
|
|
383
|
+
Behaviour,
|
|
384
|
+
names,
|
|
385
|
+
scopeId
|
|
386
|
+
) {
|
|
387
|
+
const wanted = new Set(names);
|
|
388
|
+
if (!Behaviour || !wanted.size) return [];
|
|
389
|
+
const result = [];
|
|
390
|
+
const rawDefs = this.definitionContext.getActivities(scopeId) || [];
|
|
391
|
+
for (const rawDef of rawDefs) {
|
|
392
|
+
const eds = rawDef.behaviour?.eventDefinitions;
|
|
393
|
+
if (!eds) continue;
|
|
394
|
+
if (!eds.some((ed) => ed.Behaviour === Behaviour && wanted.has(ed.behaviour?.name))) continue;
|
|
395
|
+
result.push(this.upsertActivity(rawDef));
|
|
396
|
+
}
|
|
397
|
+
return result;
|
|
398
|
+
};
|
|
399
|
+
|
|
400
|
+
/**
|
|
401
|
+
* Resolve user-registered extensions and the built-in BpmnIO extension for an activity.
|
|
402
|
+
* Returns undefined when the activity has no extensions to attach.
|
|
403
|
+
* @param {import('#types').ElementBase} activity
|
|
404
|
+
* @returns {import('#types').IExtension | undefined}
|
|
405
|
+
*/
|
|
230
406
|
ContextInstance.prototype.loadExtensions = function loadExtensions(activity) {
|
|
231
407
|
const io = new BpmnIO(activity, this);
|
|
232
408
|
const extensions = this.extensionsMapper.get(activity);
|
|
@@ -235,8 +411,12 @@ ContextInstance.prototype.loadExtensions = function loadExtensions(activity) {
|
|
|
235
411
|
return extensions;
|
|
236
412
|
};
|
|
237
413
|
|
|
414
|
+
/**
|
|
415
|
+
* Resolve the parent process or sub-process activity that owns the given activity.
|
|
416
|
+
* @param {string} activityId
|
|
417
|
+
*/
|
|
238
418
|
ContextInstance.prototype.getActivityParentById = function getActivityParentById(activityId) {
|
|
239
|
-
const owner = this[
|
|
419
|
+
const owner = this[K_OWNER];
|
|
240
420
|
if (owner) return owner;
|
|
241
421
|
const activity = this.getActivityById(activityId);
|
|
242
422
|
const parentId = activity.parent.id;
|
|
@@ -251,6 +431,7 @@ ExtensionsMapper.prototype.get = function get(activity) {
|
|
|
251
431
|
return new Extensions(activity, this.context, this._getExtensions());
|
|
252
432
|
};
|
|
253
433
|
|
|
434
|
+
/** @internal */
|
|
254
435
|
ExtensionsMapper.prototype._getExtensions = function getExtensions() {
|
|
255
436
|
let extensions;
|
|
256
437
|
if (!(extensions = this.context.environment.extensions)) return [];
|
|
@@ -263,7 +444,7 @@ function Extensions(activity, context, extensions) {
|
|
|
263
444
|
const extension = Extension(activity, context);
|
|
264
445
|
if (extension) result.push(extension);
|
|
265
446
|
}
|
|
266
|
-
this[
|
|
447
|
+
this[K_ACTIVATED] = false;
|
|
267
448
|
}
|
|
268
449
|
|
|
269
450
|
Object.defineProperty(Extensions.prototype, 'count', {
|
|
@@ -273,13 +454,13 @@ Object.defineProperty(Extensions.prototype, 'count', {
|
|
|
273
454
|
});
|
|
274
455
|
|
|
275
456
|
Extensions.prototype.activate = function activate(message) {
|
|
276
|
-
if (this[
|
|
277
|
-
this[
|
|
457
|
+
if (this[K_ACTIVATED]) return;
|
|
458
|
+
this[K_ACTIVATED] = true;
|
|
278
459
|
for (const extension of this.extensions) extension.activate(message);
|
|
279
460
|
};
|
|
280
461
|
|
|
281
462
|
Extensions.prototype.deactivate = function deactivate(message) {
|
|
282
|
-
if (!this[
|
|
283
|
-
this[
|
|
463
|
+
if (!this[K_ACTIVATED]) return;
|
|
464
|
+
this[K_ACTIVATED] = false;
|
|
284
465
|
for (const extension of this.extensions) extension.deactivate(message);
|
|
285
466
|
};
|
package/src/Environment.js
CHANGED
|
@@ -1,69 +1,96 @@
|
|
|
1
|
-
import Expressions from './Expressions.js';
|
|
1
|
+
import { Expressions } from './Expressions.js';
|
|
2
2
|
import { Scripts } from './Scripts.js';
|
|
3
3
|
import { Timers } from './Timers.js';
|
|
4
4
|
|
|
5
|
-
const
|
|
6
|
-
const
|
|
5
|
+
const K_SERVICES = Symbol.for('services');
|
|
6
|
+
const K_VARIABLES = Symbol.for('variables');
|
|
7
7
|
|
|
8
8
|
const defaultOptions = new Set(['expressions', 'extensions', 'Logger', 'output', 'scripts', 'services', 'settings', 'timers', 'variables']);
|
|
9
9
|
|
|
10
|
-
|
|
10
|
+
/**
|
|
11
|
+
* Holds global execution config: variables, injected services, timers, scripts engine,
|
|
12
|
+
* expressions, Logger factory, and settings such as `batchSize`. Cloned and merged per Definition.
|
|
13
|
+
* @param {import('#types').EnvironmentOptions} [options]
|
|
14
|
+
*/
|
|
15
|
+
export function Environment(options = {}) {
|
|
11
16
|
this.options = validateOptions(options);
|
|
12
17
|
|
|
18
|
+
/** @type {import('#types').IExpressions} */
|
|
13
19
|
this.expressions = options.expressions || Expressions();
|
|
14
20
|
this.extensions = options.extensions;
|
|
15
21
|
this.output = options.output || {};
|
|
22
|
+
/** @type {import('#types').IScripts} */
|
|
16
23
|
this.scripts = options.scripts || new Scripts();
|
|
24
|
+
/** @type {import('#types').ITimers} */
|
|
17
25
|
this.timers = options.timers || new Timers();
|
|
26
|
+
/** @type {import('#types').EnvironmentSettings} */
|
|
18
27
|
this.settings = { ...options.settings };
|
|
28
|
+
/** @type {import('#types').LoggerFactory} */
|
|
19
29
|
this.Logger = options.Logger || DummyLogger;
|
|
20
|
-
this[
|
|
21
|
-
this[
|
|
30
|
+
this[K_SERVICES] = options.services || {};
|
|
31
|
+
this[K_VARIABLES] = options.variables || {};
|
|
22
32
|
}
|
|
23
33
|
|
|
24
|
-
Object.
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
},
|
|
34
|
+
Object.defineProperty(Environment.prototype, 'variables', {
|
|
35
|
+
/** @returns {Record<string, any>} */
|
|
36
|
+
get() {
|
|
37
|
+
return this[K_VARIABLES];
|
|
29
38
|
},
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
39
|
+
});
|
|
40
|
+
|
|
41
|
+
Object.defineProperty(Environment.prototype, 'services', {
|
|
42
|
+
/** @returns {Record<string, CallableFunction>} */
|
|
43
|
+
get() {
|
|
44
|
+
return this[K_SERVICES];
|
|
45
|
+
},
|
|
46
|
+
set(value) {
|
|
47
|
+
const services = this[K_SERVICES];
|
|
48
|
+
for (const name in services) {
|
|
49
|
+
if (!(name in value)) delete services[name];
|
|
50
|
+
}
|
|
51
|
+
Object.assign(services, value);
|
|
41
52
|
},
|
|
42
53
|
});
|
|
43
54
|
|
|
55
|
+
/**
|
|
56
|
+
* Snapshot environment state for recover.
|
|
57
|
+
* @returns {import('#types').EnvironmentState}
|
|
58
|
+
*/
|
|
44
59
|
Environment.prototype.getState = function getState() {
|
|
45
60
|
return {
|
|
46
61
|
settings: { ...this.settings },
|
|
47
|
-
variables: { ...this[
|
|
62
|
+
variables: { ...this[K_VARIABLES] },
|
|
48
63
|
output: { ...this.output },
|
|
49
64
|
};
|
|
50
65
|
};
|
|
51
66
|
|
|
67
|
+
/**
|
|
68
|
+
* Restore environment state captured by getState. Merges into the existing settings,
|
|
69
|
+
* variables, and output rather than replacing them.
|
|
70
|
+
* @param {import('#types').EnvironmentState} [state]
|
|
71
|
+
* @returns {this}
|
|
72
|
+
*/
|
|
52
73
|
Environment.prototype.recover = function recover(state) {
|
|
53
74
|
if (!state) return this;
|
|
54
75
|
|
|
55
76
|
if (state.settings) Object.assign(this.settings, state.settings);
|
|
56
|
-
if (state.variables) Object.assign(this[
|
|
77
|
+
if (state.variables) Object.assign(this[K_VARIABLES], state.variables);
|
|
57
78
|
if (state.output) Object.assign(this.output, state.output);
|
|
58
79
|
|
|
59
80
|
return this;
|
|
60
81
|
};
|
|
61
82
|
|
|
83
|
+
/**
|
|
84
|
+
* Clone the environment, optionally overriding options. Services are merged when
|
|
85
|
+
* `overrideOptions.services` is supplied.
|
|
86
|
+
* @param {import('#types').EnvironmentOptions} [overrideOptions]
|
|
87
|
+
* @returns {Environment}
|
|
88
|
+
*/
|
|
62
89
|
Environment.prototype.clone = function clone(overrideOptions) {
|
|
63
|
-
const services = this[
|
|
90
|
+
const services = this[K_SERVICES];
|
|
64
91
|
const newOptions = {
|
|
65
92
|
settings: { ...this.settings },
|
|
66
|
-
variables: { ...this[
|
|
93
|
+
variables: { ...this[K_VARIABLES] },
|
|
67
94
|
Logger: this.Logger,
|
|
68
95
|
extensions: this.extensions,
|
|
69
96
|
scripts: this.scripts,
|
|
@@ -79,36 +106,66 @@ Environment.prototype.clone = function clone(overrideOptions) {
|
|
|
79
106
|
return new this.constructor(newOptions);
|
|
80
107
|
};
|
|
81
108
|
|
|
109
|
+
/**
|
|
110
|
+
* Merge variables into the environment. Non-objects are ignored.
|
|
111
|
+
* @param {Record<string, any>} newVars
|
|
112
|
+
*/
|
|
82
113
|
Environment.prototype.assignVariables = function assignVariables(newVars) {
|
|
83
114
|
if (!newVars || typeof newVars !== 'object') return;
|
|
84
115
|
|
|
85
|
-
this[
|
|
116
|
+
this[K_VARIABLES] = {
|
|
86
117
|
...this.variables,
|
|
87
118
|
...newVars,
|
|
88
119
|
};
|
|
89
120
|
};
|
|
90
121
|
|
|
122
|
+
/**
|
|
123
|
+
* Merge settings into the environment. Non-objects are ignored.
|
|
124
|
+
* @param {import('#types').EnvironmentSettings} newSettings
|
|
125
|
+
* @returns {this}
|
|
126
|
+
*/
|
|
91
127
|
Environment.prototype.assignSettings = function assignSettings(newSettings) {
|
|
92
|
-
if (!newSettings || typeof newSettings !== 'object') return;
|
|
128
|
+
if (!newSettings || typeof newSettings !== 'object') return this;
|
|
93
129
|
|
|
94
130
|
this.settings = {
|
|
95
131
|
...this.settings,
|
|
96
132
|
...newSettings,
|
|
97
133
|
};
|
|
134
|
+
|
|
135
|
+
return this;
|
|
98
136
|
};
|
|
99
137
|
|
|
138
|
+
/**
|
|
139
|
+
* Resolve a registered script by language and identifier.
|
|
140
|
+
* @param {string} language
|
|
141
|
+
* @param {{ id: string, [x: string]: any }} identifier
|
|
142
|
+
*/
|
|
100
143
|
Environment.prototype.getScript = function getScript(...args) {
|
|
101
144
|
return this.scripts.getScript(...args);
|
|
102
145
|
};
|
|
103
146
|
|
|
147
|
+
/**
|
|
148
|
+
* Register a script for an activity, delegating to the configured scripts engine.
|
|
149
|
+
* @param {any} activity
|
|
150
|
+
*/
|
|
104
151
|
Environment.prototype.registerScript = function registerScript(...args) {
|
|
105
152
|
return this.scripts.register(...args);
|
|
106
153
|
};
|
|
107
154
|
|
|
155
|
+
/**
|
|
156
|
+
* Lookup a registered service by name.
|
|
157
|
+
* @param {string} serviceName
|
|
158
|
+
*/
|
|
108
159
|
Environment.prototype.getServiceByName = function getServiceByName(serviceName) {
|
|
109
|
-
return this[
|
|
160
|
+
return this[K_SERVICES][serviceName];
|
|
110
161
|
};
|
|
111
162
|
|
|
163
|
+
/**
|
|
164
|
+
* Resolve an expression with the environment as scope, optionally extended by an element message.
|
|
165
|
+
* @param {string} expression
|
|
166
|
+
* @param {import('#types').ElementBrokerMessage} [message] Element message merged onto the resolution scope
|
|
167
|
+
* @param {any} [expressionFnContext]
|
|
168
|
+
*/
|
|
112
169
|
Environment.prototype.resolveExpression = function resolveExpression(expression, message, expressionFnContext) {
|
|
113
170
|
const from = {
|
|
114
171
|
environment: this,
|
|
@@ -118,10 +175,19 @@ Environment.prototype.resolveExpression = function resolveExpression(expression,
|
|
|
118
175
|
return this.expressions.resolveExpression(expression, from, expressionFnContext);
|
|
119
176
|
};
|
|
120
177
|
|
|
178
|
+
/**
|
|
179
|
+
* Register a service callable by name.
|
|
180
|
+
* @param {string} name service function name
|
|
181
|
+
* @param {CallableFunction} fn service function
|
|
182
|
+
*/
|
|
121
183
|
Environment.prototype.addService = function addService(name, fn) {
|
|
122
|
-
this[
|
|
184
|
+
this[K_SERVICES][name] = fn;
|
|
123
185
|
};
|
|
124
186
|
|
|
187
|
+
/**
|
|
188
|
+
* @param {import('#types').EnvironmentOptions} input
|
|
189
|
+
* @returns {import('#types').EnvironmentOptions} validated options
|
|
190
|
+
*/
|
|
125
191
|
function validateOptions(input) {
|
|
126
192
|
const options = {};
|
|
127
193
|
for (const key in input) {
|
|
@@ -151,6 +217,9 @@ function validateOptions(input) {
|
|
|
151
217
|
return options;
|
|
152
218
|
}
|
|
153
219
|
|
|
220
|
+
/**
|
|
221
|
+
* @returns {import('#types').ILogger}
|
|
222
|
+
*/
|
|
154
223
|
function DummyLogger() {
|
|
155
224
|
return {
|
|
156
225
|
debug,
|