@onify/flow-extensions 7.1.0 → 8.0.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1 @@
1
+ import './types/index.js';
package/README.md CHANGED
@@ -11,10 +11,14 @@
11
11
 
12
12
  ## Bpmn engine example
13
13
 
14
- ```js
15
- const { Engine } = require('bpmn-engine');
16
- const { extensions } = require('@onify/flow-extensions');
17
- const FlowScripts = require('@onify/flow-extensions/dist/src/FlowScripts');
14
+ ```javascript
15
+ import { createRequire } from 'node:module';
16
+ import { fileURLToPath } from 'node:url';
17
+ import { Engine } from 'bpmn-engine';
18
+ import { extensions } from '@onify/flow-extensions';
19
+ import { FlowScripts } from '@onify/flow-extensions/FlowScripts';
20
+
21
+ const nodeRequire = createRequire(fileURLToPath(import.meta.url));
18
22
 
19
23
  const source = `
20
24
  <definitions xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL"
@@ -23,7 +27,7 @@ const source = `
23
27
  <process id="theProcess" isExecutable="true">
24
28
  <serviceTask id="task1" camunda:expression="\${environment.services.serviceFn}" camunda:resultVariable="result" />
25
29
  <sequenceFlow id="to-task2" sourceRef="task1" targetRef="task2" />
26
- <scriptTask id="task2" camunda:resultVariable="out">
30
+ <scriptTask id="task2" camunda:resultVariable="out" scriptFormat="js">
27
31
  <script>
28
32
  next(null, myContextFn());
29
33
  </script>
