state-machine-cat 12.0.6 → 12.0.7
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/dist/cli/actions.mjs +34 -31
- package/dist/cli/attributes-parser.mjs +914 -889
- package/dist/cli/execute-command-line.mjs +98 -48
- package/dist/cli/file-name-to-stream.mjs +8 -8
- package/dist/cli/normalize.mjs +89 -70
- package/dist/cli/validations.mjs +72 -52
- package/dist/index-node.mjs +12 -9
- package/dist/index.mjs +10 -7
- package/dist/options.mjs +53 -53
- package/dist/parse/index.mjs +17 -17
- package/dist/parse/parser-helpers.mjs +159 -139
- package/dist/parse/scxml/index.mjs +152 -129
- package/dist/parse/scxml/normalize-machine.mjs +36 -35
- package/dist/parse/scxml/utl.mjs +1 -1
- package/dist/parse/smcat/smcat-parser.mjs +2794 -2844
- package/dist/parse/smcat-ast.schema.mjs +185 -168
- package/dist/render/dot/attributebuilder.mjs +40 -37
- package/dist/render/dot/counter.mjs +14 -14
- package/dist/render/dot/dot.states.template.js +1 -26
- package/dist/render/dot/dot.template.js +1 -14
- package/dist/render/dot/index.mjs +129 -82
- package/dist/render/dot/render-dot-from-ast.mjs +33 -16
- package/dist/render/dot/state-transformers.mjs +96 -85
- package/dist/render/dot/transition-transformers.mjs +39 -41
- package/dist/render/dot/utl.mjs +21 -19
- package/dist/render/index-node.mjs +16 -16
- package/dist/render/index.mjs +9 -9
- package/dist/render/scjson/index.mjs +111 -94
- package/dist/render/scjson/make-valid-event-names.mjs +21 -18
- package/dist/render/scjson/make-valid-xml-name.mjs +17 -13
- package/dist/render/scxml/index.mjs +2 -1
- package/dist/render/scxml/render-from-scjson.mjs +5 -2
- package/dist/render/scxml/scxml.states.template.js +1 -14
- package/dist/render/scxml/scxml.template.js +1 -6
- package/dist/render/smcat/index.mjs +54 -39
- package/dist/render/smcat/smcat.template.js +1 -13
- package/dist/render/vector/dot-to-vector-native.mjs +30 -26
- package/dist/render/vector/vector-native-dot-with-fallback.mjs +27 -20
- package/dist/render/vector/vector-with-wasm.mjs +13 -6
- package/dist/state-machine-model.mjs +67 -52
- package/dist/transform/desugar.mjs +115 -66
- package/dist/transform/utl.mjs +12 -12
- package/dist/version.mjs +1 -1
- package/package.json +74 -74
- package/types/state-machine-cat.d.mts +209 -209
package/dist/options.mjs
CHANGED
|
@@ -1,61 +1,61 @@
|
|
|
1
1
|
const ALLOWED_VALUES = Object.freeze({
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
|
|
5
|
-
|
|
6
|
-
|
|
7
|
-
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
36
|
-
|
|
37
|
-
|
|
38
|
-
|
|
39
|
-
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
2
|
+
inputType: {
|
|
3
|
+
default: "smcat",
|
|
4
|
+
values: [{ name: "smcat" }, { name: "json" }, { name: "scxml" }],
|
|
5
|
+
},
|
|
6
|
+
outputType: {
|
|
7
|
+
default: "svg",
|
|
8
|
+
values: [
|
|
9
|
+
{ name: "ast" },
|
|
10
|
+
{ name: "dot" },
|
|
11
|
+
{ name: "eps" },
|
|
12
|
+
{ name: "json" },
|
|
13
|
+
{ name: "oldeps" },
|
|
14
|
+
{ name: "oldps" },
|
|
15
|
+
{ name: "oldps2" },
|
|
16
|
+
{ name: "oldsvg" },
|
|
17
|
+
{ name: "pdf" },
|
|
18
|
+
{ name: "png" },
|
|
19
|
+
{ name: "ps" },
|
|
20
|
+
{ name: "ps2" },
|
|
21
|
+
{ name: "scjson" },
|
|
22
|
+
{ name: "scxml" },
|
|
23
|
+
{ name: "smcat" },
|
|
24
|
+
{ name: "svg" },
|
|
25
|
+
],
|
|
26
|
+
},
|
|
27
|
+
engine: {
|
|
28
|
+
default: "dot",
|
|
29
|
+
values: [
|
|
30
|
+
{ name: "dot" },
|
|
31
|
+
{ name: "circo" },
|
|
32
|
+
{ name: "fdp" },
|
|
33
|
+
{ name: "neato" },
|
|
34
|
+
{ name: "osage" },
|
|
35
|
+
{ name: "twopi" },
|
|
36
|
+
],
|
|
37
|
+
},
|
|
38
|
+
direction: {
|
|
39
|
+
default: "top-down",
|
|
40
|
+
values: [
|
|
41
|
+
{ name: "top-down" },
|
|
42
|
+
{ name: "bottom-top" },
|
|
43
|
+
{ name: "left-right" },
|
|
44
|
+
{ name: "right-left" },
|
|
45
|
+
],
|
|
46
|
+
},
|
|
47
|
+
desugar: {
|
|
48
|
+
default: false,
|
|
49
|
+
values: [{ name: true }, { name: false }],
|
|
50
|
+
},
|
|
51
51
|
});
|
|
52
52
|
function getOptionValue(pOptions, pOptionName) {
|
|
53
|
-
|
|
53
|
+
return pOptions?.[pOptionName] ?? ALLOWED_VALUES[pOptionName].default;
|
|
54
54
|
}
|
|
55
55
|
function getAllowedValues() {
|
|
56
|
-
|
|
56
|
+
return ALLOWED_VALUES;
|
|
57
57
|
}
|
|
58
58
|
export default {
|
|
59
|
-
|
|
60
|
-
|
|
59
|
+
getAllowedValues,
|
|
60
|
+
getOptionValue,
|
|
61
61
|
};
|
package/dist/parse/index.mjs
CHANGED
|
@@ -5,23 +5,23 @@ import { parse as parseSCXML } from "./scxml/index.mjs";
|
|
|
5
5
|
import $schema from "./smcat-ast.schema.mjs";
|
|
6
6
|
const ajv = new Ajv();
|
|
7
7
|
function validateAgainstSchema(pSchema, pObject) {
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
8
|
+
if (!ajv.validate(pSchema, pObject)) {
|
|
9
|
+
throw new Error(
|
|
10
|
+
`The provided JSON is not a valid state-machine-cat AST: ${ajv.errorsText()}.\n`,
|
|
11
|
+
);
|
|
12
|
+
}
|
|
11
13
|
}
|
|
12
14
|
export default {
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
return lReturnValue;
|
|
26
|
-
},
|
|
15
|
+
getAST(pScript, pOptions) {
|
|
16
|
+
let lReturnValue = pScript;
|
|
17
|
+
if (options.getOptionValue(pOptions, "inputType") === "smcat") {
|
|
18
|
+
lReturnValue = parseSmCat(pScript);
|
|
19
|
+
} else if (options.getOptionValue(pOptions, "inputType") === "scxml") {
|
|
20
|
+
lReturnValue = parseSCXML(pScript);
|
|
21
|
+
} else if (typeof pScript === "string") {
|
|
22
|
+
lReturnValue = JSON.parse(pScript);
|
|
23
|
+
}
|
|
24
|
+
validateAgainstSchema($schema, lReturnValue);
|
|
25
|
+
return lReturnValue;
|
|
26
|
+
},
|
|
27
27
|
};
|
|
@@ -1,175 +1,195 @@
|
|
|
1
1
|
import StateMachineModel from "../state-machine-model.mjs";
|
|
2
|
-
const TRIGGER_RE_AS_A_STRING =
|
|
2
|
+
const TRIGGER_RE_AS_A_STRING =
|
|
3
|
+
"^(entry|activity|exit)\\s*/\\s*([^\\n$]*)(\\n|$)";
|
|
3
4
|
const TRIGGER_RE = new RegExp(TRIGGER_RE_AS_A_STRING);
|
|
4
5
|
function stateExists(pKnownStateNames, pName) {
|
|
5
|
-
|
|
6
|
+
return pKnownStateNames.includes(pName);
|
|
6
7
|
}
|
|
7
8
|
const RE2STATE_TYPE = [
|
|
8
|
-
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
|
|
12
|
-
|
|
13
|
-
|
|
14
|
-
|
|
15
|
-
|
|
16
|
-
|
|
17
|
-
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
27
|
-
|
|
28
|
-
|
|
29
|
-
|
|
30
|
-
|
|
31
|
-
|
|
32
|
-
|
|
33
|
-
|
|
34
|
-
|
|
35
|
-
|
|
9
|
+
{
|
|
10
|
+
re: /initial/,
|
|
11
|
+
stateType: "initial",
|
|
12
|
+
},
|
|
13
|
+
{
|
|
14
|
+
re: /final/,
|
|
15
|
+
stateType: "final",
|
|
16
|
+
},
|
|
17
|
+
{
|
|
18
|
+
re: /parallel/,
|
|
19
|
+
stateType: "parallel",
|
|
20
|
+
},
|
|
21
|
+
{
|
|
22
|
+
re: /(deep.*history)|(history.*deep)/,
|
|
23
|
+
stateType: "deephistory",
|
|
24
|
+
},
|
|
25
|
+
{
|
|
26
|
+
re: /history/,
|
|
27
|
+
stateType: "history",
|
|
28
|
+
},
|
|
29
|
+
{
|
|
30
|
+
re: /^\^.*/,
|
|
31
|
+
stateType: "choice",
|
|
32
|
+
},
|
|
33
|
+
{
|
|
34
|
+
re: /^].*/,
|
|
35
|
+
stateType: "forkjoin",
|
|
36
|
+
},
|
|
36
37
|
];
|
|
37
38
|
function matches(pName) {
|
|
38
|
-
|
|
39
|
+
return (pEntry) => pEntry.re.test(pName);
|
|
39
40
|
}
|
|
40
41
|
function getStateType(pName) {
|
|
41
|
-
|
|
42
|
-
|
|
42
|
+
return (RE2STATE_TYPE.find(matches(pName)) || { stateType: "regular" })
|
|
43
|
+
.stateType;
|
|
43
44
|
}
|
|
44
45
|
function initState(pName) {
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
46
|
+
return {
|
|
47
|
+
name: pName,
|
|
48
|
+
type: getStateType(pName),
|
|
49
|
+
};
|
|
49
50
|
}
|
|
50
51
|
function isComposite(pState) {
|
|
51
|
-
|
|
52
|
+
return Boolean(pState.statemachine);
|
|
52
53
|
}
|
|
53
54
|
function getAlreadyDeclaredStates(pStateMachine) {
|
|
54
|
-
|
|
55
|
-
|
|
55
|
+
const lStates = pStateMachine?.states ?? [];
|
|
56
|
+
return lStates.filter(isComposite).reduce(
|
|
57
|
+
(pAllStateNames, pThisState) =>
|
|
58
|
+
pAllStateNames.concat(getAlreadyDeclaredStates(pThisState.statemachine)),
|
|
59
|
+
lStates.map(({ name }) => name),
|
|
60
|
+
);
|
|
56
61
|
}
|
|
57
62
|
function extractUndeclaredStates(pStateMachine, pKnownStateNames) {
|
|
58
|
-
|
|
59
|
-
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
63
|
-
|
|
64
|
-
|
|
65
|
-
|
|
66
|
-
|
|
67
|
-
|
|
68
|
-
|
|
69
|
-
|
|
70
|
-
|
|
71
|
-
|
|
72
|
-
|
|
73
|
-
|
|
74
|
-
|
|
75
|
-
|
|
76
|
-
|
|
63
|
+
pKnownStateNames = pKnownStateNames
|
|
64
|
+
? pKnownStateNames
|
|
65
|
+
: getAlreadyDeclaredStates(pStateMachine);
|
|
66
|
+
pStateMachine.states = pStateMachine?.states ?? [];
|
|
67
|
+
const lTransitions = pStateMachine?.transitions ?? [];
|
|
68
|
+
pStateMachine.states.filter(isComposite).forEach((pState) => {
|
|
69
|
+
pState.statemachine.states = extractUndeclaredStates(
|
|
70
|
+
pState.statemachine,
|
|
71
|
+
pKnownStateNames,
|
|
72
|
+
);
|
|
73
|
+
});
|
|
74
|
+
lTransitions.forEach((pTransition) => {
|
|
75
|
+
if (!stateExists(pKnownStateNames, pTransition.from)) {
|
|
76
|
+
pKnownStateNames.push(pTransition.from);
|
|
77
|
+
pStateMachine.states.push(initState(pTransition.from));
|
|
78
|
+
}
|
|
79
|
+
if (!stateExists(pKnownStateNames, pTransition.to)) {
|
|
80
|
+
pKnownStateNames.push(pTransition.to);
|
|
81
|
+
pStateMachine.states.push(initState(pTransition.to));
|
|
82
|
+
}
|
|
83
|
+
});
|
|
84
|
+
return pStateMachine.states;
|
|
77
85
|
}
|
|
78
86
|
function classifyForkJoin(pInComingCount, pOutGoingCount) {
|
|
79
|
-
|
|
80
|
-
|
|
81
|
-
|
|
82
|
-
|
|
83
|
-
|
|
84
|
-
|
|
85
|
-
|
|
86
|
-
|
|
87
|
-
}
|
|
88
|
-
function classifyForkJoins(
|
|
89
|
-
|
|
90
|
-
|
|
91
|
-
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
|
|
100
|
-
|
|
87
|
+
let lReturnValue = "junction";
|
|
88
|
+
if (pInComingCount <= 1 && pOutGoingCount > 1) {
|
|
89
|
+
lReturnValue = "fork";
|
|
90
|
+
}
|
|
91
|
+
if (pInComingCount > 1 && pOutGoingCount <= 1) {
|
|
92
|
+
lReturnValue = "join";
|
|
93
|
+
}
|
|
94
|
+
return lReturnValue;
|
|
95
|
+
}
|
|
96
|
+
function classifyForkJoins(
|
|
97
|
+
pStateMachine,
|
|
98
|
+
pFlattenedStateMachineModel = new StateMachineModel(pStateMachine),
|
|
99
|
+
) {
|
|
100
|
+
pStateMachine.states = pStateMachine.states.map((pState) => {
|
|
101
|
+
if (pState.type === "forkjoin" && !pState.typeExplicitlySet) {
|
|
102
|
+
const lInComingCount = pFlattenedStateMachineModel.findTransitionsByTo(
|
|
103
|
+
pState.name,
|
|
104
|
+
).length;
|
|
105
|
+
const lOutGoingCount = pFlattenedStateMachineModel.findTransitionsByFrom(
|
|
106
|
+
pState.name,
|
|
107
|
+
).length;
|
|
108
|
+
pState.type = classifyForkJoin(lInComingCount, lOutGoingCount);
|
|
109
|
+
}
|
|
110
|
+
if (pState.statemachine) {
|
|
111
|
+
pState.statemachine = classifyForkJoins(
|
|
112
|
+
pState.statemachine,
|
|
113
|
+
pFlattenedStateMachineModel,
|
|
114
|
+
);
|
|
115
|
+
}
|
|
116
|
+
return pState;
|
|
117
|
+
});
|
|
118
|
+
return pStateMachine;
|
|
101
119
|
}
|
|
102
120
|
function stateEqual(pStateOne, pStateTwo) {
|
|
103
|
-
|
|
121
|
+
return pStateOne.name === pStateTwo.name;
|
|
104
122
|
}
|
|
105
123
|
function uniq(pArray, pEqualFunction) {
|
|
106
|
-
|
|
107
|
-
|
|
108
|
-
|
|
109
|
-
|
|
110
|
-
|
|
111
|
-
|
|
112
|
-
|
|
113
|
-
|
|
124
|
+
return pArray.reduce((pBag, pMarble) => {
|
|
125
|
+
const lMarbleIndex = pBag.findIndex((pBagItem) =>
|
|
126
|
+
pEqualFunction(pBagItem, pMarble),
|
|
127
|
+
);
|
|
128
|
+
if (lMarbleIndex > -1) {
|
|
129
|
+
pBag[lMarbleIndex] = pMarble;
|
|
130
|
+
return pBag;
|
|
131
|
+
}
|
|
132
|
+
return pBag.concat(pMarble);
|
|
133
|
+
}, []);
|
|
114
134
|
}
|
|
115
135
|
function parseTransitionExpression(pString) {
|
|
116
|
-
|
|
117
|
-
|
|
118
|
-
|
|
119
|
-
|
|
120
|
-
|
|
121
|
-
|
|
122
|
-
|
|
123
|
-
|
|
124
|
-
|
|
125
|
-
|
|
126
|
-
|
|
127
|
-
|
|
128
|
-
|
|
129
|
-
|
|
130
|
-
|
|
131
|
-
|
|
132
|
-
|
|
133
|
-
|
|
136
|
+
const lTransitionExpressionRe = /([^[/]+)?(\[[^\]]+\])?[^/]*(\/.+)?/;
|
|
137
|
+
const lReturnValue = {};
|
|
138
|
+
const lMatchResult = pString.match(lTransitionExpressionRe);
|
|
139
|
+
const lEventPos = 1;
|
|
140
|
+
const lConditionPos = 2;
|
|
141
|
+
const lActionPos = 3;
|
|
142
|
+
if (lMatchResult[lEventPos]) {
|
|
143
|
+
lReturnValue.event = lMatchResult[lEventPos].trim();
|
|
144
|
+
}
|
|
145
|
+
if (lMatchResult[lConditionPos]) {
|
|
146
|
+
lReturnValue.cond = lMatchResult[lConditionPos].slice(1, -1).trim();
|
|
147
|
+
}
|
|
148
|
+
if (lMatchResult[lActionPos]) {
|
|
149
|
+
lReturnValue.action = lMatchResult[lActionPos]
|
|
150
|
+
.slice(1, lMatchResult[lActionPos].length)
|
|
151
|
+
.trim();
|
|
152
|
+
}
|
|
153
|
+
return lReturnValue;
|
|
134
154
|
}
|
|
135
155
|
function setIf(pObject, pProperty, pValue, pCondition = Boolean) {
|
|
136
|
-
|
|
137
|
-
|
|
138
|
-
|
|
156
|
+
if (pCondition(pValue)) {
|
|
157
|
+
pObject[pProperty] = pValue;
|
|
158
|
+
}
|
|
139
159
|
}
|
|
140
160
|
function setIfNotEmpty(pObject, pProperty, pValue) {
|
|
141
|
-
|
|
161
|
+
setIf(pObject, pProperty, pValue, (pX) => pX && pX.length > 0);
|
|
142
162
|
}
|
|
143
163
|
function extractAction(pActivityCandidate) {
|
|
144
|
-
|
|
145
|
-
|
|
146
|
-
|
|
147
|
-
|
|
148
|
-
|
|
149
|
-
|
|
150
|
-
|
|
151
|
-
|
|
152
|
-
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
164
|
+
const lMatch = pActivityCandidate.match(TRIGGER_RE);
|
|
165
|
+
const lTypePos = 1;
|
|
166
|
+
const lBodyPos = 2;
|
|
167
|
+
if (lMatch) {
|
|
168
|
+
return {
|
|
169
|
+
type: lMatch[lTypePos],
|
|
170
|
+
body: lMatch[lBodyPos],
|
|
171
|
+
};
|
|
172
|
+
}
|
|
173
|
+
return {
|
|
174
|
+
type: "activity",
|
|
175
|
+
body: pActivityCandidate,
|
|
176
|
+
};
|
|
157
177
|
}
|
|
158
178
|
function extractActions(pString) {
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
179
|
+
return pString
|
|
180
|
+
.split(/\n\s*/g)
|
|
181
|
+
.map((pActivityCandidate) => pActivityCandidate.trim())
|
|
182
|
+
.map(extractAction);
|
|
163
183
|
}
|
|
164
184
|
export default {
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
169
|
-
|
|
170
|
-
|
|
171
|
-
|
|
172
|
-
|
|
173
|
-
|
|
174
|
-
|
|
185
|
+
initState,
|
|
186
|
+
extractUndeclaredStates,
|
|
187
|
+
classifyForkJoins,
|
|
188
|
+
getStateType,
|
|
189
|
+
stateEqual,
|
|
190
|
+
uniq,
|
|
191
|
+
parseTransitionExpression,
|
|
192
|
+
extractActions,
|
|
193
|
+
setIf,
|
|
194
|
+
setIfNotEmpty,
|
|
175
195
|
};
|