@openmbee/opensysml 0.9.1 → 0.10.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 +355 -33
- package/dist/browser/index.d.ts +9 -0
- package/dist/browser/index.js +16 -0
- package/dist/browser/wasm-worker.d.ts +1 -0
- package/dist/browser/wasm-worker.js +2 -0
- package/dist/browser/wasm.d.ts +17 -0
- package/dist/browser/wasm.js +94 -0
- package/dist/core/arguments.d.ts +4 -0
- package/dist/core/arguments.js +19 -0
- package/dist/core/capabilities.d.ts +90 -9
- package/dist/core/capabilities.js +111 -10
- package/dist/core/connection.d.ts +203 -2
- package/dist/core/connection.js +810 -17
- package/dist/core/conversion.d.ts +153 -0
- package/dist/core/conversion.js +191 -0
- package/dist/core/document.d.ts +188 -0
- package/dist/core/document.js +457 -0
- package/dist/core/edit.d.ts +446 -0
- package/dist/core/edit.js +1994 -0
- package/dist/core/engines.d.ts +64 -0
- package/dist/core/engines.js +74 -0
- package/dist/core/errors.d.ts +164 -2
- package/dist/core/errors.js +209 -3
- package/dist/core/exploration.d.ts +71 -0
- package/dist/core/exploration.js +116 -0
- package/dist/core/graphs.d.ts +15 -0
- package/dist/core/graphs.js +3 -0
- package/dist/core/index.d.ts +30 -9
- package/dist/core/index.js +14 -5
- package/dist/core/model.d.ts +168 -8
- package/dist/core/model.js +258 -31
- package/dist/core/package.d.ts +2 -0
- package/dist/core/package.js +2 -0
- package/dist/core/query.d.ts +50 -0
- package/dist/core/query.js +197 -0
- package/dist/core/render-view.d.ts +97 -0
- package/dist/core/render-view.js +120 -0
- package/dist/core/sources.d.ts +34 -0
- package/dist/core/sources.js +134 -0
- package/dist/core/status.d.ts +9 -2
- package/dist/core/status.js +24 -8
- package/dist/core/typed.d.ts +71 -0
- package/dist/core/typed.js +245 -0
- package/dist/core/values.d.ts +127 -8
- package/dist/core/values.js +536 -30
- package/dist/core/verdict.d.ts +271 -0
- package/dist/core/verdict.js +567 -0
- package/dist/core/wasm.d.ts +114 -0
- package/dist/core/wasm.js +514 -0
- package/dist/generated/sysml_pb.d.ts +1080 -22
- package/dist/generated/sysml_pb.js +200 -100
- package/dist/node/binary.d.ts +2 -0
- package/dist/node/binary.js +8 -6
- package/dist/node/generate-cli.d.ts +2 -0
- package/dist/node/generate-cli.js +10 -0
- package/dist/node/generate.d.ts +99 -0
- package/dist/node/generate.js +757 -0
- package/dist/node/index.d.ts +29 -2
- package/dist/node/index.js +211 -10
- package/dist/node/service.d.ts +5 -3
- package/dist/node/service.js +32 -26
- package/dist/node/wasm-source.d.ts +18 -0
- package/dist/node/wasm-source.js +103 -0
- package/dist/node/wasm-worker.d.ts +1 -0
- package/dist/node/wasm-worker.js +10 -0
- package/dist/node/wasm.d.ts +17 -0
- package/dist/node/wasm.js +63 -0
- package/package.json +19 -7
- package/release-digests.json +105 -0
|
@@ -0,0 +1,457 @@
|
|
|
1
|
+
// Native document queries: a calc def specializing `DocumentQueries::Query`,
|
|
2
|
+
// answered as typed rows. Binding values are plain values, an ElementRef
|
|
3
|
+
// naming a model element, or an ObjectRef naming an object the service holds.
|
|
4
|
+
import { create } from "@bufbuild/protobuf";
|
|
5
|
+
import { DocumentObjectSchema, DocumentQueryBindingSchema, DocumentValueSchema, QuantitySchema, UnitFactorSchema, UnitTermSchema, } from "../generated/sysml_pb.js";
|
|
6
|
+
import { DocumentQueryError, UnsupportedValueError } from "./errors.js";
|
|
7
|
+
import { decodeBigInteger, decodeRational, encodeQuantityMagnitude, encodeRational, fitsInt64, formatValue, quantityRationalAsReal, rationalAsDouble, } from "./values.js";
|
|
8
|
+
/** Whether a wire binding sends an Integer beyond int64, which needs `big_int_values`. */
|
|
9
|
+
export function bindingHoldsBigInt(binding) {
|
|
10
|
+
return binding.values.some((value) => value.kind.case === "bigIntValue" ||
|
|
11
|
+
(value.kind.case === "quantity" && value.kind.value.magnitude.case === "bigIntMagnitude"));
|
|
12
|
+
}
|
|
13
|
+
/** Whether a wire binding sends an exact Rational, which needs `rational_values`. */
|
|
14
|
+
export function bindingHoldsRational(binding) {
|
|
15
|
+
return binding.values.some((value) => value.kind.case === "rationalValue" ||
|
|
16
|
+
(value.kind.case === "quantity" && value.kind.value.magnitude.case === "rationalMagnitude"));
|
|
17
|
+
}
|
|
18
|
+
/** Rewrites each Rational a binding sends that a double holds exactly as that double, for a service without `rational_values`. */
|
|
19
|
+
export function bindingRationalsAsReals(binding) {
|
|
20
|
+
for (const value of binding.values) {
|
|
21
|
+
if (value.kind.case === "rationalValue") {
|
|
22
|
+
const { numerator, denominator } = value.kind.value;
|
|
23
|
+
const double = rationalAsDouble({ numerator: BigInt(numerator), denominator: BigInt(denominator) });
|
|
24
|
+
if (double !== undefined) {
|
|
25
|
+
value.kind = { case: "realValue", value: double };
|
|
26
|
+
}
|
|
27
|
+
}
|
|
28
|
+
else if (value.kind.case === "quantity") {
|
|
29
|
+
quantityRationalAsReal(value.kind.value);
|
|
30
|
+
}
|
|
31
|
+
}
|
|
32
|
+
}
|
|
33
|
+
/** A model element, named by qualified name. */
|
|
34
|
+
export class ElementRef {
|
|
35
|
+
/** Qualified name of the element. */
|
|
36
|
+
id;
|
|
37
|
+
/** Metamodel type name; empty when bound by a caller, reported when answered. */
|
|
38
|
+
type;
|
|
39
|
+
constructor(id, type = "") {
|
|
40
|
+
this.id = id;
|
|
41
|
+
this.type = type;
|
|
42
|
+
}
|
|
43
|
+
toString() {
|
|
44
|
+
return this.type !== "" ? `${this.id} (${this.type})` : this.id;
|
|
45
|
+
}
|
|
46
|
+
}
|
|
47
|
+
/** An object the service holds for the model, created by `instantiate`. */
|
|
48
|
+
export class ObjectRef {
|
|
49
|
+
/** The object's id, as `instantiate` answered it. */
|
|
50
|
+
id;
|
|
51
|
+
/** The object by the label a session reaches it under. */
|
|
52
|
+
path;
|
|
53
|
+
/** The usage the object is held under; reported when answered, ignored when bound. */
|
|
54
|
+
element;
|
|
55
|
+
constructor(options = {}) {
|
|
56
|
+
this.id = typeof options.id === "number" ? BigInt(options.id) : (options.id ?? 0n);
|
|
57
|
+
this.path = options.path ?? "";
|
|
58
|
+
this.element = options.element;
|
|
59
|
+
}
|
|
60
|
+
toString() {
|
|
61
|
+
return this.path !== "" ? this.path : `#${this.id.toString()}`;
|
|
62
|
+
}
|
|
63
|
+
}
|
|
64
|
+
/** A row a `Verdicts` query answered: an assertion checked on one object. Answered only. */
|
|
65
|
+
export class DocumentVerdict {
|
|
66
|
+
assertion;
|
|
67
|
+
/** "constraint", "requirement", "satisfaction" or "verification". */
|
|
68
|
+
kind;
|
|
69
|
+
/** The assertion as written. */
|
|
70
|
+
text;
|
|
71
|
+
/** The object checked, named from the element the query was bound to. */
|
|
72
|
+
path;
|
|
73
|
+
/** "holds", "violated" or "undecided". */
|
|
74
|
+
status;
|
|
75
|
+
/** The condition that evaluated to false, as written; empty otherwise. */
|
|
76
|
+
condition;
|
|
77
|
+
/** Why the assertion is violated or undecided; empty when it holds. */
|
|
78
|
+
reason;
|
|
79
|
+
/** Verdict kinds of the verification cases verifying the row's requirement. */
|
|
80
|
+
verification;
|
|
81
|
+
constructor(init) {
|
|
82
|
+
this.assertion = init.assertion;
|
|
83
|
+
this.kind = init.kind;
|
|
84
|
+
this.text = init.text;
|
|
85
|
+
this.path = init.path;
|
|
86
|
+
this.status = init.status;
|
|
87
|
+
this.condition = init.condition ?? "";
|
|
88
|
+
this.reason = init.reason ?? "";
|
|
89
|
+
this.verification = init.verification ?? [];
|
|
90
|
+
}
|
|
91
|
+
toString() {
|
|
92
|
+
const where = this.path !== "" ? ` on ${this.path}` : "";
|
|
93
|
+
return `${this.text}${where}: ${this.status}`;
|
|
94
|
+
}
|
|
95
|
+
}
|
|
96
|
+
/** A row a `States` query answered: one active leaf state of one object. Answered only. */
|
|
97
|
+
export class DocumentState {
|
|
98
|
+
/** The object whose state machine the row reads. */
|
|
99
|
+
object;
|
|
100
|
+
/** The exhibited state usage's name, or the state def's. */
|
|
101
|
+
machine;
|
|
102
|
+
/** The active leaf state's own name. */
|
|
103
|
+
name;
|
|
104
|
+
/** The leaf's path from the machine's top level. */
|
|
105
|
+
path;
|
|
106
|
+
/** The state usage's declaration. */
|
|
107
|
+
state;
|
|
108
|
+
/** The orthogonal region declaring the leaf; empty when not in one. */
|
|
109
|
+
region;
|
|
110
|
+
/** The active composite states around the leaf, outermost first. */
|
|
111
|
+
enclosing;
|
|
112
|
+
constructor(init) {
|
|
113
|
+
this.object = init.object;
|
|
114
|
+
this.machine = init.machine;
|
|
115
|
+
this.name = init.name;
|
|
116
|
+
this.path = init.path;
|
|
117
|
+
this.state = init.state;
|
|
118
|
+
this.region = init.region ?? "";
|
|
119
|
+
this.enclosing = init.enclosing ?? [];
|
|
120
|
+
}
|
|
121
|
+
toString() {
|
|
122
|
+
return `${this.object.toString()}.${this.machine} in ${this.path}`;
|
|
123
|
+
}
|
|
124
|
+
}
|
|
125
|
+
/** A row an `Events` query answered: one record of a session's trace. Answered only. */
|
|
126
|
+
export class DocumentEvent {
|
|
127
|
+
/** "accept", "send", "transition", "entry", "exit", "do", "choice", "guard" or "terminate". */
|
|
128
|
+
kind;
|
|
129
|
+
/** The instant the record was written at: a quantity, an int or a real. */
|
|
130
|
+
time;
|
|
131
|
+
/** The object the record is about; undefined for a record of the run as a whole. */
|
|
132
|
+
object;
|
|
133
|
+
/** The state machine the record is about. */
|
|
134
|
+
machine;
|
|
135
|
+
/** The state entered, exited or run (entry, exit and do records). */
|
|
136
|
+
state;
|
|
137
|
+
/** The transition's source state. */
|
|
138
|
+
fromState;
|
|
139
|
+
/** The transition's target state. */
|
|
140
|
+
toState;
|
|
141
|
+
/** The object a send was delivered to. */
|
|
142
|
+
target;
|
|
143
|
+
/** The accepted or sent event's type name. */
|
|
144
|
+
event;
|
|
145
|
+
/** The accept's payload, one `name = value` text per attribute. */
|
|
146
|
+
payload;
|
|
147
|
+
/** What a choice drew from, in order. */
|
|
148
|
+
alternatives;
|
|
149
|
+
/** The alternative the choice took. */
|
|
150
|
+
taken;
|
|
151
|
+
/** The record as the trace prints it. */
|
|
152
|
+
text;
|
|
153
|
+
constructor(init) {
|
|
154
|
+
this.kind = init.kind;
|
|
155
|
+
this.time = init.time;
|
|
156
|
+
this.text = init.text;
|
|
157
|
+
this.object = init.object;
|
|
158
|
+
this.machine = init.machine ?? "";
|
|
159
|
+
this.state = init.state ?? "";
|
|
160
|
+
this.fromState = init.fromState ?? "";
|
|
161
|
+
this.toState = init.toState ?? "";
|
|
162
|
+
this.target = init.target;
|
|
163
|
+
this.event = init.event ?? "";
|
|
164
|
+
this.payload = init.payload ?? [];
|
|
165
|
+
this.alternatives = init.alternatives ?? [];
|
|
166
|
+
this.taken = init.taken ?? "";
|
|
167
|
+
}
|
|
168
|
+
toString() {
|
|
169
|
+
const time = this.time;
|
|
170
|
+
const rendered = time instanceof ElementRef ||
|
|
171
|
+
time instanceof ObjectRef ||
|
|
172
|
+
time instanceof DocumentVerdict ||
|
|
173
|
+
time instanceof DocumentState ||
|
|
174
|
+
time instanceof DocumentEvent
|
|
175
|
+
? time.toString()
|
|
176
|
+
: renderPlainTime(time);
|
|
177
|
+
return `${rendered}: ${this.text}`;
|
|
178
|
+
}
|
|
179
|
+
}
|
|
180
|
+
/** What a binding value or an answered cell value may be. */
|
|
181
|
+
/** A time that is a plain value: a SysML value formatted, anything else as JavaScript spells it. */
|
|
182
|
+
function renderPlainTime(time) {
|
|
183
|
+
return typeof time === "object" ? formatValue(time) : String(time);
|
|
184
|
+
}
|
|
185
|
+
/** One selected element and its projected cells, one per column. */
|
|
186
|
+
export class DocumentRow {
|
|
187
|
+
/** The selected element itself, or the usage the row's object is held under. */
|
|
188
|
+
element;
|
|
189
|
+
/** One value sequence per column, in column order. */
|
|
190
|
+
cells;
|
|
191
|
+
/** The verdict a `Verdicts` row carries; undefined for any other row. */
|
|
192
|
+
verdict;
|
|
193
|
+
/** The object a row over held objects is about; undefined for any other row. */
|
|
194
|
+
object;
|
|
195
|
+
/** The state a `States` row carries; undefined for any other row. */
|
|
196
|
+
state;
|
|
197
|
+
/** The event an `Events` row carries; undefined for any other row. */
|
|
198
|
+
event;
|
|
199
|
+
constructor(init) {
|
|
200
|
+
this.element = init.element;
|
|
201
|
+
this.cells = init.cells;
|
|
202
|
+
this.verdict = init.verdict;
|
|
203
|
+
this.object = init.object;
|
|
204
|
+
this.state = init.state;
|
|
205
|
+
this.event = init.event;
|
|
206
|
+
}
|
|
207
|
+
/** The values of the `index`-th column. */
|
|
208
|
+
cell(index) {
|
|
209
|
+
if (index < 0 || index >= this.cells.length) {
|
|
210
|
+
throw new RangeError(`the row has ${this.cells.length} cells, not ${index + 1}`);
|
|
211
|
+
}
|
|
212
|
+
return this.cells[index];
|
|
213
|
+
}
|
|
214
|
+
}
|
|
215
|
+
/** A document query's answer: projected columns and typed rows, in the engine's order. */
|
|
216
|
+
export class DocumentQueryResult {
|
|
217
|
+
/** Projected property names, in projection order. */
|
|
218
|
+
columns;
|
|
219
|
+
/** The selected rows, in the engine's order. */
|
|
220
|
+
rows;
|
|
221
|
+
constructor(init) {
|
|
222
|
+
this.columns = init.columns;
|
|
223
|
+
this.rows = init.rows;
|
|
224
|
+
}
|
|
225
|
+
get length() {
|
|
226
|
+
return this.rows.length;
|
|
227
|
+
}
|
|
228
|
+
[Symbol.iterator]() {
|
|
229
|
+
return this.rows[Symbol.iterator]();
|
|
230
|
+
}
|
|
231
|
+
}
|
|
232
|
+
/** Translate a bindings mapping into the RPC's protobuf. */
|
|
233
|
+
export function buildBindings(bindings) {
|
|
234
|
+
if (bindings === undefined) {
|
|
235
|
+
return [];
|
|
236
|
+
}
|
|
237
|
+
const out = [];
|
|
238
|
+
for (const [parameter, values] of Object.entries(bindings)) {
|
|
239
|
+
const list = Array.isArray(values) ? values : [values];
|
|
240
|
+
out.push(create(DocumentQueryBindingSchema, {
|
|
241
|
+
parameter,
|
|
242
|
+
values: list.map((value) => boundValue(parameter, value)),
|
|
243
|
+
}));
|
|
244
|
+
}
|
|
245
|
+
return out;
|
|
246
|
+
}
|
|
247
|
+
function boundValue(parameter, value) {
|
|
248
|
+
if (value instanceof ElementRef) {
|
|
249
|
+
return create(DocumentValueSchema, { kind: { case: "elementId", value: value.id } });
|
|
250
|
+
}
|
|
251
|
+
if (value instanceof ObjectRef) {
|
|
252
|
+
if (value.id === 0n && value.path === "") {
|
|
253
|
+
throw new DocumentQueryError(`binding ${JSON.stringify(parameter)} cannot carry ${value.toString()}: an object is ` +
|
|
254
|
+
`bound by id or by path; neither was given`);
|
|
255
|
+
}
|
|
256
|
+
return create(DocumentValueSchema, {
|
|
257
|
+
kind: {
|
|
258
|
+
case: "object",
|
|
259
|
+
value: create(DocumentObjectSchema, { instanceId: value.id, path: value.path }),
|
|
260
|
+
},
|
|
261
|
+
});
|
|
262
|
+
}
|
|
263
|
+
if (typeof value === "boolean") {
|
|
264
|
+
return create(DocumentValueSchema, { kind: { case: "boolValue", value } });
|
|
265
|
+
}
|
|
266
|
+
if (typeof value === "string") {
|
|
267
|
+
return create(DocumentValueSchema, { kind: { case: "stringValue", value } });
|
|
268
|
+
}
|
|
269
|
+
if (typeof value === "bigint") {
|
|
270
|
+
return fitsInt64(value)
|
|
271
|
+
? create(DocumentValueSchema, { kind: { case: "intValue", value } })
|
|
272
|
+
: create(DocumentValueSchema, { kind: { case: "bigIntValue", value: value.toString() } });
|
|
273
|
+
}
|
|
274
|
+
if (typeof value === "number") {
|
|
275
|
+
return create(DocumentValueSchema, { kind: { case: "realValue", value } });
|
|
276
|
+
}
|
|
277
|
+
if (value instanceof DocumentVerdict) {
|
|
278
|
+
throw new DocumentQueryError(`binding ${JSON.stringify(parameter)} cannot carry ${value.toString()}: a verdict is ` +
|
|
279
|
+
`answered by queries, not bound to them`);
|
|
280
|
+
}
|
|
281
|
+
if (value instanceof DocumentState || value instanceof DocumentEvent) {
|
|
282
|
+
const what = value instanceof DocumentState ? "a state" : "an event";
|
|
283
|
+
throw new DocumentQueryError(`binding ${JSON.stringify(parameter)} cannot carry ${value.toString()}: ${what} row is ` +
|
|
284
|
+
`answered by queries, not bound to them`);
|
|
285
|
+
}
|
|
286
|
+
if (typeof value === "object" && "kind" in value && value.kind === "rational") {
|
|
287
|
+
return create(DocumentValueSchema, { kind: { case: "rationalValue", value: encodeRational(value) } });
|
|
288
|
+
}
|
|
289
|
+
if (typeof value === "object" && "kind" in value && value.kind === "quantity") {
|
|
290
|
+
return create(DocumentValueSchema, {
|
|
291
|
+
kind: { case: "quantity", value: boundQuantity(value) },
|
|
292
|
+
});
|
|
293
|
+
}
|
|
294
|
+
throw new DocumentQueryError(`binding ${JSON.stringify(parameter)} cannot carry ${JSON.stringify(value)}: a binding is a ` +
|
|
295
|
+
`str, int, float, bool, Quantity, ElementRef or ObjectRef`);
|
|
296
|
+
}
|
|
297
|
+
/** A wire quantity's magnitude as a value; one carrying none reads as a real zero. */
|
|
298
|
+
function decodeMagnitude(magnitude) {
|
|
299
|
+
switch (magnitude.case) {
|
|
300
|
+
case "intMagnitude":
|
|
301
|
+
return { kind: "int", value: magnitude.value };
|
|
302
|
+
case "bigIntMagnitude":
|
|
303
|
+
return { kind: "int", value: decodeBigInteger(magnitude.value) };
|
|
304
|
+
case "realMagnitude":
|
|
305
|
+
return { kind: "real", value: magnitude.value };
|
|
306
|
+
case "rationalMagnitude":
|
|
307
|
+
return { kind: "rational", ...decodeRational(magnitude.value) };
|
|
308
|
+
default:
|
|
309
|
+
return { kind: "real", value: 0 };
|
|
310
|
+
}
|
|
311
|
+
}
|
|
312
|
+
function boundQuantity(value) {
|
|
313
|
+
const magnitude = value.magnitude;
|
|
314
|
+
return create(QuantitySchema, {
|
|
315
|
+
magnitude: encodeQuantityMagnitude(magnitude),
|
|
316
|
+
unit: value.unit,
|
|
317
|
+
...(value.unitTerm === undefined
|
|
318
|
+
? {}
|
|
319
|
+
: {
|
|
320
|
+
unitTerm: create(UnitTermSchema, {
|
|
321
|
+
scaleNum: value.unitTerm.scaleNum,
|
|
322
|
+
scaleDen: value.unitTerm.scaleDen,
|
|
323
|
+
factors: value.unitTerm.factors.map((factor) => create(UnitFactorSchema, { unitId: factor.unitId, exponent: factor.exponent })),
|
|
324
|
+
}),
|
|
325
|
+
}),
|
|
326
|
+
});
|
|
327
|
+
}
|
|
328
|
+
/** Decode a `RunDocumentQueryResponse` into a `DocumentQueryResult`. */
|
|
329
|
+
export function documentResult(response) {
|
|
330
|
+
return new DocumentQueryResult({
|
|
331
|
+
columns: response.columns.map((column) => column.name),
|
|
332
|
+
rows: response.rows.map(rowOf),
|
|
333
|
+
});
|
|
334
|
+
}
|
|
335
|
+
function rowOf(row) {
|
|
336
|
+
const cells = row.cells.map((cell) => cell.values.map(valueOf));
|
|
337
|
+
const kind = row.element?.kind;
|
|
338
|
+
if (kind?.case === "verdict") {
|
|
339
|
+
const verdict = valueOf(row.element);
|
|
340
|
+
return new DocumentRow({ element: verdict.assertion, cells, verdict });
|
|
341
|
+
}
|
|
342
|
+
if (kind?.case === "object") {
|
|
343
|
+
const obj = objectOf(kind.value);
|
|
344
|
+
return new DocumentRow({ element: obj.element ?? new ElementRef(""), cells, object: obj });
|
|
345
|
+
}
|
|
346
|
+
if (kind?.case === "state") {
|
|
347
|
+
const state = stateOf(kind.value);
|
|
348
|
+
return new DocumentRow({
|
|
349
|
+
element: state.object.element ?? new ElementRef(""),
|
|
350
|
+
cells,
|
|
351
|
+
object: state.object,
|
|
352
|
+
state,
|
|
353
|
+
});
|
|
354
|
+
}
|
|
355
|
+
if (kind?.case === "event") {
|
|
356
|
+
const event = eventOf(kind.value);
|
|
357
|
+
return new DocumentRow({
|
|
358
|
+
element: event.object?.element ?? new ElementRef(""),
|
|
359
|
+
cells,
|
|
360
|
+
...(event.object === undefined ? {} : { object: event.object }),
|
|
361
|
+
event,
|
|
362
|
+
});
|
|
363
|
+
}
|
|
364
|
+
return new DocumentRow({ element: elementOf(row.element), cells });
|
|
365
|
+
}
|
|
366
|
+
function elementOf(value) {
|
|
367
|
+
if (value?.kind.case === "elementId") {
|
|
368
|
+
return new ElementRef(value.kind.value, value.elementType);
|
|
369
|
+
}
|
|
370
|
+
return new ElementRef("", value?.elementType ?? "");
|
|
371
|
+
}
|
|
372
|
+
function objectOf(obj) {
|
|
373
|
+
return new ObjectRef({ id: obj.instanceId, path: obj.path, element: elementOf(obj.element) });
|
|
374
|
+
}
|
|
375
|
+
function stateOf(state) {
|
|
376
|
+
return new DocumentState({
|
|
377
|
+
object: state.object === undefined ? new ObjectRef() : objectOf(state.object),
|
|
378
|
+
machine: state.machine,
|
|
379
|
+
name: state.name,
|
|
380
|
+
path: state.statePath,
|
|
381
|
+
...(state.state === undefined ? {} : { state: elementOf(state.state) }),
|
|
382
|
+
region: state.region,
|
|
383
|
+
enclosing: [...state.enclosing],
|
|
384
|
+
});
|
|
385
|
+
}
|
|
386
|
+
function eventOf(event) {
|
|
387
|
+
return new DocumentEvent({
|
|
388
|
+
kind: event.kind,
|
|
389
|
+
time: valueOf(event.time),
|
|
390
|
+
text: event.text,
|
|
391
|
+
...(event.object === undefined ? {} : { object: objectOf(event.object) }),
|
|
392
|
+
machine: event.machine,
|
|
393
|
+
state: event.state,
|
|
394
|
+
fromState: event.from,
|
|
395
|
+
toState: event.to,
|
|
396
|
+
...(event.target === undefined ? {} : { target: objectOf(event.target) }),
|
|
397
|
+
event: event.event,
|
|
398
|
+
payload: [...event.payload],
|
|
399
|
+
alternatives: [...event.alternatives],
|
|
400
|
+
taken: event.taken,
|
|
401
|
+
});
|
|
402
|
+
}
|
|
403
|
+
/** Decode a run-trace event using the document query's event conversion. */
|
|
404
|
+
export function documentEventOf(event) {
|
|
405
|
+
return eventOf(event);
|
|
406
|
+
}
|
|
407
|
+
function valueOf(value) {
|
|
408
|
+
const kind = value?.kind;
|
|
409
|
+
switch (kind?.case) {
|
|
410
|
+
case "elementId":
|
|
411
|
+
return new ElementRef(kind.value, value?.elementType ?? "");
|
|
412
|
+
case "stringValue":
|
|
413
|
+
return kind.value;
|
|
414
|
+
case "intValue":
|
|
415
|
+
return kind.value;
|
|
416
|
+
case "bigIntValue":
|
|
417
|
+
return decodeBigInteger(kind.value);
|
|
418
|
+
case "realValue":
|
|
419
|
+
return kind.value;
|
|
420
|
+
case "rationalValue":
|
|
421
|
+
return { kind: "rational", ...decodeRational(kind.value) };
|
|
422
|
+
case "boolValue":
|
|
423
|
+
return kind.value;
|
|
424
|
+
case "infinity":
|
|
425
|
+
return { kind: "infinity" };
|
|
426
|
+
case "quantity": {
|
|
427
|
+
const magnitude = kind.value.magnitude;
|
|
428
|
+
const decoded = {
|
|
429
|
+
kind: "quantity",
|
|
430
|
+
magnitude: decodeMagnitude(magnitude),
|
|
431
|
+
unit: kind.value.unit,
|
|
432
|
+
};
|
|
433
|
+
return decoded;
|
|
434
|
+
}
|
|
435
|
+
case "object":
|
|
436
|
+
return objectOf(kind.value);
|
|
437
|
+
case "verdict": {
|
|
438
|
+
const verdict = kind.value;
|
|
439
|
+
return new DocumentVerdict({
|
|
440
|
+
assertion: elementOf(verdict.assertion),
|
|
441
|
+
kind: verdict.kind,
|
|
442
|
+
text: verdict.text,
|
|
443
|
+
path: verdict.path,
|
|
444
|
+
status: verdict.verdict,
|
|
445
|
+
condition: verdict.condition,
|
|
446
|
+
reason: verdict.reason,
|
|
447
|
+
verification: [...verdict.verification],
|
|
448
|
+
});
|
|
449
|
+
}
|
|
450
|
+
case "state":
|
|
451
|
+
return stateOf(kind.value);
|
|
452
|
+
case "event":
|
|
453
|
+
return eventOf(kind.value);
|
|
454
|
+
default:
|
|
455
|
+
throw new UnsupportedValueError(`the service answered a document value this client cannot read: ${JSON.stringify(kind?.case)}`);
|
|
456
|
+
}
|
|
457
|
+
}
|