@@ -36,7 +40,7 @@ const engine = new Engine({
36
40
  name,
37
41
  source,
38
42
  moddleOptions: {
39
- camunda: require('camunda-bpmn-moddle/resources/camunda.json'),
43
+ camunda: nodeRequire('camunda-bpmn-moddle/resources/camunda.json'),
40
44
  },
41
45
  services: {
42
46
  serviceFn(scope, callback) {
@@ -61,12 +65,15 @@ engine.execute((err, instance) => {
61
65
 
62
66
  ## Extract scripts with extend function
63
67
 
64
- ```js
65
- const { extendFn } = require('@onify/flow-extensions');
68
+ ```javascript
69
+ import { createRequire } from 'node:module';
70
+ import { fileURLToPath } from 'node:url';
71
+ import BpmnModdle from 'bpmn-moddle';
72
+ import * as Elements from 'bpmn-elements';
73
+ import { Serializer, TypeResolver } from 'moddle-context-serializer';
74
+ import { extendFn } from '@onify/flow-extensions';
66
75
 
67
- const BpmnModdle = require('bpmn-moddle');
68
- const Elements = require('bpmn-elements');
69
- const { default: Serializer, TypeResolver } = require('moddle-context-serializer');
76
+ const nodeRequire = createRequire(fileURLToPath(import.meta.url));
70
77
 
71
78
  const source = `
72
79
  <definitions id="Def_0" xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL"
@@ -97,7 +104,7 @@ const source = `
97
104
  </extensionElements>
98
105
  </serviceTask>
99
106
  <sequenceFlow id="to-task2" sourceRef="task1" targetRef="task2" />
100
- <scriptTask id="task2" camunda:resultVariable="out">
107
+ <scriptTask id="task2" camunda:resultVariable="out" scriptFormat="js">
101
108
  <script>
102
109
  next(null, 2);
103
110
  </script>
@@ -105,14 +112,85 @@ const source = `
105
112
  </process>
106
113
  </definitions>`;
107
114
 
108
- (async () => {
109
- const moddle = await getModdleContext(source, {
110
- camunda: require('camunda-bpmn-moddle/resources/camunda.json'),
115
+ getScripts(source).then(console.log).catch(console.error);
116
+
117
+ async function getScripts(bpmnSource) {
118
+ const moddle = await getModdleContext(bpmnSource, {
119
+ camunda: nodeRequire('camunda-bpmn-moddle/resources/camunda.json'),
111
120
  });
112
121
 
113
122
  const serialized = Serializer(moddle, TypeResolver(Elements), extendFn);
114
- console.log(serialized.elements.scripts);
115
- })();
123
+ return serialized.elements.scripts;
124
+ }
125
+
126
+ function getModdleContext(source, options) {
127
+ const bpmnModdle = new BpmnModdle(options);
128
+ return bpmnModdle.fromXML(Buffer.isBuffer(source) ? source.toString() : source.trim());
129
+ }
130
+ ```
131
+
132
+ ## Extract timers
133
+
134
+ ```javascript
135
+ import { createRequire } from 'node:module';
136
+ import { fileURLToPath } from 'node:url';
137
+ import BpmnModdle from 'bpmn-moddle';
138
+ import * as Elements from 'bpmn-elements';
139
+ import { Serializer, TypeResolver } from 'moddle-context-serializer';
140
+ import { extendFn, OnifyTimerEventDefinition } from '@onify/flow-extensions';
141
+
142
+ const nodeRequire = createRequire(fileURLToPath(import.meta.url));
143
+
144
+ const source = `
145
+ <definitions id="Def_0" xmlns="http://www.omg.org/spec/BPMN/20100524/MODEL"
146
+ xmlns:camunda="http://camunda.org/schema/1.0/bpmn"
147
+ xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance"
148
+ targetNamespace="http://bpmn.io/schema/bpmn">
149
+ <process id="cycle-1" name="Onify start at time cycle" isExecutable="true" camunda:historyTimeToLive="PT180M">
150
+ <startEvent id="start">
151
+ <timerEventDefinition>
152
+ <timeCycle xsi:type="tFormalExpression">0 1 * * *</timeCycle>
153
+ </timerEventDefinition>
154
+ </startEvent>
155
+ <sequenceFlow id="to-task" sourceRef="start" targetRef="task" />
156
+ <userTask id="task" />
157
+ <boundaryEvent id="bound-timer" cancelActivity="false" attachedToRef="task">
158
+ <timerEventDefinition>
159
+ <timeDuration xsi:type="tFormalExpression">R3/PT1M</timeDuration>
160
+ </timerEventDefinition>
161
+ </boundaryEvent>
162
+ <sequenceFlow id="to-wait" sourceRef="task" targetRef="wait" />
163
+ <intermediateThrowEvent id="timer">
164
+ <timerEventDefinition>
165
+ <timeCycle xsi:type="tFormalExpression">\${environment.settings.postpone}</timeCycle>
166
+ </timerEventDefinition>
167
+ </intermediateThrowEvent>
168
+ <sequenceFlow id="to-end" sourceRef="wait" targetRef="end" />
169
+ <endEvent id="end" />
170
+ </process>
171
+ </definitions>`;
172
+
173
+ getTimers(source).then(console.log).catch(console.error);
174
+
175
+ const dummyEventActivity = { broker: {}, environment: { Logger() {} } };
176
+
177
+ async function getTimers(bpmnSource) {
178
+ const moddle = await getModdleContext(bpmnSource, {
179
+ camunda: nodeRequire('camunda-bpmn-moddle/resources/camunda.json'),
180
+ });
181
+
182
+ const serialized = Serializer(moddle, TypeResolver(Elements), extendFn);
183
+
184
+ for (const t of serialized.elements.timers) {
185
+ const ed = new OnifyTimerEventDefinition(dummyEventActivity, t.timer);
186
+
187
+ try {
188
+ t.parsed = ed.parse(t.timer.timerType, t.timer.value);
189
+ } catch {}
190
+ }
191
+
192
+ return serialized.elements.timers;
193
+ }
116
194
 
117
195
  function getModdleContext(source, options) {
118
196
  const bpmnModdle = new BpmnModdle(options);
@@ -122,11 +200,15 @@ function getModdleContext(source, options) {
122
200
 
123
201
  ## Extend sequence flow with properties and take listeners
124
202
 
125
- ```js
126
- const { OnifySequenceFlow, extensions } = require('@onify/flow-extensions');
127
- const FlowScripts = require('@onify/flow-extensions/dist/src/FlowScripts');
128
- const { Engine } = require('bpmn-engine');
129
- const Elements = require('bpmn-elements');
203
+ ```javascript
204
+ import { createRequire } from 'node:module';
205
+ import { fileURLToPath } from 'node:url';
206
+ import { Engine } from 'bpmn-engine';
207
+ import * as Elements from 'bpmn-elements';
208
+ import { OnifySequenceFlow, extensions } from '@onify/flow-extensions';
209
+ import { FlowScripts } from '@onify/flow-extensions/FlowScripts';
210
+
211
+ const nodeRequire = createRequire(fileURLToPath(import.meta.url));
130
212
 
131
213
  const source = `
132
214
  <?xml version="1.0" encoding="UTF-8"?>
@@ -191,7 +273,7 @@ const engine = new Engine({
191
273
  name: 'sequence flow extension',
192
274
  source,
193
275
  moddleOptions: {
194
- camunda: require('camunda-bpmn-moddle/resources/camunda.json'),
276
+ camunda: nodeRequire('camunda-bpmn-moddle/resources/camunda.json'),
195
277
  },
196
278
  extensions: {
197
279
  onify: extensions,
@@ -201,6 +283,11 @@ const engine = new Engine({
201
283
  ...Elements,
202
284
  SequenceFlow: OnifySequenceFlow,
203
285
  },
286
+ variables: {
287
+ required: {
288
+ input: true,
289
+ },
290
+ },
204
291
  });
205
292
 
206
293
  engine.execute((err, instance) => {
package/dist/Connector.js CHANGED
@@ -30,7 +30,7 @@ Connector.prototype.execute = async function execute(...args) {
30
30
  }
31
31
  async function formatCallback(serviceErr, result) {
32
32
  if (serviceErr) return callback(serviceErr);
33
- if (!(io !== null && io !== void 0 && io.output.length)) return callback(null, result);
33
+ if (!io?.output.length) return callback(null, result);
34
34
  try {
35
35
  const formattedResult = await io.getOutput(activity, {
36
36
  ...executionMessage,
@@ -38,7 +38,7 @@ class Listener {
38
38
  }
39
39
  _getFields(environment, scope) {
40
40
  const fields = this.extension.fields;
41
- if (!(fields !== null && fields !== void 0 && fields.length)) return;
41
+ if (!fields?.length) return;
42
42
  const result = {};
43
43
  for (const {
44
44
  name,
@@ -105,7 +105,7 @@ FlowScripts.prototype.getScript = function getScript(scriptType, {
105
105
  function JavaScript(flowName, scriptBody, runContext, options) {
106
106
  this.flowName = flowName;
107
107
  this._runContext = runContext;
108
- this.timeout = options === null || options === void 0 ? void 0 : options.timeout;
108
+ this.timeout = options?.timeout;
109
109
  try {
110
110
  this.script = new _vm.Script(scriptBody, options);
111
111
  } catch (err) {
@@ -28,7 +28,7 @@ class OnifyBoundaryEventExtensions extends _OnifyElementExtensions.OnifyElementE
28
28
  }, {
29
29
  consumerTag: '_onify-extension-on-executed'
30
30
  });
31
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onStart) {
31
+ if (executionListeners?.onStart) {
32
32
  activity.on('start', async elementApi => {
33
33
  try {
34
34
  await executionListeners.execute('start', elementApi);
@@ -39,7 +39,7 @@ class OnifyBoundaryEventExtensions extends _OnifyElementExtensions.OnifyElementE
39
39
  consumerTag: '_onify-extension-on-listenerstart'
40
40
  });
41
41
  }
42
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onEnd) {
42
+ if (executionListeners?.onEnd) {
43
43
  activity.on('end', elementApi => {
44
44
  this._executeExecutionListener('end', elementApi, formatQ);
45
45
  }, {
@@ -62,7 +62,6 @@ class OnifyBoundaryEventExtensions extends _OnifyElementExtensions.OnifyElementE
62
62
  });
63
63
  }
64
64
  _onEnterSync(elementApi) {
65
- var _io$output;
66
65
  const {
67
66
  format,
68
67
  properties,
@@ -77,7 +76,7 @@ class OnifyBoundaryEventExtensions extends _OnifyElementExtensions.OnifyElementE
77
76
  });
78
77
  Object.assign(elementApi.content, result);
79
78
  }
80
- if (io !== null && io !== void 0 && (_io$output = io.output) !== null && _io$output !== void 0 && _io$output.length) {
79
+ if (io?.output?.length) {
81
80
  result.assignToOutput = true;
82
81
  }
83
82
  return result;
@@ -35,14 +35,14 @@ class OnifyElementExtensions {
35
35
  }, {
36
36
  consumerTag: '_onify-extension-on-executed'
37
37
  });
38
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onStart) {
38
+ if (executionListeners?.onStart) {
39
39
  activity.on('start', elementApi => {
40
40
  this._executeExecutionListener('start', elementApi);
41
41
  }, {
42
42
  consumerTag: '_onify-extension-on-listenerstart'
43
43
  });
44
44
  }
45
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onEnd) {
45
+ if (executionListeners?.onEnd) {
46
46
  activity.on('end', elementApi => {
47
47
  this._executeExecutionListener('end', elementApi);
48
48
  }, {
@@ -118,15 +118,14 @@ class OnifyElementExtensions {
118
118
  Object.assign(elementApi.content, result);
119
119
  }
120
120
  if (io) {
121
- var _io$input, _io$output;
122
- if ((_io$input = io.input) !== null && _io$input !== void 0 && _io$input.length) {
121
+ if (io.input?.length) {
123
122
  const input = await io.getInput(this.activity, elementApi);
124
123
  Object.assign(result, {
125
124
  input
126
125
  });
127
126
  Object.assign(elementApi.content, result);
128
127
  }
129
- if ((_io$output = io.output) !== null && _io$output !== void 0 && _io$output.length) {
128
+ if (io.output?.length) {
130
129
  result.assignToOutput = true;
131
130
  }
132
131
  }
@@ -143,7 +142,7 @@ class OnifyElementExtensions {
143
142
  io
144
143
  } = this.extensions;
145
144
  const result = {};
146
- if (io !== null && io !== void 0 && io.output.length) {
145
+ if (io?.output.length) {
147
146
  const output = await io.getOutput(this.activity, elementApi);
148
147
  Object.assign(result, {
149
148
  output
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+
3
+ var _ScriptTask = require("bpmn-elements/tasks/ScriptTask.js");
@@ -13,8 +13,7 @@ class OnifySequenceFlow extends _bpmnElements.SequenceFlow {
13
13
  this._activate();
14
14
  }
15
15
  _activate() {
16
- var _this$extensions$list;
17
- if (!((_this$extensions$list = this.extensions.listeners) !== null && _this$extensions$list !== void 0 && _this$extensions$list.onTake)) return;
16
+ if (!this.extensions.listeners?.onTake) return;
18
17
  this.broker.subscribeTmp('event', 'flow.take', (_, msg) => {
19
18
  this._executeListeners(msg);
20
19
  }, {
@@ -32,14 +31,24 @@ class OnifySequenceFlow extends _bpmnElements.SequenceFlow {
32
31
  evaluate(fromMessage, callback) {
33
32
  const properties = this.extensions.properties;
34
33
  if (!properties) return super.evaluate(fromMessage, callback);
35
- super.evaluate(fromMessage, (err, result) => {
34
+ try {
35
+ const preProperties = properties.resolve(this.getApi(fromMessage));
36
+ var evaluateMessage = fromMessage;
37
+ evaluateMessage.content.properties = {
38
+ ...fromMessage.content.properties,
39
+ ...preProperties
40
+ };
41
+ } catch (err) {
42
+ return callback(err);
43
+ }
44
+ super.evaluate(evaluateMessage, (err, result) => {
36
45
  if (err) return callback(err);
37
46
  try {
38
47
  let overriddenResult = result ? {} : false;
39
48
  if (result) {
40
49
  overriddenResult = {
41
50
  ...(typeof result === 'object' && result),
42
- properties: properties.resolve(this.getApi(fromMessage))
51
+ properties: properties.resolve(this.getApi(evaluateMessage))
43
52
  };
44
53
  }
45
54
  return callback(err, overriddenResult);
@@ -25,12 +25,12 @@ class OnifySubProcessExtensions extends _OnifyElementExtensions.OnifyElementExte
25
25
  this._setupListener(broker, 'activity.execution.completed', elementApi => {
26
26
  return this._onExecutionCompleted(elementApi);
27
27
  }, '_onify-extension-on-executed');
28
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onStart) {
28
+ if (executionListeners?.onStart) {
29
29
  this._setupListener(broker, 'activity.start', elementApi => {
30
30
  this._executeExecutionListener('start', elementApi);
31
31
  }, '_onify-extension-on-listenerstart');
32
32
  }
33
- if (executionListeners !== null && executionListeners !== void 0 && executionListeners.onEnd) {
33
+ if (executionListeners?.onEnd) {
34
34
  this._setupListener(broker, 'activity.end', elementApi => {
35
35
  this._executeExecutionListener('end', elementApi);
36
36
  }, '_onify-extension-on-listenerend');
@@ -4,8 +4,8 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.OnifyTimerEventDefinition = void 0;
7
- var _bpmnElements = require("bpmn-elements");
8
7
  var _cronParser = _interopRequireDefault(require("cron-parser"));
8
+ var _bpmnElements = require("bpmn-elements");
9
9
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
10
10
  class OnifyTimerEventDefinition extends _bpmnElements.TimerEventDefinition {
11
11
  constructor(activity, def) {
@@ -17,8 +17,7 @@ class OnifyTimerEventDefinition extends _bpmnElements.TimerEventDefinition {
17
17
  parse(timerType, value) {
18
18
  let cron;
19
19
  if (timerType === 'timeCycle' && (cron = _cronParser.default.parseString(value))) {
20
- var _cron$expressions;
21
- if ((_cron$expressions = cron.expressions) !== null && _cron$expressions !== void 0 && _cron$expressions.length) {
20
+ if (cron.expressions?.length) {
22
21
  // cronParser.parseString expressions disregards seconds, so we have to parse again
23
22
  const expireAt = _cronParser.default.parseExpression(value).next().toDate();
24
23
  return {
@@ -4,9 +4,6 @@ Object.defineProperty(exports, "__esModule", {
4
4
  value: true
5
5
  });
6
6
  exports.FormatProcess = exports.FormatActivity = void 0;
7
- var _cronParser = _interopRequireDefault(require("cron-parser"));
8
- function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
9
- const iso8601cycle = /^\s*(R\d+\/)?P\w+/i;
10
7
  class FormatActivity {
11
8
  constructor(activity) {
12
9
  this.activity = activity;
@@ -14,8 +11,7 @@ class FormatActivity {
14
11
  let timeCycles;
15
12
  if (activity.eventDefinitions) {
16
13
  for (const ed of activity.eventDefinitions.filter(e => e.type === 'bpmn:TimerEventDefinition')) {
17
- var _ed$supports;
18
- if ((_ed$supports = ed.supports) !== null && _ed$supports !== void 0 && _ed$supports.includes('cron')) continue;
14
+ if (!ed.supports?.includes('cron')) continue;
19
15
  if (!('timeCycle' in ed)) continue;
20
16
  timeCycles = timeCycles || [];
21
17
  timeCycles.push(ed.timeCycle);
@@ -24,7 +20,6 @@ class FormatActivity {
24
20
  this.timeCycles = timeCycles;
25
21
  }
26
22
  resolve(elementApi) {
27
- var _documentation$, _user, _groups;
28
23
  let user, groups, assigneeValue, description;
29
24
  const activity = this.activity;
30
25
  const {
@@ -37,17 +32,7 @@ class FormatActivity {
37
32
  if (candidateUsers) user = resolveAndSplit(elementApi, candidateUsers);
38
33
  if (candidateGroups) groups = resolveAndSplit(elementApi, candidateGroups);
39
34
  if (assignee) assigneeValue = elementApi.resolveExpression(assignee);
40
- if (documentation) description = (_documentation$ = documentation[0]) === null || _documentation$ === void 0 ? void 0 : _documentation$.text;
41
- let expireAt;
42
- const timeCycles = this.timeCycles;
43
- if (timeCycles) {
44
- for (const cycle of timeCycles) {
45
- const cron = elementApi.resolveExpression(cycle);
46
- if (!cron || iso8601cycle.test(cron)) continue;
47
- const expireAtDt = _cronParser.default.parseExpression(cron).next().toDate();
48
- if (!expireAt || expireAtDt < expireAt) expireAt = expireAtDt;
49
- }
50
- }
35
+ if (documentation) description = documentation[0]?.text;
51
36
  return {
52
37
  ...(this.resultVariable && {
53
38
  resultVariable: this.resultVariable
@@ -55,18 +40,15 @@ class FormatActivity {
55
40
  ...(scheduledStart && activity.parent.type === 'bpmn:Process' && {
56
41
  scheduledStart
57
42
  }),
58
- ...(((_user = user) === null || _user === void 0 ? void 0 : _user.length) && {
43
+ ...(user?.length && {
59
44
  candidateUsers: user
60
45
  }),
61
- ...(((_groups = groups) === null || _groups === void 0 ? void 0 : _groups.length) && {
46
+ ...(groups?.length && {
62
47
  candidateGroups: groups
63
48
  }),
64
49
  ...(!elementApi.content.description && description && {
65
50
  description: elementApi.resolveExpression(description)
66
51
  }),
67
- ...(expireAt && {
68
- expireAt
69
- }),
70
52
  ...(assigneeValue && {
71
53
  assignee: assigneeValue
72
54
  })
@@ -83,7 +65,6 @@ class FormatProcess {
83
65
  }
84
66
  }
85
67
  resolve(elementApi) {
86
- var _documentation$2, _user2, _groups2;
87
68
  let user, groups, description;
88
69
  const bp = this.process;
89
70
  const {
@@ -93,12 +74,12 @@ class FormatProcess {
93
74
  } = bp.behaviour;
94
75
  if (candidateStarterUsers) user = resolveAndSplit(elementApi, candidateStarterUsers);
95
76
  if (candidateStarterGroups) groups = resolveAndSplit(elementApi, candidateStarterGroups);
96
- if (documentation) description = (_documentation$2 = documentation[0]) === null || _documentation$2 === void 0 ? void 0 : _documentation$2.text;
77
+ if (documentation) description = documentation[0]?.text;
97
78
  return {
98
- ...(((_user2 = user) === null || _user2 === void 0 ? void 0 : _user2.length) && {
79
+ ...(user?.length && {
99
80
  candidateStarterUsers: user
100
81
  }),
101
- ...(((_groups2 = groups) === null || _groups2 === void 0 ? void 0 : _groups2.length) && {
82
+ ...(groups?.length && {
102
83
  candidateStarterGroups: groups
103
84
  }),
104
85
  ...(!elementApi.content.description && description && {
@@ -13,7 +13,6 @@ var _IOProperties = _interopRequireDefault(require("./IOProperties.js"));
13
13
  var _ServiceExpression = _interopRequireDefault(require("./ServiceExpression.js"));
14
14
  function _interopRequireDefault(obj) { return obj && obj.__esModule ? obj : { default: obj }; }
15
15
  function getExtensions(element, context) {
16
- var _element$behaviour$ex, _ext$values, _ext$fields;
17
16
  const result = {};
18
17
  switch (element.type) {
19
18
  case 'bpmn:SequenceFlow':
@@ -28,18 +27,18 @@ function getExtensions(element, context) {
28
27
  const listeners = new _ExecutionListeners.default(element, context);
29
28
  const expression = element.behaviour.expression;
30
29
  if (expression) result.Service = _ServiceExpression.default;
31
- const extensions = (_element$behaviour$ex = element.behaviour.extensionElements) === null || _element$behaviour$ex === void 0 ? void 0 : _element$behaviour$ex.values;
30
+ const extensions = element.behaviour.extensionElements?.values;
32
31
  if (extensions) {
33
32
  for (const ext of extensions) {
34
33
  switch (ext.$type) {
35
34
  case 'camunda:Properties':
36
- if ((_ext$values = ext.values) !== null && _ext$values !== void 0 && _ext$values.length) result.properties = new _IOProperties.default(element, ext);
35
+ if (ext.values?.length) result.properties = new _IOProperties.default(element, ext);
37
36
  break;
38
37
  case 'camunda:InputOutput':
39
38
  result.io = new _IO.InputOutput(element.id, ext, context);
40
39
  break;
41
40
  case 'camunda:FormData':
42
- if ((_ext$fields = ext.fields) !== null && _ext$fields !== void 0 && _ext$fields.length) result.form = new _IOForm.default(element, ext);
41
+ if (ext.fields?.length) result.form = new _IOForm.default(element, ext);
43
42
  break;
44
43
  case 'camunda:Connector':
45
44
  {
package/dist/index.js CHANGED
@@ -37,7 +37,6 @@ function extensions(element, context) {
37
37
  }
38
38
  }
39
39
  function extendFn(behaviour, context) {
40
- var _behaviour$extensionE;
41
40
  switch (behaviour.$type) {
42
41
  case 'bpmn:StartEvent':
43
42
  {
@@ -64,7 +63,7 @@ function extendFn(behaviour, context) {
64
63
  break;
65
64
  }
66
65
  }
67
- if (!Array.isArray((_behaviour$extensionE = behaviour.extensionElements) === null || _behaviour$extensionE === void 0 ? void 0 : _behaviour$extensionE.values)) return;
66
+ if (!Array.isArray(behaviour.extensionElements?.values)) return;
68
67
  let listener = 0;
69
68
  for (const extension of behaviour.extensionElements.values) {
70
69
  switch (extension.$type) {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@onify/flow-extensions",
3
- "version": "7.1.0",
3
+ "version": "8.0.1",
4
4
  "description": "Onify Flow extensions",
5
5
  "type": "module",
6
6
  "module": "src/index.js",
@@ -8,8 +8,16 @@
8
8
  "types": "./index.d.ts",
9
9
  "sideEffects": false,
10
10
  "exports": {
11
- "import": "./src/index.js",
12
- "require": "./dist/index.js"
11
+ ".": {
12
+ "types": "./types/index.d.ts",
13
+ "require": "./dist/index.js",
14
+ "import": "./src/index.js"
15
+ },
16
+ "./FlowScripts": {
17
+ "types": "./types/index.d.ts",
18
+ "require": "./dist/FlowScripts.js",
19
+ "import": "./dist/FlowScripts.js"
20
+ }
13
21
  },
14
22
  "scripts": {
15
23
  "test": "mocha -R dot",
@@ -17,6 +25,7 @@
17
25
  "lint": "eslint . --cache && prettier . --check --cache",
18
26
  "prepare": "npm run dist",
19
27
  "dist": "babel src -d dist && babel test/helpers/FlowScripts.js -d dist",
28
+ "test:md": "node --experimental-vm-modules --no-warnings scripts/test-markdown.js ./README.md",
20
29
  "test:lcov": "c8 -r lcov mocha && npm run lint",
21
30
  "cov:html": "c8 mocha -R dot && c8 report --reporter html"
22
31
  },
@@ -38,36 +47,38 @@
38
47
  "license": "MIT",
39
48
  "devDependencies": {
40
49
  "@aircall/expression-parser": "^1.0.4",
41
- "@babel/cli": "^7.23.4",
42
- "@babel/core": "^7.23.7",
43
- "@babel/preset-env": "^7.23.8",
50
+ "@babel/cli": "^7.23.9",
51
+ "@babel/core": "^7.23.9",
52
+ "@babel/preset-env": "^7.23.9",
44
53
  "@babel/register": "^7.23.7",
45
54
  "bpmn-elements-8-1": "npm:bpmn-elements@8.1",
46
- "bpmn-engine": "^18.0.0",
55
+ "bpmn-engine": "^20.0.1",
47
56
  "bpmn-engine-14": "npm:bpmn-engine@14",
48
- "bpmn-moddle": "^8.1.0",
57
+ "bpmn-moddle": "^9.0.1",
49
58
  "c8": "^9.1.0",
50
59
  "camunda-bpmn-moddle": "^7.0.1",
51
- "chai": "^5.0.0",
60
+ "chai": "^5.0.3",
52
61
  "chronokinesis": "^6.0.0",
53
62
  "debug": "^4.3.4",
54
- "eslint": "^8.56.0",
55
- "eslint-plugin-import": "^2.29.1",
63
+ "eslint": "^9.0.0",
56
64
  "mocha": "^10.2.0",
57
65
  "mocha-cakes-2": "^3.3.0",
58
66
  "moddle-context-serializer": "^4.1.1",
67
+ "nock": "^13.5.4",
59
68
  "prettier": "^3.2.4"
60
69
  },
61
70
  "peerDependencies": {
62
- "bpmn-elements": ">=8"
71
+ "bpmn-elements": "^14.0.0"
63
72
  },
64
73
  "dependencies": {
74
+ "@0dep/piso": "^0.1.3",
65
75
  "cron-parser": "^4.9.0"
66
76
  },
67
77
  "files": [
68
78
  "src",
69
79
  "dist",
70
- "index.d.ts"
80
+ "types",
81
+ "FlowScripts.d.ts"
71
82
  ],
72
83
  "c8": {
73
84
  "exclude": [
@@ -30,7 +30,18 @@ export class OnifySequenceFlow extends SequenceFlow {
30
30
  const properties = this.extensions.properties;
31
31
  if (!properties) return super.evaluate(fromMessage, callback);
32
32
 
33
- super.evaluate(fromMessage, (err, result) => {
33
+ try {
34
+ const preProperties = properties.resolve(this.getApi(fromMessage));
35
+ var evaluateMessage = fromMessage;
36
+ evaluateMessage.content.properties = {
37
+ ...fromMessage.content.properties,
38
+ ...preProperties,
39
+ };
40
+ } catch (err) {
41
+ return callback(err);
42
+ }
43
+
44
+ super.evaluate(evaluateMessage, (err, result) => {
34
45
  if (err) return callback(err);
35
46
 
36
47
  try {
@@ -38,7 +49,7 @@ export class OnifySequenceFlow extends SequenceFlow {
38
49
  if (result) {
39
50
  overriddenResult = {
40
51
  ...(typeof result === 'object' && result),
41
- properties: properties.resolve(this.getApi(fromMessage)),
52
+ properties: properties.resolve(this.getApi(evaluateMessage)),
42
53
  };
43
54
  }
44
55
  return callback(err, overriddenResult);
@@ -1,5 +1,5 @@
1
- import { TimerEventDefinition } from 'bpmn-elements';
2
1
  import cronParser from 'cron-parser';
2
+ import { TimerEventDefinition } from 'bpmn-elements';
3
3
 
4
4
  export class OnifyTimerEventDefinition extends TimerEventDefinition {
5
5
  constructor(activity, def) {
@@ -14,12 +14,14 @@ export class OnifyTimerEventDefinition extends TimerEventDefinition {
14
14
  if (cron.expressions?.length) {
15
15
  // cronParser.parseString expressions disregards seconds, so we have to parse again
16
16
  const expireAt = cronParser.parseExpression(value).next().toDate();
17
+
17
18
  return {
18
19
  expireAt,
19
20
  delay: expireAt - Date.now(),
20
21
  };
21
22
  }
22
23
  }
24
+
23
25
  return super.parse(timerType, value);
24
26
  }
25
27
  }
package/src/formatters.js CHANGED
@@ -1,7 +1,3 @@
1
- import cronParser from 'cron-parser';
2
-
3
- const iso8601cycle = /^\s*(R\d+\/)?P\w+/i;
4
-
5
1
  export class FormatActivity {
6
2
  constructor(activity) {
7
3
  this.activity = activity;
@@ -10,7 +6,7 @@ export class FormatActivity {
10
6
  let timeCycles;
11
7
  if (activity.eventDefinitions) {
12
8
  for (const ed of activity.eventDefinitions.filter((e) => e.type === 'bpmn:TimerEventDefinition')) {
13
- if (ed.supports?.includes('cron')) continue;
9
+ if (!ed.supports?.includes('cron')) continue;
14
10
  if (!('timeCycle' in ed)) continue;
15
11
  timeCycles = timeCycles || [];
16
12
  timeCycles.push(ed.timeCycle);
@@ -28,25 +24,12 @@ export class FormatActivity {
28
24
  if (assignee) assigneeValue = elementApi.resolveExpression(assignee);
29
25
  if (documentation) description = documentation[0]?.text;
30
26
 
31
- let expireAt;
32
- const timeCycles = this.timeCycles;
33
- if (timeCycles) {
34
- for (const cycle of timeCycles) {
35
- const cron = elementApi.resolveExpression(cycle);
36
- if (!cron || iso8601cycle.test(cron)) continue;
37
-
38
- const expireAtDt = cronParser.parseExpression(cron).next().toDate();
39
- if (!expireAt || expireAtDt < expireAt) expireAt = expireAtDt;
40
- }
41
- }
42
-
43
27
  return {
44
28
  ...(this.resultVariable && { resultVariable: this.resultVariable }),
45
29
  ...(scheduledStart && activity.parent.type === 'bpmn:Process' && { scheduledStart }),
46
30
  ...(user?.length && { candidateUsers: user }),
47
31
  ...(groups?.length && { candidateGroups: groups }),
48
32
  ...(!elementApi.content.description && description && { description: elementApi.resolveExpression(description) }),
49
- ...(expireAt && { expireAt }),
50
33
  ...(assigneeValue && { assignee: assigneeValue }),
51
34
  };
52
35
  }
@@ -1,5 +1,5 @@
1
1
  declare module '@onify/flow-extensions' {
2
- import { SequenceFlow, TimerEventDefinition, ElementBase, Context, IExtension } from 'bpmn-elements';
2
+ import { SequenceFlow, TimerEventDefinition, ElementBase, IExtension } from 'bpmn-elements';
3
3
  import { extendFn as extendFunction } from 'moddle-context-serializer';
4
4
 
5
5
  export class OnifySequenceFlow extends SequenceFlow {}
@@ -9,3 +9,8 @@ declare module '@onify/flow-extensions' {
9
9
  export function extensions(element: ElementBase, context: Context): IExtension;
10
10
  export const extendFn: extendFunction;
11
11
  }
12
+
13
+ declare module '@onify/flow-extensions/FlowScripts' {
14
+ import { IScripts } from 'bpmn-elements';
15
+ export var FlowScripts: IScripts;
16
+ }
package/CHANGELOG.md DELETED
@@ -1,75 +0,0 @@
1
- # Changelog
2
-
3
- # 7.1.0
4
-
5
- - add process attribute `historyTimeToLive` to process environment variables when running
6
- - add process attribute `historyTimeToLive` as timer to definition context via `extendFn`, formatted as ISO8601 duration
7
- - use prettier since eslint will deprecate formatting rules in the next major release
8
-
9
- # 7.0.0
10
-
11
- Attempting to mitigate Boundary Event formatting interrupting normal execution flow. Asynchronous formatting prevents catching events from attached task. Should probably be done in bpmn-elements but the developer is busy.
12
-
13
- ## Breaking
14
-
15
- - No async formatting on boundary events before end
16
- - Boundary event start execution listener will be executed but _without_ formatting capabilities and detached from execution. Occasional error will just be logged
17
- - Boundary event end execution listener is still executed _with_ formatting capabilities
18
-
19
- # 6.0.0
20
-
21
- - Require peer dependency `bpmn-elements >= 8`
22
- - Support timer event definition cron time cycle by overloading parse function. Requires `bpmn-elements >= 10`
23
-
24
- # 5.0.2
25
-
26
- - Correct package module file...
27
-
28
- # 5.0.1
29
-
30
- - Doh! Add neglected package.json file to common js dist folder
31
-
32
- # 5.0.0
33
-
34
- - Turn into module with exports for node
35
- - Add type declaration
36
-
37
- # 4.1.0
38
-
39
- - Support sequence flow properties and take execution listener. Requires `bpmn-elements >= 9.2`
40
-
41
- # 4.0.0
42
-
43
- - make sure sub-process extensions are only triggered once. Sub process activities unintentionally trigger formatting since events bubble
44
- - add script element type to registered scripts
45
- - restructure and split up index.js to separate files
46
- - abide to new lint rules
47
-
48
- # 3.0.0
49
-
50
- - Support activity script and expression execution listeners
51
- - Remove default behaviour of saving activity output even if output is not declared. Output **was** saved to `environment.output._<Activity ID>` if no result variable or output was declared. The reason was that there was no easy way of getting output from SubProcess or a multi-instance task. Now SubProcess output can be defined and multi-instance output can be solved with execution listener
52
-
53
- # 2.0.0
54
-
55
- - fix resume extension when recovered mid formatting
56
- - drop node 12 support
57
-
58
- # 1.1.0
59
-
60
- - allow ISO8601 repeating interval and duration in timeCycle
61
-
62
- # 1.0.0
63
-
64
- - proper routing keys for end formatting
65
-
66
- # 0.1.0
67
-
68
- - catch errors when resolving service expression
69
- - test with bpmn-engine@14
70
-
71
- # 0.0.2
72
-
73
- - allow expressions in timeCycle
74
- - test with bpmn-engine@13
75
- - error message changed in node 16