seroval 1.6.11 → 1.7.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 +10 -3
- package/dist/dev/index.cjs +1609 -1041
- package/dist/dev/index.d.cts +285 -251
- package/dist/dev/index.d.ts +285 -251
- package/dist/dev/index.js +1601 -1042
- package/dist/index.cjs +1598 -1039
- package/dist/index.d.cts +285 -251
- package/dist/index.d.ts +285 -251
- package/dist/index.js +1590 -1040
- package/package.json +19 -11
package/dist/dev/index.cjs
CHANGED
|
@@ -1,12 +1,15 @@
|
|
|
1
1
|
Object.defineProperty(exports, Symbol.toStringTag, { value: "Module" });
|
|
2
2
|
//#region src/core/compat.ts
|
|
3
3
|
/**
|
|
4
|
-
*
|
|
5
|
-
*
|
|
6
|
-
*
|
|
4
|
+
* Public feature bits for `disabledFeatures`. Stays a runtime `enum` so the
|
|
5
|
+
* published declaration is unchanged for consumers. Its values must match
|
|
6
|
+
* the internal bits (checked by test/feature.test.ts).
|
|
7
7
|
*/
|
|
8
8
|
let Feature = /* @__PURE__ */ function(Feature) {
|
|
9
9
|
Feature[Feature["AggregateError"] = 1] = "AggregateError";
|
|
10
|
+
/**
|
|
11
|
+
* @deprecated Has no effect. Output always uses arrow functions.
|
|
12
|
+
*/
|
|
10
13
|
Feature[Feature["ArrowFunction"] = 2] = "ArrowFunction";
|
|
11
14
|
Feature[Feature["ErrorPrototypeStack"] = 4] = "ErrorPrototypeStack";
|
|
12
15
|
Feature[Feature["ObjectAssign"] = 8] = "ObjectAssign";
|
|
@@ -32,35 +35,15 @@ const SYM_TO_STRING_TAG = Symbol.toStringTag;
|
|
|
32
35
|
const SYM_UNSCOPABLES = Symbol.unscopables;
|
|
33
36
|
//#endregion
|
|
34
37
|
//#region src/core/constants.ts
|
|
35
|
-
const
|
|
36
|
-
[0]: "
|
|
37
|
-
[1]: "
|
|
38
|
-
[2]: "
|
|
39
|
-
[3]: "
|
|
40
|
-
[4]: "
|
|
41
|
-
[5]: "
|
|
42
|
-
[6]: "
|
|
43
|
-
[7]: "
|
|
44
|
-
[8]: "Symbol.species",
|
|
45
|
-
[9]: "Symbol.split",
|
|
46
|
-
[10]: "Symbol.toPrimitive",
|
|
47
|
-
[11]: "Symbol.toStringTag",
|
|
48
|
-
[12]: "Symbol.unscopables"
|
|
49
|
-
};
|
|
50
|
-
const INV_SYMBOL_REF = {
|
|
51
|
-
[SYM_ASYNC_ITERATOR]: 0,
|
|
52
|
-
[SYM_HAS_INSTANCE]: 1,
|
|
53
|
-
[SYM_IS_CONCAT_SPREADABLE]: 2,
|
|
54
|
-
[SYM_ITERATOR]: 3,
|
|
55
|
-
[SYM_MATCH]: 4,
|
|
56
|
-
[SYM_MATCH_ALL]: 5,
|
|
57
|
-
[SYM_REPLACE]: 6,
|
|
58
|
-
[SYM_SEARCH]: 7,
|
|
59
|
-
[SYM_SPECIES]: 8,
|
|
60
|
-
[SYM_SPLIT]: 9,
|
|
61
|
-
[SYM_TO_PRIMITIVE]: 10,
|
|
62
|
-
[SYM_TO_STRING_TAG]: 11,
|
|
63
|
-
[SYM_UNSCOPABLES]: 12
|
|
38
|
+
const TEMPORAL_TYPE_NAME = {
|
|
39
|
+
[0]: "Instant",
|
|
40
|
+
[1]: "Duration",
|
|
41
|
+
[2]: "PlainDate",
|
|
42
|
+
[3]: "PlainDateTime",
|
|
43
|
+
[4]: "PlainMonthDay",
|
|
44
|
+
[5]: "PlainTime",
|
|
45
|
+
[6]: "PlainYearMonth",
|
|
46
|
+
[7]: "ZonedDateTime"
|
|
64
47
|
};
|
|
65
48
|
const SYMBOL_REF = {
|
|
66
49
|
[0]: SYM_ASYNC_ITERATOR,
|
|
@@ -77,6 +60,18 @@ const SYMBOL_REF = {
|
|
|
77
60
|
[11]: SYM_TO_STRING_TAG,
|
|
78
61
|
[12]: SYM_UNSCOPABLES
|
|
79
62
|
};
|
|
63
|
+
function createSymbolStringTable() {
|
|
64
|
+
const result = {};
|
|
65
|
+
for (let i = 0; i <= 12; i++) result[i] = SYMBOL_REF[i].description;
|
|
66
|
+
return result;
|
|
67
|
+
}
|
|
68
|
+
const SYMBOL_STRING = /* @__PURE__ */ createSymbolStringTable();
|
|
69
|
+
function createInverseSymbolTable() {
|
|
70
|
+
const result = {};
|
|
71
|
+
for (let i = 0; i <= 12; i++) result[SYMBOL_REF[i]] = i;
|
|
72
|
+
return result;
|
|
73
|
+
}
|
|
74
|
+
const INV_SYMBOL_REF = /* @__PURE__ */ createInverseSymbolTable();
|
|
80
75
|
const CONSTANT_STRING = {
|
|
81
76
|
[2]: "!0",
|
|
82
77
|
[3]: "!1",
|
|
@@ -93,19 +88,10 @@ const CONSTANT_VAL = {
|
|
|
93
88
|
[1]: void 0,
|
|
94
89
|
[0]: null,
|
|
95
90
|
[4]: -0,
|
|
96
|
-
[5]:
|
|
97
|
-
[6]:
|
|
91
|
+
[5]: Infinity,
|
|
92
|
+
[6]: -Infinity,
|
|
98
93
|
[7]: NaN
|
|
99
94
|
};
|
|
100
|
-
const ERROR_CONSTRUCTOR_STRING = {
|
|
101
|
-
[0]: "Error",
|
|
102
|
-
[1]: "EvalError",
|
|
103
|
-
[2]: "RangeError",
|
|
104
|
-
[3]: "ReferenceError",
|
|
105
|
-
[4]: "SyntaxError",
|
|
106
|
-
[5]: "TypeError",
|
|
107
|
-
[6]: "URIError"
|
|
108
|
-
};
|
|
109
95
|
const ERROR_CONSTRUCTOR = {
|
|
110
96
|
[0]: Error,
|
|
111
97
|
[1]: EvalError,
|
|
@@ -115,9 +101,20 @@ const ERROR_CONSTRUCTOR = {
|
|
|
115
101
|
[5]: TypeError,
|
|
116
102
|
[6]: URIError
|
|
117
103
|
};
|
|
104
|
+
function createErrorConstructorStringTable() {
|
|
105
|
+
const result = {};
|
|
106
|
+
for (let i = 0; i <= 6; i++) result[i] = ERROR_CONSTRUCTOR[i].name;
|
|
107
|
+
return result;
|
|
108
|
+
}
|
|
109
|
+
const ERROR_CONSTRUCTOR_STRING = /* @__PURE__ */ createErrorConstructorStringTable();
|
|
118
110
|
//#endregion
|
|
119
111
|
//#region src/core/node.ts
|
|
120
112
|
function createSerovalNode(t, i, s, c, m, p, e, a, f, b, o, l) {
|
|
113
|
+
if (c === void 0 && m === void 0 && p === void 0 && e === void 0 && a === void 0 && f === void 0 && b === void 0 && o === void 0 && l === void 0) return {
|
|
114
|
+
t,
|
|
115
|
+
i,
|
|
116
|
+
s
|
|
117
|
+
};
|
|
121
118
|
return {
|
|
122
119
|
t,
|
|
123
120
|
i,
|
|
@@ -136,7 +133,7 @@ function createSerovalNode(t, i, s, c, m, p, e, a, f, b, o, l) {
|
|
|
136
133
|
//#endregion
|
|
137
134
|
//#region src/core/literals.ts
|
|
138
135
|
function createConstantNode(value) {
|
|
139
|
-
return createSerovalNode(2, void 0, value
|
|
136
|
+
return createSerovalNode(2, void 0, value);
|
|
140
137
|
}
|
|
141
138
|
const TRUE_NODE = /* @__PURE__ */ createConstantNode(2);
|
|
142
139
|
const FALSE_NODE = /* @__PURE__ */ createConstantNode(3);
|
|
@@ -149,60 +146,109 @@ const NAN_NODE = /* @__PURE__ */ createConstantNode(7);
|
|
|
149
146
|
//#endregion
|
|
150
147
|
//#region src/core/string.ts
|
|
151
148
|
const MIN_JSON_STRINGIFY_LENGTH = 64;
|
|
152
|
-
const
|
|
153
|
-
|
|
154
|
-
|
|
155
|
-
|
|
156
|
-
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
case
|
|
160
|
-
case
|
|
161
|
-
case
|
|
162
|
-
case
|
|
163
|
-
case
|
|
164
|
-
case
|
|
149
|
+
const NEEDS_ESCAPE = /["\\\n\r\b\t\f<\u2028\u2029]/;
|
|
150
|
+
const JSON_ESCAPE_DIFFERENCES = /[\x00-\x07\x0b\x0e-\x1f\ud800-\udfff]/;
|
|
151
|
+
const LESS_THAN = /</g;
|
|
152
|
+
const LINE_SEPARATOR = /\u2028/g;
|
|
153
|
+
const PARAGRAPH_SEPARATOR = /\u2029/g;
|
|
154
|
+
function escapeCharCode(code) {
|
|
155
|
+
switch (code) {
|
|
156
|
+
case 34: return "\\\"";
|
|
157
|
+
case 92: return "\\\\";
|
|
158
|
+
case 10: return "\\n";
|
|
159
|
+
case 13: return "\\r";
|
|
160
|
+
case 8: return "\\b";
|
|
161
|
+
case 9: return "\\t";
|
|
162
|
+
case 12: return "\\f";
|
|
163
|
+
case 60: return "\\x3C";
|
|
164
|
+
case 8232: return "\\u2028";
|
|
165
|
+
case 8233: return "\\u2029";
|
|
165
166
|
default: return;
|
|
166
167
|
}
|
|
167
168
|
}
|
|
168
169
|
function serializeString(str) {
|
|
169
|
-
if (
|
|
170
|
+
if (!NEEDS_ESCAPE.test(str)) return str;
|
|
171
|
+
if (str.length >= MIN_JSON_STRINGIFY_LENGTH && !JSON_ESCAPE_DIFFERENCES.test(str)) {
|
|
172
|
+
let result = JSON.stringify(str).slice(1, -1);
|
|
173
|
+
if (result.includes("<")) result = result.replace(LESS_THAN, "\\x3C");
|
|
174
|
+
if (result.includes("\u2028")) result = result.replace(LINE_SEPARATOR, "\\u2028");
|
|
175
|
+
if (result.includes("\u2029")) result = result.replace(PARAGRAPH_SEPARATOR, "\\u2029");
|
|
176
|
+
return result;
|
|
177
|
+
}
|
|
170
178
|
let result = "";
|
|
171
179
|
let lastPos = 0;
|
|
172
180
|
let replacement;
|
|
173
181
|
for (let i = 0, len = str.length; i < len; i++) {
|
|
174
|
-
replacement =
|
|
182
|
+
replacement = escapeCharCode(str.charCodeAt(i));
|
|
175
183
|
if (replacement) {
|
|
176
184
|
result += str.slice(lastPos, i) + replacement;
|
|
177
185
|
lastPos = i + 1;
|
|
178
186
|
}
|
|
179
187
|
}
|
|
180
|
-
|
|
181
|
-
else result += str.slice(lastPos);
|
|
182
|
-
return result;
|
|
183
|
-
}
|
|
184
|
-
function deserializeReplacer(str) {
|
|
185
|
-
switch (str) {
|
|
186
|
-
case "\\\\": return "\\";
|
|
187
|
-
case "\\\"": return "\"";
|
|
188
|
-
case "\\n": return "\n";
|
|
189
|
-
case "\\r": return "\r";
|
|
190
|
-
case "\\b": return "\b";
|
|
191
|
-
case "\\t": return " ";
|
|
192
|
-
case "\\f": return "\f";
|
|
193
|
-
case "\\x3C": return "<";
|
|
194
|
-
case "\\u2028": return "\u2028";
|
|
195
|
-
case "\\u2029": return "\u2029";
|
|
196
|
-
default: return str;
|
|
197
|
-
}
|
|
188
|
+
return result + str.slice(lastPos);
|
|
198
189
|
}
|
|
190
|
+
const JSON_COMPATIBLE = /^(?:[^"\\\x00-\x1f]|\\["\\nrbtf])*$/;
|
|
191
|
+
const ESCAPE_SEQUENCE = /(\\\\|\\"|\\n|\\r|\\b|\\t|\\f|\\u2028|\\u2029|\\x3C)/g;
|
|
199
192
|
function deserializeString(str) {
|
|
200
|
-
if (typeof str
|
|
201
|
-
|
|
193
|
+
if (typeof str !== "string") return str.replace(ESCAPE_SEQUENCE, deserializeString);
|
|
194
|
+
let index = str.indexOf("\\");
|
|
195
|
+
if (index === -1) return str;
|
|
196
|
+
if (JSON_COMPATIBLE.test(str)) return JSON.parse("\"" + str + "\"");
|
|
197
|
+
let result = "";
|
|
198
|
+
let lastPos = 0;
|
|
199
|
+
const last = str.length - 1;
|
|
200
|
+
while (index !== -1 && index < last) {
|
|
201
|
+
let replacement;
|
|
202
|
+
let length = 2;
|
|
203
|
+
switch (str.charCodeAt(index + 1)) {
|
|
204
|
+
case 92:
|
|
205
|
+
replacement = "\\";
|
|
206
|
+
break;
|
|
207
|
+
case 34:
|
|
208
|
+
replacement = "\"";
|
|
209
|
+
break;
|
|
210
|
+
case 110:
|
|
211
|
+
replacement = "\n";
|
|
212
|
+
break;
|
|
213
|
+
case 114:
|
|
214
|
+
replacement = "\r";
|
|
215
|
+
break;
|
|
216
|
+
case 98:
|
|
217
|
+
replacement = "\b";
|
|
218
|
+
break;
|
|
219
|
+
case 116:
|
|
220
|
+
replacement = " ";
|
|
221
|
+
break;
|
|
222
|
+
case 102:
|
|
223
|
+
replacement = "\f";
|
|
224
|
+
break;
|
|
225
|
+
case 120:
|
|
226
|
+
if (str.startsWith("3C", index + 2)) {
|
|
227
|
+
replacement = "<";
|
|
228
|
+
length = 4;
|
|
229
|
+
}
|
|
230
|
+
break;
|
|
231
|
+
case 117: if (str.startsWith("2028", index + 2)) {
|
|
232
|
+
replacement = "\u2028";
|
|
233
|
+
length = 6;
|
|
234
|
+
} else if (str.startsWith("2029", index + 2)) {
|
|
235
|
+
replacement = "\u2029";
|
|
236
|
+
length = 6;
|
|
237
|
+
}
|
|
238
|
+
}
|
|
239
|
+
if (replacement) {
|
|
240
|
+
result += str.slice(lastPos, index) + replacement;
|
|
241
|
+
lastPos = index + length;
|
|
242
|
+
index = str.indexOf("\\", lastPos);
|
|
243
|
+
} else index = str.indexOf("\\", index + 1);
|
|
244
|
+
}
|
|
245
|
+
return result + str.slice(lastPos);
|
|
202
246
|
}
|
|
203
247
|
//#endregion
|
|
204
248
|
//#region src/core/errors.ts
|
|
205
|
-
|
|
249
|
+
function objectToString(value) {
|
|
250
|
+
return Object.prototype.toString.call(value);
|
|
251
|
+
}
|
|
206
252
|
function getErrorMessageDev(type, cause) {
|
|
207
253
|
if (cause instanceof Error) return `Seroval caught an error during the ${type} process.
|
|
208
254
|
|
|
@@ -213,14 +259,13 @@ ${cause.message}
|
|
|
213
259
|
- If you believe this is an error in Seroval, please submit an issue at https://github.com/lxsmnsyc/seroval/issues/new`;
|
|
214
260
|
return `Seroval caught an error during the ${type} process.
|
|
215
261
|
|
|
216
|
-
"${objectToString
|
|
262
|
+
"${objectToString(cause)}"
|
|
217
263
|
|
|
218
264
|
For more information, please check the "cause" property of this error.`;
|
|
219
265
|
}
|
|
220
|
-
const getErrorMessage = (type, cause) => getErrorMessageDev(type, cause);
|
|
221
266
|
var SerovalError = class extends Error {
|
|
222
267
|
constructor(type, cause) {
|
|
223
|
-
super(
|
|
268
|
+
super(getErrorMessageDev(type, cause));
|
|
224
269
|
this.cause = cause;
|
|
225
270
|
}
|
|
226
271
|
};
|
|
@@ -241,7 +286,7 @@ var SerovalDeserializationError = class extends SerovalError {
|
|
|
241
286
|
};
|
|
242
287
|
var SerovalUnsupportedTypeError = class extends Error {
|
|
243
288
|
constructor(value) {
|
|
244
|
-
super(`The value ${objectToString
|
|
289
|
+
super(`The value ${objectToString(value)} of type "${typeof value}" cannot be parsed/serialized.
|
|
245
290
|
|
|
246
291
|
There are few workarounds for this problem:
|
|
247
292
|
- Transform the value in a way that it can be serialized.
|
|
@@ -264,9 +309,13 @@ var SerovalMissingInstanceError = class extends Error {
|
|
|
264
309
|
super("Missing \"" + tag + "\" instance.");
|
|
265
310
|
}
|
|
266
311
|
};
|
|
312
|
+
/**
|
|
313
|
+
* @deprecated Not thrown by seroval. A missing `createReference` key throws
|
|
314
|
+
* {@link SerovalMissingReferenceForIdError} instead.
|
|
315
|
+
*/
|
|
267
316
|
var SerovalMissingReferenceError = class extends Error {
|
|
268
317
|
constructor(value) {
|
|
269
|
-
super("Missing reference for the value \"" + objectToString
|
|
318
|
+
super("Missing reference for the value \"" + objectToString(value) + "\" of type \"" + typeof value + "\"");
|
|
270
319
|
this.value = value;
|
|
271
320
|
}
|
|
272
321
|
};
|
|
@@ -295,103 +344,43 @@ var SerovalDepthLimitError = class extends Error {
|
|
|
295
344
|
super("Depth limit of " + limit + " reached");
|
|
296
345
|
}
|
|
297
346
|
};
|
|
298
|
-
|
|
299
|
-
|
|
300
|
-
|
|
301
|
-
|
|
302
|
-
|
|
303
|
-
|
|
304
|
-
|
|
305
|
-
|
|
306
|
-
|
|
307
|
-
|
|
308
|
-
|
|
309
|
-
|
|
310
|
-
|
|
311
|
-
|
|
312
|
-
|
|
313
|
-
|
|
314
|
-
}
|
|
315
|
-
function hasReferenceID(value) {
|
|
316
|
-
return REFERENCE.has(value);
|
|
317
|
-
}
|
|
318
|
-
function hasReference(id) {
|
|
319
|
-
return INV_REFERENCE.has(id);
|
|
320
|
-
}
|
|
321
|
-
function getReferenceID(value) {
|
|
322
|
-
if (hasReferenceID(value)) return REFERENCE.get(value);
|
|
323
|
-
throw new SerovalMissingReferenceError(value);
|
|
324
|
-
}
|
|
325
|
-
function getReference(id) {
|
|
326
|
-
if (hasReference(id)) return INV_REFERENCE.get(id);
|
|
327
|
-
throw new SerovalMissingReferenceForIdError(id);
|
|
328
|
-
}
|
|
329
|
-
if (typeof globalThis !== "undefined") Object.defineProperty(globalThis, REFERENCES_KEY, {
|
|
330
|
-
value: INV_REFERENCE,
|
|
331
|
-
configurable: true,
|
|
332
|
-
writable: false,
|
|
333
|
-
enumerable: false
|
|
334
|
-
});
|
|
335
|
-
else if (typeof window !== "undefined") Object.defineProperty(window, REFERENCES_KEY, {
|
|
336
|
-
value: INV_REFERENCE,
|
|
337
|
-
configurable: true,
|
|
338
|
-
writable: false,
|
|
339
|
-
enumerable: false
|
|
340
|
-
});
|
|
341
|
-
else if (typeof self !== "undefined") Object.defineProperty(self, REFERENCES_KEY, {
|
|
342
|
-
value: INV_REFERENCE,
|
|
343
|
-
configurable: true,
|
|
344
|
-
writable: false,
|
|
345
|
-
enumerable: false
|
|
346
|
-
});
|
|
347
|
-
else if (typeof global !== "undefined") Object.defineProperty(global, REFERENCES_KEY, {
|
|
348
|
-
value: INV_REFERENCE,
|
|
349
|
-
configurable: true,
|
|
350
|
-
writable: false,
|
|
351
|
-
enumerable: false
|
|
352
|
-
});
|
|
347
|
+
var SerovalAbortedError = class extends Error {
|
|
348
|
+
constructor() {
|
|
349
|
+
super("Cross deserializer has been aborted.");
|
|
350
|
+
}
|
|
351
|
+
};
|
|
352
|
+
const LIVE_STREAM_ERROR_MESSAGES = {
|
|
353
|
+
consumed: "Live stream already has a consumer",
|
|
354
|
+
pending: "Live stream already has a pending event",
|
|
355
|
+
reading: "Live stream already has a pending read",
|
|
356
|
+
closed: "Live stream is closed"
|
|
357
|
+
};
|
|
358
|
+
var SerovalLiveStreamError = class extends Error {
|
|
359
|
+
constructor(reason) {
|
|
360
|
+
super(LIVE_STREAM_ERROR_MESSAGES[reason]);
|
|
361
|
+
this.reason = reason;
|
|
362
|
+
}
|
|
363
|
+
};
|
|
353
364
|
//#endregion
|
|
354
365
|
//#region src/core/utils/error.ts
|
|
355
366
|
function getErrorConstructor(error) {
|
|
356
|
-
if (error instanceof
|
|
357
|
-
if (error instanceof RangeError) return 2;
|
|
358
|
-
if (error instanceof ReferenceError) return 3;
|
|
359
|
-
if (error instanceof SyntaxError) return 4;
|
|
360
|
-
if (error instanceof TypeError) return 5;
|
|
361
|
-
if (error instanceof URIError) return 6;
|
|
367
|
+
for (let i = 1; i <= 6; i++) if (error instanceof ERROR_CONSTRUCTOR[i]) return i;
|
|
362
368
|
return 0;
|
|
363
369
|
}
|
|
364
|
-
function getInitialErrorOptions(error) {
|
|
365
|
-
const construct = ERROR_CONSTRUCTOR_STRING[getErrorConstructor(error)];
|
|
366
|
-
if (error.name !== construct) return { name: error.name };
|
|
367
|
-
if (error.constructor.name !== construct) return { name: error.constructor.name };
|
|
368
|
-
return {};
|
|
369
|
-
}
|
|
370
370
|
function getErrorOptions(error, features) {
|
|
371
|
-
|
|
372
|
-
const
|
|
373
|
-
|
|
374
|
-
|
|
375
|
-
|
|
376
|
-
if (name === "stack") {
|
|
377
|
-
if (features & 4) {
|
|
378
|
-
options = options || {};
|
|
379
|
-
options[name] = error[name];
|
|
380
|
-
}
|
|
381
|
-
} else {
|
|
382
|
-
options = options || {};
|
|
383
|
-
options[name] = error[name];
|
|
384
|
-
}
|
|
385
|
-
}
|
|
386
|
-
}
|
|
371
|
+
const options = Object.create(null);
|
|
372
|
+
const construct = ERROR_CONSTRUCTOR_STRING[getErrorConstructor(error)];
|
|
373
|
+
if (error.name !== construct) options.name = error.name;
|
|
374
|
+
else if (error.constructor.name !== construct) options.name = error.constructor.name;
|
|
375
|
+
for (const name of Object.getOwnPropertyNames(error)) if (name !== "name" && name !== "message" && (name !== "stack" || features & 4)) options[name] = error[name];
|
|
387
376
|
return options;
|
|
388
377
|
}
|
|
389
378
|
//#endregion
|
|
390
379
|
//#region src/core/utils/get-object-flag.ts
|
|
391
380
|
function getObjectFlag(obj) {
|
|
381
|
+
if (Object.isExtensible(obj)) return 0;
|
|
392
382
|
if (Object.isFrozen(obj)) return 3;
|
|
393
383
|
if (Object.isSealed(obj)) return 2;
|
|
394
|
-
if (Object.isExtensible(obj)) return 0;
|
|
395
384
|
return 1;
|
|
396
385
|
}
|
|
397
386
|
//#endregion
|
|
@@ -426,86 +415,265 @@ function createNumberNode(value) {
|
|
|
426
415
|
}
|
|
427
416
|
if (value !== value) return NAN_NODE;
|
|
428
417
|
if (Object.is(value, -0)) return NEG_ZERO_NODE;
|
|
429
|
-
return createSerovalNode(0, void 0, value
|
|
418
|
+
return createSerovalNode(0, void 0, value);
|
|
430
419
|
}
|
|
431
420
|
function createStringNode(value) {
|
|
432
|
-
return createSerovalNode(1, void 0, serializeString(value)
|
|
421
|
+
return createSerovalNode(1, void 0, serializeString(value));
|
|
433
422
|
}
|
|
434
423
|
function createBigIntNode(current) {
|
|
435
|
-
return createSerovalNode(3, void 0, "" + current
|
|
424
|
+
return createSerovalNode(3, void 0, "" + current);
|
|
436
425
|
}
|
|
437
426
|
function createIndexedValueNode(id) {
|
|
438
|
-
return createSerovalNode(4, id
|
|
427
|
+
return createSerovalNode(4, id);
|
|
439
428
|
}
|
|
440
429
|
function createDateNode(id, current) {
|
|
441
430
|
const timestamp = current.valueOf();
|
|
442
|
-
return createSerovalNode(5, id, timestamp
|
|
431
|
+
return createSerovalNode(5, id, timestamp === timestamp ? current.toISOString() : "");
|
|
443
432
|
}
|
|
444
433
|
function createTemporalNode(id, type, current) {
|
|
445
|
-
return createSerovalNode(36, id, current.toString(), type
|
|
434
|
+
return createSerovalNode(36, id, current.toString(), type);
|
|
446
435
|
}
|
|
447
436
|
function createRegExpNode(id, current) {
|
|
448
|
-
return createSerovalNode(6, id, void 0, serializeString(current.source), current.flags
|
|
437
|
+
return createSerovalNode(6, id, void 0, serializeString(current.source), current.flags);
|
|
449
438
|
}
|
|
450
439
|
function createWKSymbolNode(id, current) {
|
|
451
|
-
return createSerovalNode(17, id, INV_SYMBOL_REF[current]
|
|
440
|
+
return createSerovalNode(17, id, INV_SYMBOL_REF[current]);
|
|
452
441
|
}
|
|
453
|
-
function createReferenceNode(id,
|
|
454
|
-
return createSerovalNode(18, id, serializeString(
|
|
442
|
+
function createReferenceNode(id, referenceId) {
|
|
443
|
+
return createSerovalNode(18, id, serializeString(referenceId));
|
|
455
444
|
}
|
|
456
445
|
function createPluginNode(id, tag, value) {
|
|
457
|
-
return createSerovalNode(25, id, value, serializeString(tag)
|
|
446
|
+
return createSerovalNode(25, id, value, serializeString(tag));
|
|
458
447
|
}
|
|
459
448
|
function createArrayNode(id, current, parsedItems) {
|
|
460
|
-
return createSerovalNode(9, id, void 0, void 0, void 0, void 0, void 0, parsedItems, void 0, void 0, getObjectFlag(current)
|
|
449
|
+
return createSerovalNode(9, id, void 0, void 0, void 0, void 0, void 0, parsedItems, void 0, void 0, getObjectFlag(current));
|
|
461
450
|
}
|
|
462
451
|
function createBoxedNode(id, boxed) {
|
|
463
|
-
return createSerovalNode(21, id, void 0, void 0, void 0, void 0, void 0, void 0, boxed
|
|
452
|
+
return createSerovalNode(21, id, void 0, void 0, void 0, void 0, void 0, void 0, boxed);
|
|
464
453
|
}
|
|
465
454
|
const MAX_TYPED_ARRAY_LENGTH = 1e6;
|
|
466
|
-
function
|
|
467
|
-
|
|
468
|
-
|
|
469
|
-
|
|
470
|
-
|
|
471
|
-
if (current.length > MAX_TYPED_ARRAY_LENGTH) throw new SerovalUnsupportedTypeError(current);
|
|
472
|
-
return createSerovalNode(16, id, void 0, getTypedArrayName(current), void 0, void 0, void 0, void 0, buffer, current.byteOffset, void 0, current.length);
|
|
473
|
-
}
|
|
474
|
-
function createDataViewNode(id, current, buffer) {
|
|
475
|
-
if (current.byteLength > MAX_TYPED_ARRAY_LENGTH) throw new SerovalUnsupportedTypeError(current);
|
|
476
|
-
return createSerovalNode(20, id, void 0, void 0, void 0, void 0, void 0, void 0, buffer, current.byteOffset, void 0, current.byteLength);
|
|
455
|
+
function createViewNode(type, id, current, buffer) {
|
|
456
|
+
const isDataView = type === 20;
|
|
457
|
+
const size = isDataView ? current.byteLength : current.length;
|
|
458
|
+
if (size > MAX_TYPED_ARRAY_LENGTH) throw new SerovalUnsupportedTypeError(current);
|
|
459
|
+
return createSerovalNode(type, id, void 0, isDataView ? void 0 : getTypedArrayName(current), void 0, void 0, void 0, void 0, buffer, current.byteOffset, void 0, size);
|
|
477
460
|
}
|
|
478
|
-
function createErrorNode(id, current, options) {
|
|
479
|
-
return createSerovalNode(
|
|
480
|
-
}
|
|
481
|
-
function createAggregateErrorNode(id, current, options) {
|
|
482
|
-
return createSerovalNode(14, id, getErrorConstructor(current), void 0, serializeString(current.message), options, void 0, void 0, void 0, void 0, void 0, void 0);
|
|
461
|
+
function createErrorNode(type, id, current, options) {
|
|
462
|
+
return createSerovalNode(type, id, getErrorConstructor(current), void 0, serializeString(current.message), options);
|
|
483
463
|
}
|
|
484
464
|
function createSetNode(id, items) {
|
|
485
|
-
return createSerovalNode(7, id, void 0, void 0, void 0, void 0, void 0, items
|
|
486
|
-
}
|
|
487
|
-
function createIteratorFactoryInstanceNode(factory, items) {
|
|
488
|
-
return createSerovalNode(28, void 0, void 0, void 0, void 0, void 0, void 0, [factory, items], void 0, void 0, void 0, void 0);
|
|
489
|
-
}
|
|
490
|
-
function createAsyncIteratorFactoryInstanceNode(factory, items) {
|
|
491
|
-
return createSerovalNode(30, void 0, void 0, void 0, void 0, void 0, void 0, [factory, items], void 0, void 0, void 0, void 0);
|
|
492
|
-
}
|
|
493
|
-
function createStreamConstructorNode(id, factory, sequence) {
|
|
494
|
-
return createSerovalNode(31, id, void 0, void 0, void 0, void 0, void 0, sequence, factory, void 0, void 0, void 0);
|
|
465
|
+
return createSerovalNode(7, id, void 0, void 0, void 0, void 0, void 0, items);
|
|
495
466
|
}
|
|
496
|
-
function
|
|
497
|
-
return createSerovalNode(
|
|
467
|
+
function createIteratorFactoryInstanceNode(type, factory, items) {
|
|
468
|
+
return createSerovalNode(type, void 0, void 0, void 0, void 0, void 0, void 0, [factory, items]);
|
|
498
469
|
}
|
|
499
|
-
function
|
|
500
|
-
return createSerovalNode(
|
|
470
|
+
function createStreamConstructorNode(id, factory, sequence, live) {
|
|
471
|
+
return createSerovalNode(31, id, void 0, void 0, void 0, void 0, void 0, sequence, factory, void 0, void 0, live);
|
|
501
472
|
}
|
|
502
|
-
function
|
|
503
|
-
return createSerovalNode(
|
|
473
|
+
function createStreamEventNode(type, id, parsed) {
|
|
474
|
+
return createSerovalNode(type, id, void 0, void 0, void 0, void 0, void 0, void 0, parsed);
|
|
504
475
|
}
|
|
505
476
|
function createSequenceNode(id, sequence, throwAt, doneAt) {
|
|
506
477
|
return createSerovalNode(35, id, throwAt, void 0, void 0, void 0, void 0, sequence, void 0, void 0, void 0, doneAt);
|
|
507
478
|
}
|
|
508
479
|
//#endregion
|
|
480
|
+
//#region src/core/live-stream.ts
|
|
481
|
+
function isLiveStream(value) {
|
|
482
|
+
return value instanceof LiveStream;
|
|
483
|
+
}
|
|
484
|
+
/**
|
|
485
|
+
* A single-consumer stream for incremental serialization. Unlike
|
|
486
|
+
* `createStream`, it keeps no history: at most one event is held, and the
|
|
487
|
+
* producer operation that sent it settles only when the consumer accepts it.
|
|
488
|
+
*
|
|
489
|
+
* An internal class rather than a tagged POJO: identity is checked with
|
|
490
|
+
* `instanceof`, which untrusted input cannot forge. The class is exported
|
|
491
|
+
* because bundlers cannot drop an unexported top-level class.
|
|
492
|
+
*/
|
|
493
|
+
var LiveStream = class {
|
|
494
|
+
constructor(options) {
|
|
495
|
+
this.consumed = false;
|
|
496
|
+
this.closed = false;
|
|
497
|
+
this.cancelled = false;
|
|
498
|
+
this.options = options;
|
|
499
|
+
}
|
|
500
|
+
deliver(reader, record) {
|
|
501
|
+
record.delivered = true;
|
|
502
|
+
reader.resolve({
|
|
503
|
+
event: record.event,
|
|
504
|
+
accept: () => {
|
|
505
|
+
if (this.pending === record && record.delivered) {
|
|
506
|
+
const terminal = record.event.type !== "next";
|
|
507
|
+
record.event = void 0;
|
|
508
|
+
this.pending = void 0;
|
|
509
|
+
const resolve = record.resolve;
|
|
510
|
+
record.resolve = void 0;
|
|
511
|
+
record.reject = void 0;
|
|
512
|
+
if (terminal) {
|
|
513
|
+
this.closed = true;
|
|
514
|
+
this.options = void 0;
|
|
515
|
+
const waiter = this.waiting;
|
|
516
|
+
this.waiting = void 0;
|
|
517
|
+
waiter?.reject(new SerovalLiveStreamError("closed"));
|
|
518
|
+
}
|
|
519
|
+
resolve?.();
|
|
520
|
+
}
|
|
521
|
+
}
|
|
522
|
+
});
|
|
523
|
+
}
|
|
524
|
+
/** @internal */
|
|
525
|
+
push(event) {
|
|
526
|
+
if (this.cancelled) return Promise.reject(this.cancelReason);
|
|
527
|
+
if (this.closed) return Promise.reject(new SerovalLiveStreamError("closed"));
|
|
528
|
+
if (this.pending) return Promise.reject(new SerovalLiveStreamError("pending"));
|
|
529
|
+
return new Promise((resolve, reject) => {
|
|
530
|
+
const record = {
|
|
531
|
+
event,
|
|
532
|
+
delivered: false,
|
|
533
|
+
resolve,
|
|
534
|
+
reject
|
|
535
|
+
};
|
|
536
|
+
this.pending = record;
|
|
537
|
+
if (this.waiting) {
|
|
538
|
+
const waiter = this.waiting;
|
|
539
|
+
this.waiting = void 0;
|
|
540
|
+
this.deliver(waiter, record);
|
|
541
|
+
}
|
|
542
|
+
});
|
|
543
|
+
}
|
|
544
|
+
cancel(reason) {
|
|
545
|
+
if (this.cancelled || this.closed) return;
|
|
546
|
+
this.cancelled = true;
|
|
547
|
+
this.cancelReason = reason;
|
|
548
|
+
const record = this.pending;
|
|
549
|
+
const waiter = this.waiting;
|
|
550
|
+
this.pending = void 0;
|
|
551
|
+
this.waiting = void 0;
|
|
552
|
+
const callbackOwner = this.options;
|
|
553
|
+
this.options = void 0;
|
|
554
|
+
if (record) {
|
|
555
|
+
record.event = void 0;
|
|
556
|
+
const reject = record.reject;
|
|
557
|
+
record.resolve = void 0;
|
|
558
|
+
record.reject = void 0;
|
|
559
|
+
reject?.(reason);
|
|
560
|
+
}
|
|
561
|
+
if (waiter) waiter.reject(reason);
|
|
562
|
+
callbackOwner?.onCancel?.(reason);
|
|
563
|
+
}
|
|
564
|
+
read() {
|
|
565
|
+
if (this.cancelled) return Promise.reject(this.cancelReason);
|
|
566
|
+
if (this.closed) return Promise.reject(new SerovalLiveStreamError("closed"));
|
|
567
|
+
if (this.waiting) return Promise.reject(new SerovalLiveStreamError("reading"));
|
|
568
|
+
return new Promise((resolve, reject) => {
|
|
569
|
+
const next = {
|
|
570
|
+
resolve,
|
|
571
|
+
reject
|
|
572
|
+
};
|
|
573
|
+
if (this.pending && !this.pending.delivered) this.deliver(next, this.pending);
|
|
574
|
+
else this.waiting = next;
|
|
575
|
+
});
|
|
576
|
+
}
|
|
577
|
+
consume() {
|
|
578
|
+
if (this.consumed) throw new SerovalLiveStreamError("consumed");
|
|
579
|
+
this.consumed = true;
|
|
580
|
+
return {
|
|
581
|
+
read: () => this.read(),
|
|
582
|
+
cancel: (reason) => this.cancel(reason)
|
|
583
|
+
};
|
|
584
|
+
}
|
|
585
|
+
/**
|
|
586
|
+
* Consumes the stream through a replay-style listener, accepting each
|
|
587
|
+
* event as soon as it has been delivered. Use `consume` or `pump` when
|
|
588
|
+
* acceptance must wait for processing.
|
|
589
|
+
*/
|
|
590
|
+
on(listener) {
|
|
591
|
+
const wrap = (key) => (value, accept) => {
|
|
592
|
+
listener[key](value);
|
|
593
|
+
accept();
|
|
594
|
+
};
|
|
595
|
+
return this.pump({
|
|
596
|
+
next: wrap("next"),
|
|
597
|
+
throw: wrap("throw"),
|
|
598
|
+
return: wrap("return")
|
|
599
|
+
});
|
|
600
|
+
}
|
|
601
|
+
/**
|
|
602
|
+
* Consumes the stream into a sink that controls acceptance. Returns the
|
|
603
|
+
* cancel function.
|
|
604
|
+
* @internal
|
|
605
|
+
*/
|
|
606
|
+
pump(sink) {
|
|
607
|
+
const consumer = this.consume();
|
|
608
|
+
let current = sink;
|
|
609
|
+
function next() {
|
|
610
|
+
consumer.read().then((delivery) => {
|
|
611
|
+
const target = current;
|
|
612
|
+
if (!target) return;
|
|
613
|
+
const event = delivery.event;
|
|
614
|
+
let failure;
|
|
615
|
+
let failed = false;
|
|
616
|
+
try {
|
|
617
|
+
failure = target[event.type](event.type === "throw" ? event.error : event.value, delivery.accept);
|
|
618
|
+
} catch (error) {
|
|
619
|
+
failed = true;
|
|
620
|
+
failure = error;
|
|
621
|
+
}
|
|
622
|
+
if (failed || failure !== void 0) {
|
|
623
|
+
current = void 0;
|
|
624
|
+
try {
|
|
625
|
+
consumer.cancel(failure);
|
|
626
|
+
} finally {
|
|
627
|
+
target.done?.();
|
|
628
|
+
}
|
|
629
|
+
return;
|
|
630
|
+
}
|
|
631
|
+
if (event.type === "next") {
|
|
632
|
+
next();
|
|
633
|
+
return;
|
|
634
|
+
}
|
|
635
|
+
current = void 0;
|
|
636
|
+
target.done?.();
|
|
637
|
+
}, (reason) => {
|
|
638
|
+
const target = current;
|
|
639
|
+
current = void 0;
|
|
640
|
+
target?.error?.(reason);
|
|
641
|
+
});
|
|
642
|
+
}
|
|
643
|
+
next();
|
|
644
|
+
return consumer.cancel;
|
|
645
|
+
}
|
|
646
|
+
};
|
|
647
|
+
/**
|
|
648
|
+
* Creates a live stream and the producer that writes to it.
|
|
649
|
+
*/
|
|
650
|
+
function createLiveStream(options) {
|
|
651
|
+
const stream = new LiveStream(options);
|
|
652
|
+
return {
|
|
653
|
+
stream,
|
|
654
|
+
producer: {
|
|
655
|
+
write(value) {
|
|
656
|
+
return stream.push({
|
|
657
|
+
type: "next",
|
|
658
|
+
value
|
|
659
|
+
});
|
|
660
|
+
},
|
|
661
|
+
close(value) {
|
|
662
|
+
return stream.push({
|
|
663
|
+
type: "return",
|
|
664
|
+
value
|
|
665
|
+
});
|
|
666
|
+
},
|
|
667
|
+
fail(error) {
|
|
668
|
+
return stream.push({
|
|
669
|
+
type: "throw",
|
|
670
|
+
error
|
|
671
|
+
});
|
|
672
|
+
}
|
|
673
|
+
}
|
|
674
|
+
};
|
|
675
|
+
}
|
|
676
|
+
//#endregion
|
|
509
677
|
//#region src/core/opaque-reference.ts
|
|
510
678
|
/**
|
|
511
679
|
* An opaque reference allows hiding values from the serializer.
|
|
@@ -543,7 +711,7 @@ const PROMISE_FAILURE = (resolver, data) => {
|
|
|
543
711
|
const SERIALIZED_PROMISE_CONSTRUCTOR = /* @__PURE__ */ PROMISE_CONSTRUCTOR.toString();
|
|
544
712
|
const SERIALIZED_PROMISE_SUCCESS = /* @__PURE__ */ PROMISE_SUCCESS.toString();
|
|
545
713
|
const SERIALIZED_PROMISE_FAILURE = /* @__PURE__ */ PROMISE_FAILURE.toString();
|
|
546
|
-
const STREAM_CONSTRUCTOR = () => {
|
|
714
|
+
const STREAM_CONSTRUCTOR = (live) => {
|
|
547
715
|
const buffer = [];
|
|
548
716
|
const listeners = [];
|
|
549
717
|
let alive = true;
|
|
@@ -551,6 +719,7 @@ const STREAM_CONSTRUCTOR = () => {
|
|
|
551
719
|
let count = 0;
|
|
552
720
|
const internal = {
|
|
553
721
|
flush(value, mode, x) {
|
|
722
|
+
live > 1 || buffer.push(value);
|
|
554
723
|
for (x = 0; x < count; x++) {
|
|
555
724
|
const listener = listeners[x];
|
|
556
725
|
if (listener) listener[mode](value);
|
|
@@ -564,6 +733,7 @@ const STREAM_CONSTRUCTOR = () => {
|
|
|
564
733
|
}
|
|
565
734
|
},
|
|
566
735
|
on(listener, temp = 0) {
|
|
736
|
+
if (live > 1) throw new Error("Stream consumed");
|
|
567
737
|
let subscribed = alive;
|
|
568
738
|
if (alive) {
|
|
569
739
|
for (temp = 0; temp < count; temp++) if (!listeners[temp]) break;
|
|
@@ -571,6 +741,10 @@ const STREAM_CONSTRUCTOR = () => {
|
|
|
571
741
|
listeners[temp] = listener;
|
|
572
742
|
}
|
|
573
743
|
internal.up(listener);
|
|
744
|
+
if (live) {
|
|
745
|
+
live = 2;
|
|
746
|
+
buffer.length = 0;
|
|
747
|
+
}
|
|
574
748
|
return () => {
|
|
575
749
|
if (alive && subscribed) {
|
|
576
750
|
subscribed = false;
|
|
@@ -587,14 +761,10 @@ const STREAM_CONSTRUCTOR = () => {
|
|
|
587
761
|
return internal.on(listener);
|
|
588
762
|
},
|
|
589
763
|
next(value) {
|
|
590
|
-
if (alive)
|
|
591
|
-
buffer.push(value);
|
|
592
|
-
internal.flush(value, "next");
|
|
593
|
-
}
|
|
764
|
+
if (alive) internal.flush(value, "next");
|
|
594
765
|
},
|
|
595
766
|
throw(value) {
|
|
596
767
|
if (alive) {
|
|
597
|
-
buffer.push(value);
|
|
598
768
|
internal.flush(value, "throw");
|
|
599
769
|
alive = false;
|
|
600
770
|
success = false;
|
|
@@ -603,7 +773,6 @@ const STREAM_CONSTRUCTOR = () => {
|
|
|
603
773
|
},
|
|
604
774
|
return(value) {
|
|
605
775
|
if (alive) {
|
|
606
|
-
buffer.push(value);
|
|
607
776
|
internal.flush(value, "return");
|
|
608
777
|
alive = false;
|
|
609
778
|
success = true;
|
|
@@ -725,7 +894,8 @@ const SERIALIZED_ARRAY_BUFFER_CONSTRUCTOR = /* @__PURE__ */ ARRAY_BUFFER_CONSTRU
|
|
|
725
894
|
//#region src/core/sequence.ts
|
|
726
895
|
/**
|
|
727
896
|
* An internal class rather than a tagged POJO: identity is checked with
|
|
728
|
-
* `instanceof`, which untrusted input cannot forge
|
|
897
|
+
* `instanceof`, which untrusted input cannot forge. The class is exported
|
|
898
|
+
* because bundlers cannot drop an unexported top-level class.
|
|
729
899
|
* The eval-based `deserialize` path still rebuilds a `{__SEROVAL_SEQUENCE__…}`
|
|
730
900
|
* POJO from embedded source - it has no access to this class - so a value read
|
|
731
901
|
* back through `deserialize` is not an instance and, by design, is not treated
|
|
@@ -749,7 +919,7 @@ function createSequenceFromIterable(source) {
|
|
|
749
919
|
let throwsAt = -1;
|
|
750
920
|
let doneAt = -1;
|
|
751
921
|
const iterator = source[SYM_ITERATOR]();
|
|
752
|
-
|
|
922
|
+
for (;;) try {
|
|
753
923
|
const value = iterator.next();
|
|
754
924
|
values.push(value.value);
|
|
755
925
|
if (value.done) {
|
|
@@ -764,7 +934,7 @@ function createSequenceFromIterable(source) {
|
|
|
764
934
|
}
|
|
765
935
|
return createSequence(values, throwsAt, doneAt);
|
|
766
936
|
}
|
|
767
|
-
const createIterator = ITERATOR_CONSTRUCTOR(SYM_ITERATOR);
|
|
937
|
+
const createIterator = /* @__PURE__ */ ITERATOR_CONSTRUCTOR(SYM_ITERATOR);
|
|
768
938
|
function sequenceToIterator(sequence) {
|
|
769
939
|
return createIterator(sequence);
|
|
770
940
|
}
|
|
@@ -795,7 +965,8 @@ const SPECIAL_REF_STRING = {
|
|
|
795
965
|
//#region src/core/stream.ts
|
|
796
966
|
/**
|
|
797
967
|
* An internal class rather than a tagged POJO: identity is checked with
|
|
798
|
-
* `instanceof`, which untrusted input cannot forge
|
|
968
|
+
* `instanceof`, which untrusted input cannot forge. The class is exported
|
|
969
|
+
* because bundlers cannot drop an unexported top-level class.
|
|
799
970
|
*
|
|
800
971
|
* The behavior is intentionally duplicated from `STREAM_CONSTRUCTOR`. That
|
|
801
972
|
* constructor's source is embedded verbatim into the eval-based `deserialize`
|
|
@@ -805,18 +976,17 @@ const SPECIAL_REF_STRING = {
|
|
|
805
976
|
* implementations in sync.
|
|
806
977
|
*/
|
|
807
978
|
var Stream = class {
|
|
808
|
-
constructor() {
|
|
979
|
+
constructor(live) {
|
|
809
980
|
this.buffer = [];
|
|
810
981
|
this.listeners = [];
|
|
811
982
|
this.alive = true;
|
|
812
983
|
this.success = false;
|
|
813
984
|
this.count = 0;
|
|
985
|
+
this.live = live;
|
|
814
986
|
}
|
|
815
987
|
flush(value, mode) {
|
|
816
|
-
|
|
817
|
-
|
|
818
|
-
(_this$listeners$x = this.listeners[x]) === null || _this$listeners$x === void 0 || _this$listeners$x[mode](value);
|
|
819
|
-
}
|
|
988
|
+
this.live > 1 || this.buffer.push(value);
|
|
989
|
+
for (let x = 0; x < this.count; x++) this.listeners[x]?.[mode](value);
|
|
820
990
|
}
|
|
821
991
|
replay(listener) {
|
|
822
992
|
for (let x = 0, z = this.buffer.length; x < z; x++) {
|
|
@@ -826,6 +996,7 @@ var Stream = class {
|
|
|
826
996
|
}
|
|
827
997
|
}
|
|
828
998
|
on(listener) {
|
|
999
|
+
if (this.live > 1) throw new Error("Stream consumed");
|
|
829
1000
|
let subscribed = this.alive;
|
|
830
1001
|
let temp = 0;
|
|
831
1002
|
if (subscribed) {
|
|
@@ -834,6 +1005,10 @@ var Stream = class {
|
|
|
834
1005
|
this.listeners[temp] = listener;
|
|
835
1006
|
}
|
|
836
1007
|
this.replay(listener);
|
|
1008
|
+
if (this.live) {
|
|
1009
|
+
this.live = 2;
|
|
1010
|
+
this.buffer.length = 0;
|
|
1011
|
+
}
|
|
837
1012
|
return () => {
|
|
838
1013
|
if (this.alive && subscribed) {
|
|
839
1014
|
subscribed = false;
|
|
@@ -844,14 +1019,10 @@ var Stream = class {
|
|
|
844
1019
|
};
|
|
845
1020
|
}
|
|
846
1021
|
next(value) {
|
|
847
|
-
if (this.alive)
|
|
848
|
-
this.buffer.push(value);
|
|
849
|
-
this.flush(value, "next");
|
|
850
|
-
}
|
|
1022
|
+
if (this.alive) this.flush(value, "next");
|
|
851
1023
|
}
|
|
852
1024
|
throw(value) {
|
|
853
1025
|
if (this.alive) {
|
|
854
|
-
this.buffer.push(value);
|
|
855
1026
|
this.flush(value, "throw");
|
|
856
1027
|
this.alive = false;
|
|
857
1028
|
this.success = false;
|
|
@@ -860,7 +1031,6 @@ var Stream = class {
|
|
|
860
1031
|
}
|
|
861
1032
|
return(value) {
|
|
862
1033
|
if (this.alive) {
|
|
863
|
-
this.buffer.push(value);
|
|
864
1034
|
this.flush(value, "return");
|
|
865
1035
|
this.alive = false;
|
|
866
1036
|
this.success = true;
|
|
@@ -869,46 +1039,12 @@ var Stream = class {
|
|
|
869
1039
|
}
|
|
870
1040
|
};
|
|
871
1041
|
function isStream(value) {
|
|
872
|
-
return value instanceof Stream;
|
|
1042
|
+
return value instanceof Stream || isLiveStream(value);
|
|
873
1043
|
}
|
|
874
1044
|
function createStream() {
|
|
875
1045
|
return new Stream();
|
|
876
1046
|
}
|
|
877
|
-
|
|
878
|
-
const stream = createStream();
|
|
879
|
-
const iterator = iterable[SYM_ASYNC_ITERATOR]();
|
|
880
|
-
let cancelled = false;
|
|
881
|
-
let done = false;
|
|
882
|
-
cleanups === null || cleanups === void 0 || cleanups.push(() => {
|
|
883
|
-
if (!(done || cancelled)) {
|
|
884
|
-
cancelled = true;
|
|
885
|
-
Promise.resolve().then(() => {
|
|
886
|
-
var _iterator$return;
|
|
887
|
-
return (_iterator$return = iterator.return) === null || _iterator$return === void 0 ? void 0 : _iterator$return.call(iterator);
|
|
888
|
-
}).catch(() => {});
|
|
889
|
-
}
|
|
890
|
-
});
|
|
891
|
-
async function push() {
|
|
892
|
-
try {
|
|
893
|
-
while (!cancelled) {
|
|
894
|
-
const value = await iterator.next();
|
|
895
|
-
if (cancelled) return;
|
|
896
|
-
if (value.done) {
|
|
897
|
-
done = true;
|
|
898
|
-
stream.return(value.value);
|
|
899
|
-
break;
|
|
900
|
-
}
|
|
901
|
-
stream.next(value.value);
|
|
902
|
-
}
|
|
903
|
-
} catch (error) {
|
|
904
|
-
done = true;
|
|
905
|
-
if (!cancelled) stream.throw(error);
|
|
906
|
-
}
|
|
907
|
-
}
|
|
908
|
-
push().catch(() => {});
|
|
909
|
-
return stream;
|
|
910
|
-
}
|
|
911
|
-
const createAsyncIterable = ASYNC_ITERATOR_CONSTRUCTOR(SYM_ASYNC_ITERATOR, PROMISE_CONSTRUCTOR);
|
|
1047
|
+
const createAsyncIterable = /* @__PURE__ */ ASYNC_ITERATOR_CONSTRUCTOR(SYM_ASYNC_ITERATOR, PROMISE_CONSTRUCTOR);
|
|
912
1048
|
function streamToAsyncIterable(stream) {
|
|
913
1049
|
return createAsyncIterable(stream);
|
|
914
1050
|
}
|
|
@@ -922,20 +1058,158 @@ async function promiseToResult(current) {
|
|
|
922
1058
|
}
|
|
923
1059
|
}
|
|
924
1060
|
//#endregion
|
|
1061
|
+
//#region src/core/binary-browser.ts
|
|
1062
|
+
function encodeArrayBuffer$1(current) {
|
|
1063
|
+
const bytes = new Uint8Array(current);
|
|
1064
|
+
if (typeof bytes.toBase64 === "function") return bytes.toBase64();
|
|
1065
|
+
let result = "";
|
|
1066
|
+
for (let i = 0, len = bytes.length; i < len; i++) result += String.fromCharCode(bytes[i]);
|
|
1067
|
+
return btoa(result);
|
|
1068
|
+
}
|
|
1069
|
+
//#endregion
|
|
1070
|
+
//#region src/core/binary-neutral.ts
|
|
1071
|
+
const MIN_NATIVE_BASE64_LENGTH = 512;
|
|
1072
|
+
function encodeArrayBuffer(current) {
|
|
1073
|
+
if (typeof Buffer !== "undefined") return Buffer.from(current).toString("base64");
|
|
1074
|
+
return encodeArrayBuffer$1(current);
|
|
1075
|
+
}
|
|
1076
|
+
function decodeArrayBuffer(source) {
|
|
1077
|
+
if (source.length < MIN_NATIVE_BASE64_LENGTH || typeof Buffer === "undefined") return ARRAY_BUFFER_CONSTRUCTOR(source);
|
|
1078
|
+
const decoded = atob(source);
|
|
1079
|
+
const buffer = new ArrayBuffer(decoded.length);
|
|
1080
|
+
Buffer.from(buffer).write(decoded, "latin1");
|
|
1081
|
+
return buffer;
|
|
1082
|
+
}
|
|
1083
|
+
//#endregion
|
|
1084
|
+
//#region src/core/plugin.ts
|
|
1085
|
+
let SerovalMode = /* @__PURE__ */ function(SerovalMode) {
|
|
1086
|
+
SerovalMode[SerovalMode["Vanilla"] = 1] = "Vanilla";
|
|
1087
|
+
SerovalMode[SerovalMode["Cross"] = 2] = "Cross";
|
|
1088
|
+
return SerovalMode;
|
|
1089
|
+
}({});
|
|
1090
|
+
function createPlugin(plugin) {
|
|
1091
|
+
return plugin;
|
|
1092
|
+
}
|
|
1093
|
+
function dedupePlugins(deduped, plugins) {
|
|
1094
|
+
for (let i = 0, len = plugins.length; i < len; i++) {
|
|
1095
|
+
const current = plugins[i];
|
|
1096
|
+
if (!deduped.has(current)) {
|
|
1097
|
+
deduped.add(current);
|
|
1098
|
+
if (current.extends) dedupePlugins(deduped, current.extends);
|
|
1099
|
+
}
|
|
1100
|
+
}
|
|
1101
|
+
}
|
|
1102
|
+
const RESOLVED_PLUGINS = /* @__PURE__ */ new WeakMap();
|
|
1103
|
+
function matchResolved(resolved, plugins, added) {
|
|
1104
|
+
for (let i = 0, len = plugins.length; i < len; i++) {
|
|
1105
|
+
const current = plugins[i];
|
|
1106
|
+
if (current === resolved[added]) {
|
|
1107
|
+
added++;
|
|
1108
|
+
if (current.extends) {
|
|
1109
|
+
added = matchResolved(resolved, current.extends, added);
|
|
1110
|
+
if (added === -1) return -1;
|
|
1111
|
+
}
|
|
1112
|
+
} else {
|
|
1113
|
+
const index = resolved.indexOf(current);
|
|
1114
|
+
if (index === -1 || index >= added) return -1;
|
|
1115
|
+
}
|
|
1116
|
+
}
|
|
1117
|
+
return added;
|
|
1118
|
+
}
|
|
1119
|
+
function resolvePlugins(plugins) {
|
|
1120
|
+
if (plugins) {
|
|
1121
|
+
const cached = RESOLVED_PLUGINS.get(plugins);
|
|
1122
|
+
if (cached && matchResolved(cached, plugins, 0) === cached.length) return cached;
|
|
1123
|
+
const deduped = /* @__PURE__ */ new Set();
|
|
1124
|
+
dedupePlugins(deduped, plugins);
|
|
1125
|
+
const resolved = [...deduped];
|
|
1126
|
+
RESOLVED_PLUGINS.set(plugins, resolved);
|
|
1127
|
+
return resolved;
|
|
1128
|
+
}
|
|
1129
|
+
}
|
|
1130
|
+
/**
|
|
1131
|
+
* Returns the plugins that are tested for plain objects. It is the same array
|
|
1132
|
+
* when no plugin sets `skipPlainObjects`.
|
|
1133
|
+
*/
|
|
1134
|
+
function getPlainObjectPlugins(plugins) {
|
|
1135
|
+
if (plugins) {
|
|
1136
|
+
for (let i = 0, len = plugins.length; i < len; i++) if (plugins[i].skipPlainObjects) {
|
|
1137
|
+
const result = plugins.filter((plugin) => !plugin.skipPlainObjects);
|
|
1138
|
+
return result.length ? result : void 0;
|
|
1139
|
+
}
|
|
1140
|
+
}
|
|
1141
|
+
return plugins;
|
|
1142
|
+
}
|
|
1143
|
+
//#endregion
|
|
1144
|
+
//#region src/core/keys.ts
|
|
1145
|
+
const REFERENCES_KEY = "__SEROVAL_REFS__";
|
|
1146
|
+
const GLOBAL_CONTEXT_R = `self.\$R`;
|
|
1147
|
+
function getCrossReferenceHeader(id) {
|
|
1148
|
+
if (id == null) return `${GLOBAL_CONTEXT_R}=${GLOBAL_CONTEXT_R}||[]`;
|
|
1149
|
+
return `(${GLOBAL_CONTEXT_R}=${GLOBAL_CONTEXT_R}||{})["${serializeString(id)}"]=[]`;
|
|
1150
|
+
}
|
|
1151
|
+
//#endregion
|
|
1152
|
+
//#region src/core/reference.ts
|
|
1153
|
+
const REFERENCE = /* @__PURE__ */ new Map();
|
|
1154
|
+
const INV_REFERENCE = /* @__PURE__ */ new Map();
|
|
1155
|
+
let installed = false;
|
|
1156
|
+
function getGlobalObject() {
|
|
1157
|
+
if (typeof globalThis !== "undefined") return globalThis;
|
|
1158
|
+
if (typeof window !== "undefined") return window;
|
|
1159
|
+
if (typeof self !== "undefined") return self;
|
|
1160
|
+
if (typeof global !== "undefined") return global;
|
|
1161
|
+
}
|
|
1162
|
+
function installReferenceStore() {
|
|
1163
|
+
if (!installed) {
|
|
1164
|
+
installed = true;
|
|
1165
|
+
const globalObject = getGlobalObject();
|
|
1166
|
+
if (globalObject) Object.defineProperty(globalObject, REFERENCES_KEY, {
|
|
1167
|
+
value: INV_REFERENCE,
|
|
1168
|
+
configurable: true,
|
|
1169
|
+
writable: false,
|
|
1170
|
+
enumerable: false
|
|
1171
|
+
});
|
|
1172
|
+
}
|
|
1173
|
+
}
|
|
1174
|
+
function createReference(id, value) {
|
|
1175
|
+
installReferenceStore();
|
|
1176
|
+
REFERENCE.set(value, id);
|
|
1177
|
+
INV_REFERENCE.set(id, value);
|
|
1178
|
+
return value;
|
|
1179
|
+
}
|
|
1180
|
+
function hasReference(id) {
|
|
1181
|
+
return INV_REFERENCE.has(id);
|
|
1182
|
+
}
|
|
1183
|
+
function getReferenceID(value) {
|
|
1184
|
+
return REFERENCE.get(value);
|
|
1185
|
+
}
|
|
1186
|
+
function getReference(id) {
|
|
1187
|
+
if (hasReference(id)) return INV_REFERENCE.get(id);
|
|
1188
|
+
throw new SerovalMissingReferenceForIdError(id);
|
|
1189
|
+
}
|
|
1190
|
+
//#endregion
|
|
925
1191
|
//#region src/core/context/parser.ts
|
|
926
|
-
function createBaseParserContext(
|
|
927
|
-
var _options$compactArray;
|
|
1192
|
+
function createBaseParserContext(options) {
|
|
928
1193
|
return {
|
|
929
1194
|
plugins: options.plugins,
|
|
930
|
-
|
|
1195
|
+
plainObjectPlugins: getPlainObjectPlugins(options.plugins),
|
|
931
1196
|
marked: /* @__PURE__ */ new Set(),
|
|
932
|
-
features: 127 ^ (options.disabledFeatures
|
|
933
|
-
refs: options.refs
|
|
1197
|
+
features: 127 ^ (options.disabledFeatures ?? 0),
|
|
1198
|
+
refs: options.refs ?? /* @__PURE__ */ new Map(),
|
|
934
1199
|
depthLimit: options.depthLimit || 1e3,
|
|
935
|
-
compactArrayBufferViews:
|
|
1200
|
+
compactArrayBufferViews: options.compactArrayBufferViews ?? false
|
|
936
1201
|
};
|
|
937
1202
|
}
|
|
938
1203
|
/**
|
|
1204
|
+
* Returns the plugins to test for an object. Plain objects, whose prototype is
|
|
1205
|
+
* `Object.prototype`, skip the plugins that set `skipPlainObjects`. Checking
|
|
1206
|
+
* the prototype as well as `constructor` keeps instances whose prototype has
|
|
1207
|
+
* no own `constructor` property from skipping those plugins.
|
|
1208
|
+
*/
|
|
1209
|
+
function getObjectPlugins(ctx, current, currentClass) {
|
|
1210
|
+
return currentClass === Object && Object.getPrototypeOf(current) === Object.prototype ? ctx.plainObjectPlugins : ctx.plugins;
|
|
1211
|
+
}
|
|
1212
|
+
/**
|
|
939
1213
|
* Ensures that the value (based on an identifier) has been visited by the parser.
|
|
940
1214
|
* @param ctx
|
|
941
1215
|
* @param id
|
|
@@ -957,118 +1231,166 @@ function getNodeForIndexedValue(ctx, current) {
|
|
|
957
1231
|
const registeredId = ctx.refs.get(current);
|
|
958
1232
|
if (registeredId != null) {
|
|
959
1233
|
markParserRef(ctx, registeredId);
|
|
960
|
-
return
|
|
961
|
-
type: 1,
|
|
962
|
-
value: createIndexedValueNode(registeredId)
|
|
963
|
-
};
|
|
1234
|
+
return createIndexedValueNode(registeredId);
|
|
964
1235
|
}
|
|
965
|
-
return
|
|
966
|
-
type: 0,
|
|
967
|
-
value: createIndexForValue(ctx, current)
|
|
968
|
-
};
|
|
1236
|
+
return createIndexForValue(ctx, current);
|
|
969
1237
|
}
|
|
970
1238
|
function getReferenceNode(ctx, current) {
|
|
971
1239
|
const indexed = getNodeForIndexedValue(ctx, current);
|
|
972
|
-
if (indexed
|
|
973
|
-
|
|
974
|
-
|
|
975
|
-
value: createReferenceNode(indexed.value, current)
|
|
976
|
-
};
|
|
977
|
-
return indexed;
|
|
1240
|
+
if (typeof indexed !== "number") return indexed;
|
|
1241
|
+
const referenceId = getReferenceID(current);
|
|
1242
|
+
return referenceId === void 0 ? indexed : createReferenceNode(indexed, referenceId);
|
|
978
1243
|
}
|
|
979
1244
|
/**
|
|
980
1245
|
* Parsing methods
|
|
981
1246
|
*/
|
|
982
1247
|
function parseWellKnownSymbol(ctx, current) {
|
|
983
1248
|
const ref = getReferenceNode(ctx, current);
|
|
984
|
-
if (ref
|
|
985
|
-
if (current in INV_SYMBOL_REF) return createWKSymbolNode(ref
|
|
1249
|
+
if (typeof ref !== "number") return ref;
|
|
1250
|
+
if (current in INV_SYMBOL_REF) return createWKSymbolNode(ref, current);
|
|
986
1251
|
throw new SerovalUnsupportedTypeError(current);
|
|
987
1252
|
}
|
|
988
1253
|
function parseSpecialReference(ctx, ref) {
|
|
989
1254
|
const result = getNodeForIndexedValue(ctx, SPECIAL_REFS[ref]);
|
|
990
|
-
if (result
|
|
991
|
-
return createSerovalNode(26, result
|
|
1255
|
+
if (typeof result !== "number") return result;
|
|
1256
|
+
return createSerovalNode(26, result, ref);
|
|
992
1257
|
}
|
|
993
1258
|
function parseIteratorFactory(ctx) {
|
|
994
1259
|
const result = getNodeForIndexedValue(ctx, ITERATOR);
|
|
995
|
-
if (result
|
|
996
|
-
return createSerovalNode(27, result
|
|
1260
|
+
if (typeof result !== "number") return result;
|
|
1261
|
+
return createSerovalNode(27, result, void 0, void 0, void 0, void 0, void 0, void 0, parseWellKnownSymbol(ctx, SYM_ITERATOR));
|
|
997
1262
|
}
|
|
998
1263
|
function parseAsyncIteratorFactory(ctx) {
|
|
999
1264
|
const result = getNodeForIndexedValue(ctx, ASYNC_ITERATOR);
|
|
1000
|
-
if (result
|
|
1001
|
-
return createSerovalNode(29, result
|
|
1002
|
-
}
|
|
1003
|
-
function createObjectNode(id, current, empty, record) {
|
|
1004
|
-
return createSerovalNode(empty ? 11 : 10, id, void 0, void 0, void 0, record, void 0, void 0, void 0, void 0, getObjectFlag(current), void 0);
|
|
1265
|
+
if (typeof result !== "number") return result;
|
|
1266
|
+
return createSerovalNode(29, result, void 0, void 0, void 0, void 0, void 0, [parseSpecialReference(ctx, 1), parseWellKnownSymbol(ctx, SYM_ASYNC_ITERATOR)]);
|
|
1005
1267
|
}
|
|
1006
|
-
function
|
|
1007
|
-
|
|
1008
|
-
|
|
1009
|
-
|
|
1010
|
-
|
|
1011
|
-
|
|
1012
|
-
|
|
1013
|
-
|
|
1268
|
+
function getTemporalType(currentClass) {
|
|
1269
|
+
switch (currentClass) {
|
|
1270
|
+
case Temporal.Instant: return 0;
|
|
1271
|
+
case Temporal.Duration: return 1;
|
|
1272
|
+
case Temporal.PlainDate: return 2;
|
|
1273
|
+
case Temporal.PlainDateTime: return 3;
|
|
1274
|
+
case Temporal.PlainMonthDay: return 4;
|
|
1275
|
+
case Temporal.PlainTime: return 5;
|
|
1276
|
+
case Temporal.PlainYearMonth: return 6;
|
|
1277
|
+
case Temporal.ZonedDateTime: return 7;
|
|
1278
|
+
default: return;
|
|
1279
|
+
}
|
|
1014
1280
|
}
|
|
1015
|
-
function
|
|
1016
|
-
|
|
1017
|
-
|
|
1018
|
-
|
|
1281
|
+
function getObjectClass(current) {
|
|
1282
|
+
const currentClass = current.constructor;
|
|
1283
|
+
if (currentClass !== void 0 && typeof currentClass !== "function") {
|
|
1284
|
+
const proto = Object.getPrototypeOf(current);
|
|
1285
|
+
return proto === null ? void 0 : proto.constructor;
|
|
1286
|
+
}
|
|
1287
|
+
return currentClass;
|
|
1019
1288
|
}
|
|
1020
|
-
|
|
1021
|
-
|
|
1022
|
-
|
|
1023
|
-
|
|
1024
|
-
|
|
1025
|
-
|
|
1026
|
-
|
|
1289
|
+
/**
|
|
1290
|
+
* Decides how an object is parsed. Shared by the sync, stream and async
|
|
1291
|
+
* parsers so the class checks and feature gates live in one place.
|
|
1292
|
+
*/
|
|
1293
|
+
function getObjectKind(current, currentClass, features) {
|
|
1294
|
+
switch (currentClass) {
|
|
1295
|
+
case Object: return 1;
|
|
1296
|
+
case void 0: return 2;
|
|
1297
|
+
case Date: return 3;
|
|
1298
|
+
case Error:
|
|
1299
|
+
case EvalError:
|
|
1300
|
+
case RangeError:
|
|
1301
|
+
case ReferenceError:
|
|
1302
|
+
case SyntaxError:
|
|
1303
|
+
case TypeError:
|
|
1304
|
+
case URIError: return 4;
|
|
1305
|
+
case Number:
|
|
1306
|
+
case Boolean:
|
|
1307
|
+
case String:
|
|
1308
|
+
case BigInt: return 6;
|
|
1309
|
+
case ArrayBuffer: return 7;
|
|
1310
|
+
case Int8Array:
|
|
1311
|
+
case Int16Array:
|
|
1312
|
+
case Int32Array:
|
|
1313
|
+
case Uint8Array:
|
|
1314
|
+
case Uint16Array:
|
|
1315
|
+
case Uint32Array:
|
|
1316
|
+
case Uint8ClampedArray:
|
|
1317
|
+
case Float32Array:
|
|
1318
|
+
case Float64Array: return 8;
|
|
1319
|
+
case DataView: return 10;
|
|
1320
|
+
case Map: return 11;
|
|
1321
|
+
case Set: return 12;
|
|
1322
|
+
}
|
|
1323
|
+
if (currentClass === Promise || current instanceof Promise) return 13;
|
|
1324
|
+
if (features & 32 && currentClass === RegExp) return 14;
|
|
1325
|
+
if (features & 16 && (currentClass === BigInt64Array || currentClass === BigUint64Array)) return 9;
|
|
1326
|
+
if (features & 1 && typeof AggregateError !== "undefined" && (currentClass === AggregateError || current instanceof AggregateError)) return 5;
|
|
1327
|
+
if (features & 64 && typeof Temporal !== "undefined" && getTemporalType(currentClass) != null) return 15;
|
|
1328
|
+
if (current instanceof Error) return 4;
|
|
1329
|
+
if (SYM_ITERATOR in current || SYM_ASYNC_ITERATOR in current) return 16;
|
|
1330
|
+
return 0;
|
|
1331
|
+
}
|
|
1332
|
+
function createObjectNode(id, current, empty, record) {
|
|
1333
|
+
return createSerovalNode(empty ? 11 : 10, id, void 0, void 0, void 0, record, void 0, void 0, void 0, void 0, getObjectFlag(current));
|
|
1334
|
+
}
|
|
1335
|
+
/**
|
|
1336
|
+
* Gets the sentinel node for a Map. Call it before parsing the entries, so
|
|
1337
|
+
* that an outer Map declares the sentinel before any Map inside it uses it.
|
|
1338
|
+
*/
|
|
1339
|
+
function parseMapSentinel(ctx) {
|
|
1340
|
+
return parseSpecialReference(ctx, 0);
|
|
1341
|
+
}
|
|
1342
|
+
function createMapNode(id, sentinel, k, v) {
|
|
1343
|
+
return createSerovalNode(8, id, void 0, void 0, void 0, void 0, {
|
|
1344
|
+
k,
|
|
1345
|
+
v
|
|
1346
|
+
}, void 0, sentinel);
|
|
1347
|
+
}
|
|
1348
|
+
function createPromiseConstructorNode(ctx, id, resolver) {
|
|
1349
|
+
return createSerovalNode(22, id, resolver, void 0, void 0, void 0, void 0, void 0, parseSpecialReference(ctx, 1));
|
|
1350
|
+
}
|
|
1351
|
+
function getArrayBufferView(ctx, current) {
|
|
1352
|
+
if (!ctx.compactArrayBufferViews) return current;
|
|
1353
|
+
const buffer = new Uint8Array(current.buffer, current.byteOffset, current.byteLength).slice().buffer;
|
|
1354
|
+
return new (current instanceof DataView ? DataView : getTypedArrayConstructor(getTypedArrayName(current)))(buffer);
|
|
1027
1355
|
}
|
|
1028
1356
|
function createArrayBufferNode(ctx, id, current) {
|
|
1029
|
-
return createSerovalNode(19, id, encodeArrayBuffer(current), void 0, void 0, void 0, void 0, void 0, parseSpecialReference(ctx, 5)
|
|
1357
|
+
return createSerovalNode(19, id, encodeArrayBuffer(current), void 0, void 0, void 0, void 0, void 0, parseSpecialReference(ctx, 5));
|
|
1030
1358
|
}
|
|
1031
1359
|
//#endregion
|
|
1032
1360
|
//#region src/core/context/async-parser.ts
|
|
1033
|
-
function createAsyncParserContext(
|
|
1034
|
-
return {
|
|
1035
|
-
base: createBaseParserContext(mode, options),
|
|
1036
|
-
child: void 0
|
|
1037
|
-
};
|
|
1361
|
+
function createAsyncParserContext(options) {
|
|
1362
|
+
return { base: createBaseParserContext(options) };
|
|
1038
1363
|
}
|
|
1039
|
-
var AsyncParsePluginContext = class {
|
|
1040
|
-
constructor(_p, depth) {
|
|
1041
|
-
this._p = _p;
|
|
1042
|
-
this.depth = depth;
|
|
1043
|
-
}
|
|
1044
|
-
parse(current) {
|
|
1045
|
-
return parseAsync(this._p, this.depth, current);
|
|
1046
|
-
}
|
|
1047
|
-
};
|
|
1048
1364
|
async function parseItems$1(ctx, depth, current) {
|
|
1049
|
-
const
|
|
1050
|
-
|
|
1051
|
-
|
|
1365
|
+
const len = current.length;
|
|
1366
|
+
const nodes = new Array(len);
|
|
1367
|
+
for (let i = 0, node; i < len; i++) if (i in current) {
|
|
1368
|
+
node = parseValueAsync(ctx, depth, current[i]);
|
|
1369
|
+
nodes[i] = node instanceof Promise ? await node : node;
|
|
1370
|
+
} else nodes[i] = 0;
|
|
1052
1371
|
return nodes;
|
|
1053
1372
|
}
|
|
1054
1373
|
async function parseArray$1(ctx, depth, id, current) {
|
|
1055
1374
|
return createArrayNode(id, current, await parseItems$1(ctx, depth, current));
|
|
1056
1375
|
}
|
|
1057
1376
|
async function parseProperties$1(ctx, depth, properties) {
|
|
1058
|
-
const
|
|
1059
|
-
const
|
|
1060
|
-
const
|
|
1061
|
-
|
|
1062
|
-
|
|
1063
|
-
|
|
1377
|
+
const keys = Object.keys(properties);
|
|
1378
|
+
const len = keys.length;
|
|
1379
|
+
const keyNodes = new Array(len);
|
|
1380
|
+
const valueNodes = new Array(len);
|
|
1381
|
+
for (let i = 0, key, node; i < len; i++) {
|
|
1382
|
+
key = keys[i];
|
|
1383
|
+
keyNodes[i] = serializeString(key);
|
|
1384
|
+
node = parseValueAsync(ctx, depth, properties[key]);
|
|
1385
|
+
valueNodes[i] = node instanceof Promise ? await node : node;
|
|
1064
1386
|
}
|
|
1065
1387
|
if (SYM_ITERATOR in properties) {
|
|
1066
1388
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_ITERATOR));
|
|
1067
|
-
valueNodes.push(createIteratorFactoryInstanceNode(parseIteratorFactory(ctx.base), await parseAsync(ctx, depth, createSequenceFromIterable(properties))));
|
|
1389
|
+
valueNodes.push(createIteratorFactoryInstanceNode(28, parseIteratorFactory(ctx.base), await parseAsync(ctx, depth, createSequenceFromIterable(properties))));
|
|
1068
1390
|
}
|
|
1069
1391
|
if (SYM_ASYNC_ITERATOR in properties) {
|
|
1070
1392
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_ASYNC_ITERATOR));
|
|
1071
|
-
valueNodes.push(
|
|
1393
|
+
valueNodes.push(createIteratorFactoryInstanceNode(30, parseAsyncIteratorFactory(ctx.base), await parseAsyncIterable$1(ctx, depth, properties)));
|
|
1072
1394
|
}
|
|
1073
1395
|
if (SYM_TO_STRING_TAG in properties) {
|
|
1074
1396
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_TO_STRING_TAG));
|
|
@@ -1089,166 +1411,183 @@ async function parsePlainObject$1(ctx, depth, id, current, empty) {
|
|
|
1089
1411
|
async function parseBoxed$1(ctx, depth, id, current) {
|
|
1090
1412
|
return createBoxedNode(id, await parseAsync(ctx, depth, current.valueOf()));
|
|
1091
1413
|
}
|
|
1092
|
-
async function
|
|
1093
|
-
current = getArrayBufferView(ctx.base, current);
|
|
1094
|
-
return createTypedArrayNode(id, current, await parseAsync(ctx, depth, current.buffer));
|
|
1095
|
-
}
|
|
1096
|
-
async function parseBigIntTypedArray$1(ctx, depth, id, current) {
|
|
1097
|
-
current = getArrayBufferView(ctx.base, current);
|
|
1098
|
-
return createBigIntTypedArrayNode(id, current, await parseAsync(ctx, depth, current.buffer));
|
|
1099
|
-
}
|
|
1100
|
-
async function parseDataView$1(ctx, depth, id, current) {
|
|
1414
|
+
async function parseView$1(ctx, depth, type, id, current) {
|
|
1101
1415
|
current = getArrayBufferView(ctx.base, current);
|
|
1102
|
-
return
|
|
1416
|
+
return createViewNode(type, id, current, await parseAsync(ctx, depth, current.buffer));
|
|
1103
1417
|
}
|
|
1104
|
-
async function parseError$1(ctx, depth, id, current) {
|
|
1418
|
+
async function parseError$1(ctx, depth, type, id, current) {
|
|
1105
1419
|
const options = getErrorOptions(current, ctx.base.features);
|
|
1106
|
-
return createErrorNode(id, current, options ? await parseProperties$1(ctx, depth, options) : void 0);
|
|
1107
|
-
}
|
|
1108
|
-
async function parseAggregateError$1(ctx, depth, id, current) {
|
|
1109
|
-
const options = getErrorOptions(current, ctx.base.features);
|
|
1110
|
-
return createAggregateErrorNode(id, current, options ? await parseProperties$1(ctx, depth, options) : void 0);
|
|
1420
|
+
return createErrorNode(type, id, current, options ? await parseProperties$1(ctx, depth, options) : void 0);
|
|
1111
1421
|
}
|
|
1112
1422
|
async function parseMap$1(ctx, depth, id, current) {
|
|
1113
|
-
const
|
|
1114
|
-
const
|
|
1423
|
+
const sentinel = parseMapSentinel(ctx.base);
|
|
1424
|
+
const keyNodes = new Array(current.size);
|
|
1425
|
+
const valueNodes = new Array(current.size);
|
|
1426
|
+
let node;
|
|
1427
|
+
let i = 0;
|
|
1115
1428
|
for (const [key, value] of current.entries()) {
|
|
1116
|
-
|
|
1117
|
-
|
|
1429
|
+
node = parseValueAsync(ctx, depth, key);
|
|
1430
|
+
keyNodes[i] = node instanceof Promise ? await node : node;
|
|
1431
|
+
node = parseValueAsync(ctx, depth, value);
|
|
1432
|
+
valueNodes[i] = node instanceof Promise ? await node : node;
|
|
1433
|
+
i++;
|
|
1118
1434
|
}
|
|
1119
|
-
return createMapNode(
|
|
1435
|
+
return createMapNode(id, sentinel, keyNodes, valueNodes);
|
|
1120
1436
|
}
|
|
1121
1437
|
async function parseSet$1(ctx, depth, id, current) {
|
|
1122
|
-
const items =
|
|
1123
|
-
|
|
1438
|
+
const items = new Array(current.size);
|
|
1439
|
+
let node;
|
|
1440
|
+
let i = 0;
|
|
1441
|
+
for (const item of current.keys()) {
|
|
1442
|
+
node = parseValueAsync(ctx, depth, item);
|
|
1443
|
+
items[i++] = node instanceof Promise ? await node : node;
|
|
1444
|
+
}
|
|
1124
1445
|
return createSetNode(id, items);
|
|
1125
1446
|
}
|
|
1126
|
-
async function parsePlugin$1(ctx, depth, id, current) {
|
|
1127
|
-
const currentPlugins = ctx.base.plugins;
|
|
1447
|
+
async function parsePlugin$1(ctx, depth, id, current, currentPlugins) {
|
|
1128
1448
|
if (currentPlugins) for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
1129
1449
|
const plugin = currentPlugins[i];
|
|
1130
|
-
if (plugin.parse.async && plugin.test(current)) return createPluginNode(id, plugin.tag, await plugin.parse.async(current,
|
|
1450
|
+
if (plugin.parse.async && plugin.test(current)) return createPluginNode(id, plugin.tag, await plugin.parse.async(current, {
|
|
1451
|
+
parse: (value) => parseAsync(ctx, depth, value),
|
|
1452
|
+
parseStreamSource(source) {
|
|
1453
|
+
if (depth >= ctx.base.depthLimit) throw new SerovalDepthLimitError(ctx.base.depthLimit);
|
|
1454
|
+
return parseAsyncIterable$1(ctx, depth + 1, source);
|
|
1455
|
+
}
|
|
1456
|
+
}, { id }));
|
|
1131
1457
|
}
|
|
1132
1458
|
}
|
|
1133
1459
|
async function parsePromise$1(ctx, depth, id, current) {
|
|
1134
1460
|
const [status, result] = await promiseToResult(current);
|
|
1135
|
-
return createSerovalNode(12, id, status, void 0, void 0, void 0, void 0, void 0, await parseAsync(ctx, depth, result)
|
|
1461
|
+
return createSerovalNode(12, id, status, void 0, void 0, void 0, void 0, void 0, await parseAsync(ctx, depth, result));
|
|
1136
1462
|
}
|
|
1137
1463
|
function parseStreamHandle(depth, id, current, resolve, reject) {
|
|
1138
1464
|
const sequence = [];
|
|
1139
|
-
|
|
1140
|
-
|
|
1141
|
-
|
|
1142
|
-
|
|
1143
|
-
|
|
1144
|
-
|
|
1145
|
-
|
|
1146
|
-
cleanup();
|
|
1147
|
-
}
|
|
1148
|
-
|
|
1149
|
-
throw: (value) => {
|
|
1150
|
-
markParserRef(this.base, id);
|
|
1151
|
-
parseAsync(this, depth, value).then((data) => {
|
|
1152
|
-
sequence.push(createStreamThrowNode(id, data));
|
|
1153
|
-
resolve(sequence);
|
|
1154
|
-
cleanup();
|
|
1155
|
-
}, (data) => {
|
|
1156
|
-
reject(data);
|
|
1157
|
-
cleanup();
|
|
1158
|
-
});
|
|
1159
|
-
},
|
|
1160
|
-
return: (value) => {
|
|
1161
|
-
markParserRef(this.base, id);
|
|
1162
|
-
parseAsync(this, depth, value).then((data) => {
|
|
1163
|
-
sequence.push(createStreamReturnNode(id, data));
|
|
1164
|
-
resolve(sequence);
|
|
1165
|
-
cleanup();
|
|
1166
|
-
}, (data) => {
|
|
1167
|
-
reject(data);
|
|
1168
|
-
cleanup();
|
|
1169
|
-
});
|
|
1465
|
+
let unparsed = 0;
|
|
1466
|
+
let ended = false;
|
|
1467
|
+
let settled = false;
|
|
1468
|
+
const fail = (error) => {
|
|
1469
|
+
if (!settled) {
|
|
1470
|
+
settled = true;
|
|
1471
|
+
try {
|
|
1472
|
+
cleanup(error);
|
|
1473
|
+
} catch {}
|
|
1474
|
+
reject(error);
|
|
1170
1475
|
}
|
|
1171
|
-
}
|
|
1476
|
+
};
|
|
1477
|
+
const handle = (type) => (value, accept) => {
|
|
1478
|
+
if (settled) return;
|
|
1479
|
+
markParserRef(this.base, id);
|
|
1480
|
+
const slot = sequence.push(void 0) - 1;
|
|
1481
|
+
unparsed++;
|
|
1482
|
+
if (type !== 32) ended = true;
|
|
1483
|
+
parseAsync(this, depth, value).then((data) => {
|
|
1484
|
+
if (!settled) {
|
|
1485
|
+
sequence[slot] = createStreamEventNode(type, id, data);
|
|
1486
|
+
unparsed--;
|
|
1487
|
+
accept?.();
|
|
1488
|
+
if (ended && unparsed === 0) {
|
|
1489
|
+
settled = true;
|
|
1490
|
+
try {
|
|
1491
|
+
cleanup();
|
|
1492
|
+
} catch (error) {
|
|
1493
|
+
reject(error);
|
|
1494
|
+
return;
|
|
1495
|
+
}
|
|
1496
|
+
resolve(sequence);
|
|
1497
|
+
}
|
|
1498
|
+
}
|
|
1499
|
+
}, fail);
|
|
1500
|
+
};
|
|
1501
|
+
const listener = {
|
|
1502
|
+
next: handle(32),
|
|
1503
|
+
throw: handle(33),
|
|
1504
|
+
return: handle(34)
|
|
1505
|
+
};
|
|
1506
|
+
const cleanup = isLiveStream(current) ? current.pump(listener) : current.on(listener);
|
|
1172
1507
|
}
|
|
1173
1508
|
async function parseStream$1(ctx, depth, id, current) {
|
|
1174
1509
|
return createStreamConstructorNode(id, parseSpecialReference(ctx.base, 4), await new Promise(parseStreamHandle.bind(ctx, depth, id, current)));
|
|
1175
1510
|
}
|
|
1511
|
+
/**
|
|
1512
|
+
* Collects an async iterable into a replay node, one value at a time.
|
|
1513
|
+
*/
|
|
1514
|
+
async function parseAsyncIterable$1(ctx, depth, current) {
|
|
1515
|
+
const id = createIndexForValue(ctx.base, {});
|
|
1516
|
+
const reference = parseSpecialReference(ctx.base, 4);
|
|
1517
|
+
const iterator = current[SYM_ASYNC_ITERATOR]();
|
|
1518
|
+
const sequence = [];
|
|
1519
|
+
for (;;) {
|
|
1520
|
+
let result;
|
|
1521
|
+
try {
|
|
1522
|
+
result = await iterator.next();
|
|
1523
|
+
} catch (error) {
|
|
1524
|
+
markParserRef(ctx.base, id);
|
|
1525
|
+
sequence.push(createStreamEventNode(33, id, await parseAsync(ctx, depth, error)));
|
|
1526
|
+
break;
|
|
1527
|
+
}
|
|
1528
|
+
markParserRef(ctx.base, id);
|
|
1529
|
+
let parsed;
|
|
1530
|
+
try {
|
|
1531
|
+
parsed = await parseAsync(ctx, depth, result.value);
|
|
1532
|
+
} catch (error) {
|
|
1533
|
+
Promise.resolve().then(() => iterator.return?.()).catch(() => {});
|
|
1534
|
+
throw error;
|
|
1535
|
+
}
|
|
1536
|
+
sequence.push(createStreamEventNode(result.done ? 34 : 32, id, parsed));
|
|
1537
|
+
if (result.done) break;
|
|
1538
|
+
}
|
|
1539
|
+
return createStreamConstructorNode(id, reference, sequence);
|
|
1540
|
+
}
|
|
1176
1541
|
async function parseSequence$1(ctx, depth, id, current) {
|
|
1177
|
-
const
|
|
1178
|
-
|
|
1542
|
+
const len = current.v.length;
|
|
1543
|
+
const nodes = new Array(len);
|
|
1544
|
+
for (let i = 0, node; i < len; i++) {
|
|
1545
|
+
node = parseValueAsync(ctx, depth, current.v[i]);
|
|
1546
|
+
nodes[i] = node instanceof Promise ? await node : node;
|
|
1547
|
+
}
|
|
1179
1548
|
return createSequenceNode(id, nodes, current.t, current.d);
|
|
1180
1549
|
}
|
|
1181
1550
|
async function parseObjectAsync(ctx, depth, id, current) {
|
|
1182
1551
|
if (Array.isArray(current)) return parseArray$1(ctx, depth, id, current);
|
|
1183
1552
|
if (isStream(current)) return parseStream$1(ctx, depth, id, current);
|
|
1184
1553
|
if (isSequence(current)) return parseSequence$1(ctx, depth, id, current);
|
|
1185
|
-
|
|
1186
|
-
if (currentClass !== void 0 && typeof currentClass !== "function") {
|
|
1187
|
-
const proto = Object.getPrototypeOf(current);
|
|
1188
|
-
currentClass = proto === null ? void 0 : proto.constructor;
|
|
1189
|
-
}
|
|
1554
|
+
const currentClass = getObjectClass(current);
|
|
1190
1555
|
if (currentClass === OpaqueReference) return parseAsync(ctx, depth, current.replacement);
|
|
1191
|
-
const parsed = await parsePlugin$1(ctx, depth, id, current);
|
|
1556
|
+
const parsed = await parsePlugin$1(ctx, depth, id, current, getObjectPlugins(ctx.base, current, currentClass));
|
|
1192
1557
|
if (parsed) return parsed;
|
|
1193
|
-
|
|
1194
|
-
|
|
1195
|
-
case
|
|
1196
|
-
case
|
|
1197
|
-
case
|
|
1198
|
-
case
|
|
1199
|
-
case
|
|
1200
|
-
case
|
|
1201
|
-
case
|
|
1202
|
-
case
|
|
1203
|
-
case
|
|
1204
|
-
case
|
|
1205
|
-
case
|
|
1206
|
-
case
|
|
1207
|
-
case
|
|
1208
|
-
case
|
|
1209
|
-
case
|
|
1210
|
-
|
|
1211
|
-
|
|
1212
|
-
case Uint8Array:
|
|
1213
|
-
case Uint16Array:
|
|
1214
|
-
case Uint32Array:
|
|
1215
|
-
case Uint8ClampedArray:
|
|
1216
|
-
case Float32Array:
|
|
1217
|
-
case Float64Array: return parseTypedArray$1(ctx, depth, id, current);
|
|
1218
|
-
case DataView: return parseDataView$1(ctx, depth, id, current);
|
|
1219
|
-
case Map: return parseMap$1(ctx, depth, id, current);
|
|
1220
|
-
case Set: return parseSet$1(ctx, depth, id, current);
|
|
1221
|
-
}
|
|
1222
|
-
if (currentClass === Promise || current instanceof Promise) return parsePromise$1(ctx, depth, id, current);
|
|
1223
|
-
const currentFeatures = ctx.base.features;
|
|
1224
|
-
if (currentFeatures & 32 && currentClass === RegExp) return createRegExpNode(id, current);
|
|
1225
|
-
if (currentFeatures & 16) switch (currentClass) {
|
|
1226
|
-
case BigInt64Array:
|
|
1227
|
-
case BigUint64Array: return parseBigIntTypedArray$1(ctx, depth, id, current);
|
|
1228
|
-
}
|
|
1229
|
-
if (currentFeatures & 1 && typeof AggregateError !== "undefined" && (currentClass === AggregateError || current instanceof AggregateError)) return parseAggregateError$1(ctx, depth, id, current);
|
|
1230
|
-
if (currentFeatures & 64 && typeof Temporal !== "undefined") switch (currentClass) {
|
|
1231
|
-
case Temporal.Instant: return createTemporalNode(id, 0, current);
|
|
1232
|
-
case Temporal.Duration: return createTemporalNode(id, 1, current);
|
|
1233
|
-
case Temporal.PlainDate: return createTemporalNode(id, 2, current);
|
|
1234
|
-
case Temporal.PlainDateTime: return createTemporalNode(id, 3, current);
|
|
1235
|
-
case Temporal.PlainMonthDay: return createTemporalNode(id, 4, current);
|
|
1236
|
-
case Temporal.PlainTime: return createTemporalNode(id, 5, current);
|
|
1237
|
-
case Temporal.PlainYearMonth: return createTemporalNode(id, 6, current);
|
|
1238
|
-
case Temporal.ZonedDateTime: return createTemporalNode(id, 7, current);
|
|
1239
|
-
}
|
|
1240
|
-
if (current instanceof Error) return parseError$1(ctx, depth, id, current);
|
|
1241
|
-
if (SYM_ITERATOR in current || SYM_ASYNC_ITERATOR in current) return parsePlainObject$1(ctx, depth, id, current, !!currentClass);
|
|
1242
|
-
throw new SerovalUnsupportedTypeError(current);
|
|
1558
|
+
if (currentClass === Object) return parsePlainObject$1(ctx, depth, id, current, false);
|
|
1559
|
+
switch (getObjectKind(current, currentClass, ctx.base.features)) {
|
|
1560
|
+
case 2: return parsePlainObject$1(ctx, depth, id, current, true);
|
|
1561
|
+
case 3: return createDateNode(id, current);
|
|
1562
|
+
case 4: return parseError$1(ctx, depth, 13, id, current);
|
|
1563
|
+
case 5: return parseError$1(ctx, depth, 14, id, current);
|
|
1564
|
+
case 6: return parseBoxed$1(ctx, depth, id, current);
|
|
1565
|
+
case 7: return createArrayBufferNode(ctx.base, id, current);
|
|
1566
|
+
case 8: return parseView$1(ctx, depth, 15, id, current);
|
|
1567
|
+
case 9: return parseView$1(ctx, depth, 16, id, current);
|
|
1568
|
+
case 10: return parseView$1(ctx, depth, 20, id, current);
|
|
1569
|
+
case 11: return parseMap$1(ctx, depth, id, current);
|
|
1570
|
+
case 12: return parseSet$1(ctx, depth, id, current);
|
|
1571
|
+
case 13: return parsePromise$1(ctx, depth, id, current);
|
|
1572
|
+
case 14: return createRegExpNode(id, current);
|
|
1573
|
+
case 15: return createTemporalNode(id, getTemporalType(currentClass), current);
|
|
1574
|
+
case 16: return parsePlainObject$1(ctx, depth, id, current, !!currentClass);
|
|
1575
|
+
default: throw new SerovalUnsupportedTypeError(current);
|
|
1576
|
+
}
|
|
1243
1577
|
}
|
|
1244
1578
|
async function parseFunctionAsync(ctx, depth, current) {
|
|
1245
1579
|
const ref = getReferenceNode(ctx.base, current);
|
|
1246
|
-
if (ref
|
|
1247
|
-
const plugin = await parsePlugin$1(ctx, depth, ref
|
|
1580
|
+
if (typeof ref !== "number") return ref;
|
|
1581
|
+
const plugin = await parsePlugin$1(ctx, depth, ref, current, ctx.base.plugins);
|
|
1248
1582
|
if (plugin) return plugin;
|
|
1249
1583
|
throw new SerovalUnsupportedTypeError(current);
|
|
1250
1584
|
}
|
|
1251
|
-
|
|
1585
|
+
/**
|
|
1586
|
+
* Parses primitives and already-seen values synchronously; only objects and
|
|
1587
|
+
* functions come back as a Promise. Errors are thrown synchronously, which
|
|
1588
|
+
* an async caller turns into a rejection as before.
|
|
1589
|
+
*/
|
|
1590
|
+
function parseValueAsync(ctx, depth, current) {
|
|
1252
1591
|
if (depth >= ctx.base.depthLimit) throw new SerovalDepthLimitError(ctx.base.depthLimit);
|
|
1253
1592
|
switch (typeof current) {
|
|
1254
1593
|
case "boolean": return current ? TRUE_NODE : FALSE_NODE;
|
|
@@ -1259,7 +1598,7 @@ async function parseAsync(ctx, depth, current) {
|
|
|
1259
1598
|
case "object":
|
|
1260
1599
|
if (current) {
|
|
1261
1600
|
const ref = getReferenceNode(ctx.base, current);
|
|
1262
|
-
return ref
|
|
1601
|
+
return typeof ref === "number" ? parseObjectAsync(ctx, depth + 1, ref, current) : ref;
|
|
1263
1602
|
}
|
|
1264
1603
|
return NULL_NODE;
|
|
1265
1604
|
case "symbol": return parseWellKnownSymbol(ctx.base, current);
|
|
@@ -1267,6 +1606,9 @@ async function parseAsync(ctx, depth, current) {
|
|
|
1267
1606
|
default: throw new SerovalUnsupportedTypeError(current);
|
|
1268
1607
|
}
|
|
1269
1608
|
}
|
|
1609
|
+
async function parseAsync(ctx, depth, current) {
|
|
1610
|
+
return await parseValueAsync(ctx, depth, current);
|
|
1611
|
+
}
|
|
1270
1612
|
async function parseTopAsync(ctx, current) {
|
|
1271
1613
|
try {
|
|
1272
1614
|
return await parseAsync(ctx, 0, current);
|
|
@@ -1275,32 +1617,6 @@ async function parseTopAsync(ctx, current) {
|
|
|
1275
1617
|
}
|
|
1276
1618
|
}
|
|
1277
1619
|
//#endregion
|
|
1278
|
-
//#region src/core/plugin.ts
|
|
1279
|
-
let SerovalMode = /* @__PURE__ */ function(SerovalMode) {
|
|
1280
|
-
SerovalMode[SerovalMode["Vanilla"] = 1] = "Vanilla";
|
|
1281
|
-
SerovalMode[SerovalMode["Cross"] = 2] = "Cross";
|
|
1282
|
-
return SerovalMode;
|
|
1283
|
-
}({});
|
|
1284
|
-
function createPlugin(plugin) {
|
|
1285
|
-
return plugin;
|
|
1286
|
-
}
|
|
1287
|
-
function dedupePlugins(deduped, plugins) {
|
|
1288
|
-
for (let i = 0, len = plugins.length; i < len; i++) {
|
|
1289
|
-
const current = plugins[i];
|
|
1290
|
-
if (!deduped.has(current)) {
|
|
1291
|
-
deduped.add(current);
|
|
1292
|
-
if (current.extends) dedupePlugins(deduped, current.extends);
|
|
1293
|
-
}
|
|
1294
|
-
}
|
|
1295
|
-
}
|
|
1296
|
-
function resolvePlugins(plugins) {
|
|
1297
|
-
if (plugins) {
|
|
1298
|
-
const deduped = /* @__PURE__ */ new Set();
|
|
1299
|
-
dedupePlugins(deduped, plugins);
|
|
1300
|
-
return [...deduped];
|
|
1301
|
-
}
|
|
1302
|
-
}
|
|
1303
|
-
//#endregion
|
|
1304
1620
|
//#region src/core/utils/valid-properties.ts
|
|
1305
1621
|
function isValidKey(key) {
|
|
1306
1622
|
switch (key) {
|
|
@@ -1326,7 +1642,6 @@ function isValidSymbol(symbol) {
|
|
|
1326
1642
|
//#endregion
|
|
1327
1643
|
//#region src/core/context/deserializer.ts
|
|
1328
1644
|
const DEFAULT_MAX_BASE64_LENGTH = 1e6;
|
|
1329
|
-
const MIN_NATIVE_BASE64_LENGTH = 512;
|
|
1330
1645
|
const MAX_BIGINT_LENGTH = 1e4;
|
|
1331
1646
|
const MAX_REGEXP_SOURCE_LENGTH = 2e4;
|
|
1332
1647
|
function applyObjectFlag(obj, flag) {
|
|
@@ -1338,68 +1653,48 @@ function applyObjectFlag(obj, flag) {
|
|
|
1338
1653
|
}
|
|
1339
1654
|
}
|
|
1340
1655
|
const DEFAULT_DEPTH_LIMIT = 1e3;
|
|
1341
|
-
function createBaseDeserializerContext(
|
|
1342
|
-
|
|
1343
|
-
const maxBase64Length = (_options$maxBase64Len = options.maxBase64Length) !== null && _options$maxBase64Len !== void 0 ? _options$maxBase64Len : DEFAULT_MAX_BASE64_LENGTH;
|
|
1656
|
+
function createBaseDeserializerContext(options) {
|
|
1657
|
+
const maxBase64Length = options.maxBase64Length ?? DEFAULT_MAX_BASE64_LENGTH;
|
|
1344
1658
|
if (!Number.isSafeInteger(maxBase64Length) || maxBase64Length < 0) throw new RangeError("maxBase64Length must be a non-negative safe integer");
|
|
1345
|
-
const refs = options.refs
|
|
1659
|
+
const refs = options.refs ?? /* @__PURE__ */ new Map();
|
|
1346
1660
|
if (!("types" in refs)) Object.assign(refs, { types: /* @__PURE__ */ new Map() });
|
|
1347
1661
|
return {
|
|
1348
|
-
mode,
|
|
1349
1662
|
plugins: options.plugins,
|
|
1350
1663
|
refs,
|
|
1351
|
-
features:
|
|
1664
|
+
features: options.features ?? 127 ^ (options.disabledFeatures ?? 0),
|
|
1352
1665
|
depthLimit: options.depthLimit || DEFAULT_DEPTH_LIMIT,
|
|
1353
1666
|
maxBase64Length
|
|
1354
1667
|
};
|
|
1355
1668
|
}
|
|
1356
1669
|
function createVanillaDeserializerContext(options) {
|
|
1357
1670
|
return {
|
|
1358
|
-
|
|
1359
|
-
|
|
1360
|
-
child: void 0,
|
|
1361
|
-
state: { marked: new Set(options.markedRefs) }
|
|
1671
|
+
base: createBaseDeserializerContext(options),
|
|
1672
|
+
marked: new Set(options.markedRefs)
|
|
1362
1673
|
};
|
|
1363
1674
|
}
|
|
1364
1675
|
function createCrossDeserializerContext(options) {
|
|
1365
1676
|
return {
|
|
1366
|
-
|
|
1367
|
-
|
|
1368
|
-
child: void 0
|
|
1677
|
+
base: createBaseDeserializerContext(options),
|
|
1678
|
+
marked: void 0
|
|
1369
1679
|
};
|
|
1370
1680
|
}
|
|
1371
|
-
var DeserializePluginContext = class {
|
|
1372
|
-
constructor(_p, depth) {
|
|
1373
|
-
this._p = _p;
|
|
1374
|
-
this.depth = depth;
|
|
1375
|
-
}
|
|
1376
|
-
deserialize(node) {
|
|
1377
|
-
return deserialize$1(this._p, this.depth, node);
|
|
1378
|
-
}
|
|
1379
|
-
};
|
|
1380
1681
|
function guardIndexedValue(ctx, id) {
|
|
1381
|
-
|
|
1682
|
+
const node = {
|
|
1382
1683
|
t: 4,
|
|
1383
1684
|
i: id
|
|
1384
|
-
}
|
|
1385
|
-
if (
|
|
1685
|
+
};
|
|
1686
|
+
if (id < 0 || !Number.isInteger(id)) throw new SerovalMalformedNodeError(node);
|
|
1687
|
+
if (ctx.refs.has(id)) throw new SerovalConflictedNodeIdError(node);
|
|
1386
1688
|
}
|
|
1387
1689
|
function isThennable(value) {
|
|
1388
1690
|
return !!value && (typeof value === "object" || typeof value === "function") && "then" in value && typeof value.then === "function";
|
|
1389
1691
|
}
|
|
1390
|
-
function
|
|
1391
|
-
guardIndexedValue(ctx.base, id);
|
|
1392
|
-
if (ctx.state.marked.has(id)) ctx.base.refs.set(id, value);
|
|
1393
|
-
return value;
|
|
1394
|
-
}
|
|
1395
|
-
function assignIndexedValueCross(ctx, id, value) {
|
|
1692
|
+
function assignIndexedValue$1(ctx, id, value) {
|
|
1396
1693
|
guardIndexedValue(ctx.base, id);
|
|
1397
|
-
ctx.
|
|
1694
|
+
const marked = ctx.marked;
|
|
1695
|
+
if (!marked || marked.has(id)) ctx.base.refs.set(id, value);
|
|
1398
1696
|
return value;
|
|
1399
1697
|
}
|
|
1400
|
-
function assignIndexedValue$1(ctx, id, value) {
|
|
1401
|
-
return ctx.mode === 1 ? assignIndexedValueVanilla(ctx, id, value) : assignIndexedValueCross(ctx, id, value);
|
|
1402
|
-
}
|
|
1403
1698
|
function deserializeKnownValue(node, record, key) {
|
|
1404
1699
|
if (Object.hasOwn(record, key)) return record[key];
|
|
1405
1700
|
throw new SerovalMalformedNodeError(node);
|
|
@@ -1456,7 +1751,8 @@ function deserializeProperties(ctx, depth, node, result) {
|
|
|
1456
1751
|
const keys = node.k;
|
|
1457
1752
|
validateNodeList(node, keys);
|
|
1458
1753
|
validateNodeList(node, node.v);
|
|
1459
|
-
|
|
1754
|
+
const len = keys.length;
|
|
1755
|
+
if (len > 0) for (let i = 0, vals = node.v; i < len; i++) assignProperty(ctx, depth, result, keys[i], vals[i]);
|
|
1460
1756
|
return result;
|
|
1461
1757
|
}
|
|
1462
1758
|
function deserializeObject(ctx, depth, node) {
|
|
@@ -1470,35 +1766,8 @@ function deserializeDate(ctx, node) {
|
|
|
1470
1766
|
}
|
|
1471
1767
|
function deserializeTemporal(ctx, node) {
|
|
1472
1768
|
if (!(ctx.base.features & 64)) throw new SerovalUnsupportedNodeError(node);
|
|
1473
|
-
|
|
1474
|
-
|
|
1475
|
-
case 0:
|
|
1476
|
-
value = Temporal.Instant.from(node.s);
|
|
1477
|
-
break;
|
|
1478
|
-
case 1:
|
|
1479
|
-
value = Temporal.Duration.from(node.s);
|
|
1480
|
-
break;
|
|
1481
|
-
case 2:
|
|
1482
|
-
value = Temporal.PlainDate.from(node.s);
|
|
1483
|
-
break;
|
|
1484
|
-
case 3:
|
|
1485
|
-
value = Temporal.PlainDateTime.from(node.s);
|
|
1486
|
-
break;
|
|
1487
|
-
case 4:
|
|
1488
|
-
value = Temporal.PlainMonthDay.from(node.s);
|
|
1489
|
-
break;
|
|
1490
|
-
case 5:
|
|
1491
|
-
value = Temporal.PlainTime.from(node.s);
|
|
1492
|
-
break;
|
|
1493
|
-
case 6:
|
|
1494
|
-
value = Temporal.PlainYearMonth.from(node.s);
|
|
1495
|
-
break;
|
|
1496
|
-
case 7:
|
|
1497
|
-
value = Temporal.ZonedDateTime.from(node.s);
|
|
1498
|
-
break;
|
|
1499
|
-
default: throw new SerovalMalformedNodeError(node);
|
|
1500
|
-
}
|
|
1501
|
-
return assignIndexedValue$1(ctx, node.i, value);
|
|
1769
|
+
const construct = Temporal[deserializeKnownValue(node, TEMPORAL_TYPE_NAME, node.c)];
|
|
1770
|
+
return assignIndexedValue$1(ctx, node.i, construct.from(node.s));
|
|
1502
1771
|
}
|
|
1503
1772
|
function deserializeRegExp(ctx, node) {
|
|
1504
1773
|
if (ctx.base.features & 32) {
|
|
@@ -1524,32 +1793,15 @@ function deserializeMap(ctx, depth, node) {
|
|
|
1524
1793
|
function deserializeArrayBuffer(ctx, node) {
|
|
1525
1794
|
if (typeof node.s !== "string") throw new SerovalMalformedNodeError(node);
|
|
1526
1795
|
if (node.s.length > ctx.base.maxBase64Length) throw new RangeError("ArrayBuffer exceeds maxBase64Length (" + ctx.base.maxBase64Length + ")");
|
|
1527
|
-
const
|
|
1528
|
-
let buffer;
|
|
1529
|
-
if (source.length < MIN_NATIVE_BASE64_LENGTH || typeof Buffer === "undefined") buffer = ARRAY_BUFFER_CONSTRUCTOR(source);
|
|
1530
|
-
else {
|
|
1531
|
-
const decoded = atob(source);
|
|
1532
|
-
buffer = new ArrayBuffer(decoded.length);
|
|
1533
|
-
Buffer.from(buffer).write(decoded, "latin1");
|
|
1534
|
-
}
|
|
1796
|
+
const buffer = decodeArrayBuffer(deserializeString(node.s));
|
|
1535
1797
|
return assignIndexedValue$1(ctx, node.i, buffer);
|
|
1536
1798
|
}
|
|
1537
|
-
function
|
|
1538
|
-
var _node$b;
|
|
1539
|
-
const construct = getTypedArrayConstructor(node.c);
|
|
1799
|
+
function deserializeView(ctx, depth, node, construct) {
|
|
1540
1800
|
const source = deserialize$1(ctx, depth, node.f);
|
|
1541
1801
|
if (!(source instanceof ArrayBuffer)) throw new SerovalMalformedNodeError(node);
|
|
1542
|
-
const offset =
|
|
1802
|
+
const offset = node.b ?? 0;
|
|
1543
1803
|
if (offset < 0 || offset > source.byteLength) throw new SerovalMalformedNodeError(node);
|
|
1544
|
-
return assignIndexedValue$1(ctx, node.i, new construct(source, offset, node.l));
|
|
1545
|
-
}
|
|
1546
|
-
function deserializeDataView(ctx, depth, node) {
|
|
1547
|
-
var _node$b2;
|
|
1548
|
-
const source = deserialize$1(ctx, depth, node.f);
|
|
1549
|
-
if (!(source instanceof ArrayBuffer)) throw new SerovalMalformedNodeError(node);
|
|
1550
|
-
const offset = (_node$b2 = node.b) !== null && _node$b2 !== void 0 ? _node$b2 : 0;
|
|
1551
|
-
if (offset < 0 || offset > source.byteLength) throw new SerovalMalformedNodeError(node);
|
|
1552
|
-
return assignIndexedValue$1(ctx, node.i, new DataView(source, offset, node.l));
|
|
1804
|
+
return assignIndexedValue$1(ctx, node.i, construct ? new construct(source, offset, node.l) : new DataView(source, offset, node.l));
|
|
1553
1805
|
}
|
|
1554
1806
|
function deserializeDictionary(ctx, depth, node, result) {
|
|
1555
1807
|
if (node.p) {
|
|
@@ -1583,7 +1835,7 @@ function deserializePlugin(ctx, depth, node) {
|
|
|
1583
1835
|
const tag = deserializeString(node.c);
|
|
1584
1836
|
for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
1585
1837
|
const plugin = currentPlugins[i];
|
|
1586
|
-
if (plugin.tag === tag) return assignIndexedValue$1(ctx, node.i, plugin.deserialize(node.s,
|
|
1838
|
+
if (plugin.tag === tag) return assignIndexedValue$1(ctx, node.i, plugin.deserialize(node.s, { deserialize: (current) => deserialize$1(ctx, depth, current) }, { id: node.i }));
|
|
1587
1839
|
}
|
|
1588
1840
|
}
|
|
1589
1841
|
throw new SerovalMissingPluginError(node.c);
|
|
@@ -1591,6 +1843,7 @@ function deserializePlugin(ctx, depth, node) {
|
|
|
1591
1843
|
function deserializePromiseConstructor(ctx, node) {
|
|
1592
1844
|
const value = assignIndexedValue$1(ctx, node.i, assignIndexedValue$1(ctx, node.s, PROMISE_CONSTRUCTOR()).p);
|
|
1593
1845
|
assignNodeType(ctx, node.s, 22);
|
|
1846
|
+
ctx.base.pending?.add(node.s);
|
|
1594
1847
|
return value;
|
|
1595
1848
|
}
|
|
1596
1849
|
function deserializePromiseFulfill(ctx, depth, node) {
|
|
@@ -1601,6 +1854,7 @@ function deserializePromiseFulfill(ctx, depth, node) {
|
|
|
1601
1854
|
if (isThennable(deserialized)) throw new SerovalMalformedNodeError(node.a[1]);
|
|
1602
1855
|
if (node.t === 23) deferred.s(deserialized);
|
|
1603
1856
|
else deferred.f(deserialized);
|
|
1857
|
+
ctx.base.pending?.delete(node.i);
|
|
1604
1858
|
return;
|
|
1605
1859
|
}
|
|
1606
1860
|
throw new SerovalMissingInstanceError("Promise");
|
|
@@ -1618,37 +1872,21 @@ function deserializeAsyncIteratorFactoryInstance(ctx, depth, node) {
|
|
|
1618
1872
|
return streamToAsyncIterable(source);
|
|
1619
1873
|
}
|
|
1620
1874
|
function deserializeStreamConstructor(ctx, depth, node) {
|
|
1621
|
-
const result = assignIndexedValue$1(ctx, node.i,
|
|
1875
|
+
const result = assignIndexedValue$1(ctx, node.i, new Stream(node.l === 1 ? 1 : void 0));
|
|
1622
1876
|
assignNodeType(ctx, node.i, 31);
|
|
1877
|
+
ctx.base.pending?.add(node.i);
|
|
1623
1878
|
const items = node.a;
|
|
1624
1879
|
validateNodeList(node, items);
|
|
1625
1880
|
const len = items.length;
|
|
1626
1881
|
if (len) for (let i = 0; i < len; i++) deserialize$1(ctx, depth, items[i]);
|
|
1627
1882
|
return result;
|
|
1628
1883
|
}
|
|
1629
|
-
function
|
|
1630
|
-
const deferred = ctx.base.refs.get(node.i);
|
|
1631
|
-
if (deferred) {
|
|
1632
|
-
validateNodeType(ctx, node, node.i, 31);
|
|
1633
|
-
deferred.next(deserialize$1(ctx, depth, node.f));
|
|
1634
|
-
return;
|
|
1635
|
-
}
|
|
1636
|
-
throw new SerovalMissingInstanceError("Stream");
|
|
1637
|
-
}
|
|
1638
|
-
function deserializeStreamThrow(ctx, depth, node) {
|
|
1639
|
-
const deferred = ctx.base.refs.get(node.i);
|
|
1640
|
-
if (deferred) {
|
|
1641
|
-
validateNodeType(ctx, node, node.i, 31);
|
|
1642
|
-
deferred.throw(deserialize$1(ctx, depth, node.f));
|
|
1643
|
-
return;
|
|
1644
|
-
}
|
|
1645
|
-
throw new SerovalMissingInstanceError("Stream");
|
|
1646
|
-
}
|
|
1647
|
-
function deserializeStreamReturn(ctx, depth, node) {
|
|
1884
|
+
function deserializeStreamCall(ctx, depth, node, method) {
|
|
1648
1885
|
const deferred = ctx.base.refs.get(node.i);
|
|
1649
1886
|
if (deferred) {
|
|
1650
1887
|
validateNodeType(ctx, node, node.i, 31);
|
|
1651
|
-
deferred
|
|
1888
|
+
deferred[method](deserialize$1(ctx, depth, node.f));
|
|
1889
|
+
if (method !== "next") ctx.base.pending?.delete(node.i);
|
|
1652
1890
|
return;
|
|
1653
1891
|
}
|
|
1654
1892
|
throw new SerovalMissingInstanceError("Stream");
|
|
@@ -1667,6 +1905,7 @@ function deserializeSequence(ctx, depth, node) {
|
|
|
1667
1905
|
const size = node.a.length;
|
|
1668
1906
|
if (!(isSequenceIndex(node.s, size) && isSequenceIndex(node.l, size))) throw new SerovalMalformedNodeError(node);
|
|
1669
1907
|
const result = assignIndexedValue$1(ctx, node.i, createSequence([], node.s, node.l));
|
|
1908
|
+
assignNodeType(ctx, node.i, 35);
|
|
1670
1909
|
for (let i = 0; i < size; i++) result.v[i] = deserialize$1(ctx, depth, node.a[i]);
|
|
1671
1910
|
return result;
|
|
1672
1911
|
}
|
|
@@ -1691,8 +1930,8 @@ function deserialize$1(ctx, depth, node) {
|
|
|
1691
1930
|
case 8: return deserializeMap(ctx, depth, node);
|
|
1692
1931
|
case 19: return deserializeArrayBuffer(ctx, node);
|
|
1693
1932
|
case 16:
|
|
1694
|
-
case 15: return
|
|
1695
|
-
case 20: return
|
|
1933
|
+
case 15: return deserializeView(ctx, depth, node, getTypedArrayConstructor(node.c));
|
|
1934
|
+
case 20: return deserializeView(ctx, depth, node);
|
|
1696
1935
|
case 14: return deserializeAggregateError(ctx, depth, node);
|
|
1697
1936
|
case 13: return deserializeError(ctx, depth, node);
|
|
1698
1937
|
case 12: return deserializePromise(ctx, depth, node);
|
|
@@ -1705,9 +1944,9 @@ function deserialize$1(ctx, depth, node) {
|
|
|
1705
1944
|
case 28: return deserializeIteratorFactoryInstance(ctx, depth, node);
|
|
1706
1945
|
case 30: return deserializeAsyncIteratorFactoryInstance(ctx, depth, node);
|
|
1707
1946
|
case 31: return deserializeStreamConstructor(ctx, depth, node);
|
|
1708
|
-
case 32: return
|
|
1709
|
-
case 33: return
|
|
1710
|
-
case 34: return
|
|
1947
|
+
case 32: return deserializeStreamCall(ctx, depth, node, "next");
|
|
1948
|
+
case 33: return deserializeStreamCall(ctx, depth, node, "throw");
|
|
1949
|
+
case 34: return deserializeStreamCall(ctx, depth, node, "return");
|
|
1711
1950
|
case 27: return deserializeIteratorFactory(ctx, depth, node);
|
|
1712
1951
|
case 29: return deserializeAsyncIteratorFactory(ctx, depth, node);
|
|
1713
1952
|
case 35: return deserializeSequence(ctx, depth, node);
|
|
@@ -1722,11 +1961,31 @@ function deserializeTop(ctx, node) {
|
|
|
1722
1961
|
throw new SerovalDeserializationError(error);
|
|
1723
1962
|
}
|
|
1724
1963
|
}
|
|
1964
|
+
/**
|
|
1965
|
+
* Rejects every pending promise and throws into every open stream tracked
|
|
1966
|
+
* by `ctx.base.pending`, then drops the bookkeeping so the context no longer
|
|
1967
|
+
* accepts deferred values. Does nothing once the bookkeeping is gone.
|
|
1968
|
+
*/
|
|
1969
|
+
function abortDeferred(ctx, reason) {
|
|
1970
|
+
const pending = ctx.base.pending;
|
|
1971
|
+
if (pending) {
|
|
1972
|
+
ctx.base.pending = void 0;
|
|
1973
|
+
const refs = ctx.base.refs;
|
|
1974
|
+
const errors = [];
|
|
1975
|
+
for (const id of pending) try {
|
|
1976
|
+
const value = refs.get(id);
|
|
1977
|
+
if (refs.types.get(id) === 22) value.f(reason);
|
|
1978
|
+
else value.throw(reason);
|
|
1979
|
+
} catch (error) {
|
|
1980
|
+
errors.push(error);
|
|
1981
|
+
}
|
|
1982
|
+
if (errors.length) throw errors[0];
|
|
1983
|
+
}
|
|
1984
|
+
}
|
|
1725
1985
|
//#endregion
|
|
1726
1986
|
//#region src/core/function-string.ts
|
|
1727
1987
|
const RETURN = () => T;
|
|
1728
|
-
const
|
|
1729
|
-
const IS_MODERN = /* @__PURE__ */ /=>/.test(SERIALIZED_RETURN);
|
|
1988
|
+
const IS_MODERN = /* @__PURE__ */ (/* @__PURE__ */ RETURN.toString()).includes("=>");
|
|
1730
1989
|
function createFunction(parameters, body) {
|
|
1731
1990
|
if (IS_MODERN) return (parameters.length === 1 ? parameters[0] : "(" + parameters.join(",") + ")") + "=>" + (body.startsWith("{") ? "(" + body + ")" : body);
|
|
1732
1991
|
return "function(" + parameters.join(",") + "){return " + body + "}";
|
|
@@ -1754,10 +2013,13 @@ function getIdentifier(index) {
|
|
|
1754
2013
|
}
|
|
1755
2014
|
//#endregion
|
|
1756
2015
|
//#region src/core/utils/is-valid-identifier.ts
|
|
1757
|
-
const IDENTIFIER_CHECK = /^[$A-Z_][0-9A-Z_$]*$/i;
|
|
1758
2016
|
function isValidIdentifier(name) {
|
|
1759
|
-
const
|
|
1760
|
-
|
|
2017
|
+
const len = name.length;
|
|
2018
|
+
for (let i = 0; i < len; i++) {
|
|
2019
|
+
const code = name.charCodeAt(i);
|
|
2020
|
+
if (!(code >= 97 && code <= 122 || code >= 65 && code <= 90 || code >= 48 && code <= 57 && i > 0 || code === 95 || code === 36)) return false;
|
|
2021
|
+
}
|
|
2022
|
+
return len > 0;
|
|
1761
2023
|
}
|
|
1762
2024
|
//#endregion
|
|
1763
2025
|
//#region src/core/context/serializer.ts
|
|
@@ -1770,51 +2032,32 @@ function getAssignmentExpression(assignment) {
|
|
|
1770
2032
|
case 4: return "Object.defineProperty(" + assignment.s + ",\"__proto__\",{value:" + assignment.k + ",configurable:!0,enumerable:!0,writable:!0})";
|
|
1771
2033
|
}
|
|
1772
2034
|
}
|
|
1773
|
-
|
|
1774
|
-
|
|
1775
|
-
|
|
1776
|
-
|
|
1777
|
-
|
|
1778
|
-
|
|
1779
|
-
|
|
1780
|
-
|
|
1781
|
-
|
|
1782
|
-
|
|
1783
|
-
|
|
1784
|
-
|
|
1785
|
-
|
|
1786
|
-
|
|
1787
|
-
|
|
1788
|
-
|
|
1789
|
-
|
|
1790
|
-
else if (item.t === 1 && item.s === prev.s) current = {
|
|
1791
|
-
t: 1,
|
|
1792
|
-
s: getAssignmentExpression(current),
|
|
1793
|
-
k: void 0,
|
|
1794
|
-
v: item.v
|
|
1795
|
-
};
|
|
1796
|
-
else if (item.t === 3 && item.s === prev.s) current = {
|
|
1797
|
-
t: 3,
|
|
1798
|
-
s: getAssignmentExpression(current),
|
|
1799
|
-
k: item.k,
|
|
1800
|
-
v: void 0
|
|
1801
|
-
};
|
|
2035
|
+
const MAX_ASSIGNMENT_CHAIN_LENGTH = 100;
|
|
2036
|
+
function resolveAssignments(assignments) {
|
|
2037
|
+
if (!assignments.length) return void 0;
|
|
2038
|
+
let previous = assignments[0];
|
|
2039
|
+
let expression = getAssignmentExpression(previous);
|
|
2040
|
+
let result = "";
|
|
2041
|
+
let chainLength = 1;
|
|
2042
|
+
for (let index = 1, length = assignments.length; index < length; index++) {
|
|
2043
|
+
const assignment = assignments[index];
|
|
2044
|
+
if (chainLength === MAX_ASSIGNMENT_CHAIN_LENGTH) {
|
|
2045
|
+
result += expression + ",";
|
|
2046
|
+
expression = getAssignmentExpression(assignment);
|
|
2047
|
+
chainLength = 0;
|
|
2048
|
+
} else if (assignment.t === 0 && previous.t === 0 && assignment.v === previous.v) expression = assignment.s + "=" + expression;
|
|
2049
|
+
else if (assignment.t === 2 && previous.t === 2 && assignment.s === previous.s) expression += ".set(" + assignment.k + "," + assignment.v + ")";
|
|
2050
|
+
else if (assignment.t === 1 && previous.t === 1 && assignment.s === previous.s) expression += ".add(" + assignment.v + ")";
|
|
2051
|
+
else if (assignment.t === 3 && previous.t === 2 && assignment.s === previous.s) expression += ".delete(" + assignment.k + ")";
|
|
1802
2052
|
else {
|
|
1803
|
-
|
|
1804
|
-
|
|
2053
|
+
result += expression + ",";
|
|
2054
|
+
expression = getAssignmentExpression(assignment);
|
|
2055
|
+
chainLength = 0;
|
|
1805
2056
|
}
|
|
1806
|
-
|
|
1807
|
-
|
|
1808
|
-
newAssignments.push(current);
|
|
1809
|
-
return newAssignments;
|
|
1810
|
-
}
|
|
1811
|
-
function resolveAssignments(assignments) {
|
|
1812
|
-
if (assignments.length) {
|
|
1813
|
-
let result = "";
|
|
1814
|
-
const merged = mergeAssignments(assignments);
|
|
1815
|
-
for (let i = 0, len = merged.length; i < len; i++) result += getAssignmentExpression(merged[i]) + ",";
|
|
1816
|
-
return result;
|
|
2057
|
+
chainLength++;
|
|
2058
|
+
previous = assignment;
|
|
1817
2059
|
}
|
|
2060
|
+
return result + expression + ",";
|
|
1818
2061
|
}
|
|
1819
2062
|
const NULL_CONSTRUCTOR = "Object.create(null)";
|
|
1820
2063
|
const SET_CONSTRUCTOR = "new Set";
|
|
@@ -1832,42 +2075,34 @@ function createBaseSerializerContext(mode, options) {
|
|
|
1832
2075
|
mode,
|
|
1833
2076
|
plugins: options.plugins,
|
|
1834
2077
|
features: options.features,
|
|
1835
|
-
marked: new Set(options.markedRefs),
|
|
2078
|
+
marked: Array.isArray(options.markedRefs) ? new Set(options.markedRefs) : options.markedRefs,
|
|
1836
2079
|
stack: [],
|
|
1837
2080
|
flags: [],
|
|
1838
|
-
assignments: []
|
|
2081
|
+
assignments: [],
|
|
2082
|
+
assignAll: mode === 2 && !options.assignSharedRefsOnly
|
|
1839
2083
|
};
|
|
1840
2084
|
}
|
|
1841
2085
|
function createVanillaSerializerState() {
|
|
1842
2086
|
return {
|
|
1843
2087
|
valid: /* @__PURE__ */ new Map(),
|
|
1844
|
-
vars: []
|
|
2088
|
+
vars: [],
|
|
2089
|
+
sentinels: /* @__PURE__ */ new Set()
|
|
1845
2090
|
};
|
|
1846
2091
|
}
|
|
1847
2092
|
function createVanillaSerializerContext(options) {
|
|
1848
2093
|
return {
|
|
1849
2094
|
mode: 1,
|
|
1850
2095
|
base: createBaseSerializerContext(1, options),
|
|
1851
|
-
state: createVanillaSerializerState()
|
|
1852
|
-
child: void 0
|
|
2096
|
+
state: createVanillaSerializerState()
|
|
1853
2097
|
};
|
|
1854
2098
|
}
|
|
1855
2099
|
function createCrossSerializerContext(options) {
|
|
1856
2100
|
return {
|
|
1857
2101
|
mode: 2,
|
|
1858
2102
|
base: createBaseSerializerContext(2, options),
|
|
1859
|
-
state: options
|
|
1860
|
-
child: void 0
|
|
2103
|
+
state: options
|
|
1861
2104
|
};
|
|
1862
2105
|
}
|
|
1863
|
-
var SerializePluginContext = class {
|
|
1864
|
-
constructor(_p) {
|
|
1865
|
-
this._p = _p;
|
|
1866
|
-
}
|
|
1867
|
-
serialize(node) {
|
|
1868
|
-
return serialize$1(this._p, node);
|
|
1869
|
-
}
|
|
1870
|
-
};
|
|
1871
2106
|
/**
|
|
1872
2107
|
* Creates the reference param (identifier) from the given reference ID
|
|
1873
2108
|
* Calling this function means the value has been referenced somewhere
|
|
@@ -1975,7 +2210,7 @@ function createArrayAssign(ctx, ref, index, value) {
|
|
|
1975
2210
|
createAssignment(ctx.base, getRefParam(ctx, ref) + "[" + index + "]", value);
|
|
1976
2211
|
}
|
|
1977
2212
|
function createObjectAssign(ctx, ref, key, value) {
|
|
1978
|
-
if (
|
|
2213
|
+
if (key === "__proto__") {
|
|
1979
2214
|
ctx.base.assignments.push({
|
|
1980
2215
|
t: 4,
|
|
1981
2216
|
s: getRefParam(ctx, ref),
|
|
@@ -1993,17 +2228,42 @@ function createSequenceAssign(ctx, ref, index, value) {
|
|
|
1993
2228
|
* Checks if the value is in the stack. Stack here is a reference
|
|
1994
2229
|
* structure to know if a object is to be accessed in a TDZ.
|
|
1995
2230
|
*/
|
|
2231
|
+
function getKeyKind(key) {
|
|
2232
|
+
const first = key.charCodeAt(0);
|
|
2233
|
+
if (first >= 48 && first <= 57) {
|
|
2234
|
+
const check = Number(key);
|
|
2235
|
+
return check >= 0 && check.toString() === key ? 2 : 0;
|
|
2236
|
+
}
|
|
2237
|
+
if (key === "Infinity") return 2;
|
|
2238
|
+
return isValidIdentifier(key) ? 1 : 0;
|
|
2239
|
+
}
|
|
1996
2240
|
function isIndexedValueInStack(ctx, node) {
|
|
1997
2241
|
return node.t === 4 && ctx.stack.includes(node.i);
|
|
1998
2242
|
}
|
|
1999
2243
|
/**
|
|
2244
|
+
* Checks if the node, or any node inside it, is read from more than one
|
|
2245
|
+
* place. Such a node must not be created inside a deferred assignment,
|
|
2246
|
+
* because the places that read it may run before the assignment does.
|
|
2247
|
+
*/
|
|
2248
|
+
function hasMarkedNode(ctx, node) {
|
|
2249
|
+
if (Array.isArray(node)) {
|
|
2250
|
+
for (let i = 0, len = node.length; i < len; i++) if (hasMarkedNode(ctx, node[i])) return true;
|
|
2251
|
+
return false;
|
|
2252
|
+
}
|
|
2253
|
+
if (node == null || typeof node !== "object") return false;
|
|
2254
|
+
const current = node;
|
|
2255
|
+
if (current.t !== 4 && typeof current.i === "number" && isSerializerRefMarked(ctx, current.i)) return true;
|
|
2256
|
+
for (const key in current) if (hasMarkedNode(ctx, current[key])) return true;
|
|
2257
|
+
return false;
|
|
2258
|
+
}
|
|
2259
|
+
/**
|
|
2000
2260
|
* Produces an assignment expression. `id` generates a reference
|
|
2001
2261
|
* parameter (through `getRefParam`) and has the option to
|
|
2002
2262
|
* return the reference parameter directly or assign a value to
|
|
2003
2263
|
* it.
|
|
2004
2264
|
*/
|
|
2005
2265
|
function assignIndexedValue(ctx, index, value) {
|
|
2006
|
-
if (ctx.
|
|
2266
|
+
if (!ctx.base.assignAll && !isSerializerRefMarked(ctx.base, index)) return value;
|
|
2007
2267
|
/**
|
|
2008
2268
|
* In cross-reference, we have to assume that
|
|
2009
2269
|
* every reference are going to be referenced
|
|
@@ -2011,12 +2271,13 @@ function assignIndexedValue(ctx, index, value) {
|
|
|
2011
2271
|
* all of it into the reference array.
|
|
2012
2272
|
*
|
|
2013
2273
|
* otherwise in vanilla, we only do this if it
|
|
2014
|
-
* is actually referenced
|
|
2274
|
+
* is actually referenced. `assignSharedRefsOnly` gives cross-reference
|
|
2275
|
+
* output the vanilla behavior.
|
|
2015
2276
|
*/
|
|
2016
2277
|
return getRefParam(ctx, index) + "=" + value;
|
|
2017
2278
|
}
|
|
2018
2279
|
function serializeReference(node) {
|
|
2019
|
-
return "
|
|
2280
|
+
return REFERENCES_KEY + ".get(\"" + node.s + "\")";
|
|
2020
2281
|
}
|
|
2021
2282
|
function serializeArrayItem(ctx, id, item, index) {
|
|
2022
2283
|
if (item) {
|
|
@@ -2050,16 +2311,15 @@ function serializeArray(ctx, node) {
|
|
|
2050
2311
|
}
|
|
2051
2312
|
function serializeProperty(ctx, source, key, val) {
|
|
2052
2313
|
if (typeof key === "string") {
|
|
2053
|
-
const
|
|
2054
|
-
const isIdentifier = check >= 0 && check.toString() === key || isValidIdentifier(key);
|
|
2314
|
+
const kind = getKeyKind(key);
|
|
2055
2315
|
if (isIndexedValueInStack(ctx.base, val)) {
|
|
2056
2316
|
const refParam = getRefParam(ctx, val.i);
|
|
2057
2317
|
markSerializerRef(ctx.base, source.i);
|
|
2058
|
-
if (
|
|
2059
|
-
else createArrayAssign(ctx, source.i,
|
|
2318
|
+
if (kind === 1) createObjectAssign(ctx, source.i, key, refParam);
|
|
2319
|
+
else createArrayAssign(ctx, source.i, kind === 2 ? key : "\"" + key + "\"", refParam);
|
|
2060
2320
|
return "";
|
|
2061
2321
|
}
|
|
2062
|
-
if (
|
|
2322
|
+
if (key !== "__proto__") return (kind === 0 ? "\"" + key + "\"" : key) + ":" + serialize$1(ctx, val);
|
|
2063
2323
|
return "[\"" + key + "\"]:" + serialize$1(ctx, val);
|
|
2064
2324
|
}
|
|
2065
2325
|
return "[" + serialize$1(ctx, key) + "]:" + serialize$1(ctx, val);
|
|
@@ -2071,7 +2331,7 @@ function serializeProperties(ctx, source, record) {
|
|
|
2071
2331
|
const values = record.v;
|
|
2072
2332
|
ctx.base.stack.push(source.i);
|
|
2073
2333
|
let result = serializeProperty(ctx, source, keys[0], values[0]);
|
|
2074
|
-
for (let i = 1, item
|
|
2334
|
+
for (let i = 1, item; i < len; i++) {
|
|
2075
2335
|
item = serializeProperty(ctx, source, keys[i], values[i]);
|
|
2076
2336
|
result += (item && result && ",") + item;
|
|
2077
2337
|
}
|
|
@@ -2092,18 +2352,14 @@ function serializeWithObjectAssign(ctx, source, value, serialized) {
|
|
|
2092
2352
|
function serializeStringKeyAssignment(ctx, source, mainAssignments, key, value) {
|
|
2093
2353
|
const base = ctx.base;
|
|
2094
2354
|
const serialized = serialize$1(ctx, value);
|
|
2095
|
-
const
|
|
2096
|
-
|
|
2097
|
-
|
|
2098
|
-
|
|
2099
|
-
|
|
2100
|
-
|
|
2101
|
-
|
|
2102
|
-
|
|
2103
|
-
if (isIdentifier && check !== check) createObjectAssign(ctx, source.i, key, serialized);
|
|
2104
|
-
else createArrayAssign(ctx, source.i, isIdentifier ? key : "\"" + key + "\"", serialized);
|
|
2105
|
-
base.assignments = parentAssignment;
|
|
2106
|
-
}
|
|
2355
|
+
const parentAssignment = base.assignments;
|
|
2356
|
+
if (!isIndexedValueInStack(base, value)) base.assignments = mainAssignments;
|
|
2357
|
+
createKeyAssign(ctx, source.i, getKeyKind(key), key, serialized);
|
|
2358
|
+
base.assignments = parentAssignment;
|
|
2359
|
+
}
|
|
2360
|
+
function createKeyAssign(ctx, ref, kind, key, value) {
|
|
2361
|
+
if (kind === 1) createObjectAssign(ctx, ref, key, value);
|
|
2362
|
+
else createArrayAssign(ctx, ref, kind === 2 ? key : "\"" + key + "\"", value);
|
|
2107
2363
|
}
|
|
2108
2364
|
function serializeAssignment(ctx, source, mainAssignments, key, value) {
|
|
2109
2365
|
if (typeof key === "string") serializeStringKeyAssignment(ctx, source, mainAssignments, key, value);
|
|
@@ -2134,7 +2390,7 @@ function serializeAssignments(ctx, source, node) {
|
|
|
2134
2390
|
function serializeDictionary(ctx, node, init) {
|
|
2135
2391
|
if (node.p) {
|
|
2136
2392
|
const base = ctx.base;
|
|
2137
|
-
if (base.features & 8) init = serializeWithObjectAssign(ctx, node, node.p, init);
|
|
2393
|
+
if (base.features & 8 && !node.p.k.includes("__proto__")) init = serializeWithObjectAssign(ctx, node, node.p, init);
|
|
2138
2394
|
else {
|
|
2139
2395
|
markSerializerRef(base, node.i);
|
|
2140
2396
|
const assignments = serializeAssignments(ctx, node, node.p);
|
|
@@ -2150,18 +2406,8 @@ function serializeNullConstructor(ctx, node) {
|
|
|
2150
2406
|
function serializeDate(node) {
|
|
2151
2407
|
return "new Date(\"" + node.s + "\")";
|
|
2152
2408
|
}
|
|
2153
|
-
const TEMPORAL_CONSTRUCTOR = {
|
|
2154
|
-
[0]: "Temporal.Instant",
|
|
2155
|
-
[1]: "Temporal.Duration",
|
|
2156
|
-
[2]: "Temporal.PlainDate",
|
|
2157
|
-
[3]: "Temporal.PlainDateTime",
|
|
2158
|
-
[4]: "Temporal.PlainMonthDay",
|
|
2159
|
-
[5]: "Temporal.PlainTime",
|
|
2160
|
-
[6]: "Temporal.PlainYearMonth",
|
|
2161
|
-
[7]: "Temporal.ZonedDateTime"
|
|
2162
|
-
};
|
|
2163
2409
|
function serializeTemporal(ctx, node) {
|
|
2164
|
-
if (ctx.base.features & 64) return
|
|
2410
|
+
if (ctx.base.features & 64) return "Temporal." + TEMPORAL_TYPE_NAME[node.c] + ".from(\"" + node.s + "\")";
|
|
2165
2411
|
throw new SerovalUnsupportedNodeError(node);
|
|
2166
2412
|
}
|
|
2167
2413
|
function serializeRegExp(ctx, node) {
|
|
@@ -2188,7 +2434,7 @@ function serializeSet(ctx, node) {
|
|
|
2188
2434
|
if (size > 0) {
|
|
2189
2435
|
ctx.base.stack.push(id);
|
|
2190
2436
|
let result = serializeSetItem(ctx, id, items[0]);
|
|
2191
|
-
for (let i = 1, item
|
|
2437
|
+
for (let i = 1, item; i < size; i++) {
|
|
2192
2438
|
item = serializeSetItem(ctx, id, items[i]);
|
|
2193
2439
|
result += (item && result && ",") + item;
|
|
2194
2440
|
}
|
|
@@ -2197,7 +2443,7 @@ function serializeSet(ctx, node) {
|
|
|
2197
2443
|
}
|
|
2198
2444
|
return serialized;
|
|
2199
2445
|
}
|
|
2200
|
-
function serializeMapEntry(ctx, id, key, val,
|
|
2446
|
+
function serializeMapEntry(ctx, id, key, val, getSentinel) {
|
|
2201
2447
|
const base = ctx.base;
|
|
2202
2448
|
if (isIndexedValueInStack(base, key)) {
|
|
2203
2449
|
const keyRef = getRefParam(ctx, key.i);
|
|
@@ -2206,7 +2452,9 @@ function serializeMapEntry(ctx, id, key, val, sentinel) {
|
|
|
2206
2452
|
createSetAssignment(ctx, id, keyRef, getRefParam(ctx, val.i));
|
|
2207
2453
|
return "";
|
|
2208
2454
|
}
|
|
2209
|
-
if (val.t !== 4 && val.i != null &&
|
|
2455
|
+
if (val.t !== 4 && val.i != null && hasMarkedNode(base, val)) {
|
|
2456
|
+
markSerializerRef(base, val.i);
|
|
2457
|
+
const sentinel = getSentinel();
|
|
2210
2458
|
const serialized = "(" + serialize$1(ctx, val) + ",[" + sentinel + "," + sentinel + "])";
|
|
2211
2459
|
createSetAssignment(ctx, id, keyRef, getRefParam(ctx, val.i));
|
|
2212
2460
|
createDeleteAssignment(ctx, id, sentinel);
|
|
@@ -2221,7 +2469,9 @@ function serializeMapEntry(ctx, id, key, val, sentinel) {
|
|
|
2221
2469
|
if (isIndexedValueInStack(base, val)) {
|
|
2222
2470
|
const valueRef = getRefParam(ctx, val.i);
|
|
2223
2471
|
markSerializerRef(base, id);
|
|
2224
|
-
if (key.t !== 4 && key.i != null &&
|
|
2472
|
+
if (key.t !== 4 && key.i != null && hasMarkedNode(base, key)) {
|
|
2473
|
+
markSerializerRef(base, key.i);
|
|
2474
|
+
const sentinel = getSentinel();
|
|
2225
2475
|
const serialized = "(" + serialize$1(ctx, key) + ",[" + sentinel + "," + sentinel + "])";
|
|
2226
2476
|
createSetAssignment(ctx, id, getRefParam(ctx, key.i), valueRef);
|
|
2227
2477
|
createDeleteAssignment(ctx, id, sentinel);
|
|
@@ -2241,20 +2491,27 @@ function serializeMap(ctx, node) {
|
|
|
2241
2491
|
const size = keys.length;
|
|
2242
2492
|
const id = node.i;
|
|
2243
2493
|
const sentinel = node.f;
|
|
2244
|
-
|
|
2494
|
+
let sentinelRef;
|
|
2495
|
+
const getSentinel = () => {
|
|
2496
|
+
if (sentinelRef == null) {
|
|
2497
|
+
sentinelRef = getRefParam(ctx, sentinel.i);
|
|
2498
|
+
if (ctx.mode === 1) ctx.state.sentinels.add(ctx.state.valid.get(sentinel.i));
|
|
2499
|
+
}
|
|
2500
|
+
return sentinelRef;
|
|
2501
|
+
};
|
|
2245
2502
|
const base = ctx.base;
|
|
2246
2503
|
if (size > 0) {
|
|
2247
2504
|
const vals = node.e.v;
|
|
2248
2505
|
base.stack.push(id);
|
|
2249
|
-
let result = serializeMapEntry(ctx, id, keys[0], vals[0],
|
|
2250
|
-
for (let i = 1, item
|
|
2251
|
-
item = serializeMapEntry(ctx, id, keys[i], vals[i],
|
|
2506
|
+
let result = serializeMapEntry(ctx, id, keys[0], vals[0], getSentinel);
|
|
2507
|
+
for (let i = 1, item; i < size; i++) {
|
|
2508
|
+
item = serializeMapEntry(ctx, id, keys[i], vals[i], getSentinel);
|
|
2252
2509
|
result += (item && result && ",") + item;
|
|
2253
2510
|
}
|
|
2254
2511
|
base.stack.pop();
|
|
2255
2512
|
if (result) serialized += "([" + result + "])";
|
|
2256
2513
|
}
|
|
2257
|
-
if (sentinel.t === 26) {
|
|
2514
|
+
if (ctx.mode === 2 && sentinel.t === 26) {
|
|
2258
2515
|
markSerializerRef(base, sentinel.i);
|
|
2259
2516
|
serialized = "(" + serialize$1(ctx, sentinel) + "," + serialized + ")";
|
|
2260
2517
|
}
|
|
@@ -2263,11 +2520,8 @@ function serializeMap(ctx, node) {
|
|
|
2263
2520
|
function serializeArrayBuffer(ctx, node) {
|
|
2264
2521
|
return getConstructor(ctx, node.f) + "(\"" + node.s + "\")";
|
|
2265
2522
|
}
|
|
2266
|
-
function
|
|
2267
|
-
return "new " + node.c + "(" + serialize$1(ctx, node.f) + "," + node.b + "," + node.l + ")";
|
|
2268
|
-
}
|
|
2269
|
-
function serializeDataView(ctx, node) {
|
|
2270
|
-
return "new DataView(" + serialize$1(ctx, node.f) + "," + node.b + "," + node.l + ")";
|
|
2523
|
+
function serializeView(ctx, node) {
|
|
2524
|
+
return "new " + (node.t === 20 ? "DataView" : node.c) + "(" + serialize$1(ctx, node.f) + "," + node.b + "," + node.l + ")";
|
|
2271
2525
|
}
|
|
2272
2526
|
function serializeAggregateError(ctx, node) {
|
|
2273
2527
|
const id = node.i;
|
|
@@ -2307,11 +2561,7 @@ function serializePromiseConstructor(ctx, node) {
|
|
|
2307
2561
|
if (ctx.mode === 1) throw new SerovalUnsupportedNodeError(node);
|
|
2308
2562
|
return "(" + assignIndexedValue(ctx, node.s, getConstructor(ctx, node.f) + "()") + ").p";
|
|
2309
2563
|
}
|
|
2310
|
-
function
|
|
2311
|
-
if (ctx.mode === 1) throw new SerovalUnsupportedNodeError(node);
|
|
2312
|
-
return getConstructor(ctx, node.a[0]) + "(" + getRefParam(ctx, node.i) + "," + serialize$1(ctx, node.a[1]) + ")";
|
|
2313
|
-
}
|
|
2314
|
-
function serializePromiseReject(ctx, node) {
|
|
2564
|
+
function serializePromiseResult(ctx, node) {
|
|
2315
2565
|
if (ctx.mode === 1) throw new SerovalUnsupportedNodeError(node);
|
|
2316
2566
|
return getConstructor(ctx, node.a[0]) + "(" + getRefParam(ctx, node.i) + "," + serialize$1(ctx, node.a[1]) + ")";
|
|
2317
2567
|
}
|
|
@@ -2319,10 +2569,7 @@ function serializePlugin(ctx, node) {
|
|
|
2319
2569
|
const currentPlugins = ctx.base.plugins;
|
|
2320
2570
|
if (currentPlugins) for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
2321
2571
|
const plugin = currentPlugins[i];
|
|
2322
|
-
if (plugin.tag === node.c) {
|
|
2323
|
-
if (ctx.child == null) ctx.child = new SerializePluginContext(ctx);
|
|
2324
|
-
return plugin.serialize(node.s, ctx.child, { id: node.i });
|
|
2325
|
-
}
|
|
2572
|
+
if (plugin.tag === node.c) return plugin.serialize(node.s, { serialize: (current) => serialize$1(ctx, current) }, { id: node.i });
|
|
2326
2573
|
}
|
|
2327
2574
|
throw new SerovalMissingPluginError(node.c);
|
|
2328
2575
|
}
|
|
@@ -2359,11 +2606,8 @@ function serializeAsyncIteratorFactory(ctx, node) {
|
|
|
2359
2606
|
if (result) return result + iterator + ")";
|
|
2360
2607
|
return iterator;
|
|
2361
2608
|
}
|
|
2362
|
-
function serializeAsyncIteratorFactoryInstance(ctx, node) {
|
|
2363
|
-
return getConstructor(ctx, node.a[0]) + "(" + serialize$1(ctx, node.a[1]) + ")";
|
|
2364
|
-
}
|
|
2365
2609
|
function serializeStreamConstructor(ctx, node) {
|
|
2366
|
-
const result = assignIndexedValue(ctx, node.i, getConstructor(ctx, node.f) + "()");
|
|
2610
|
+
const result = assignIndexedValue(ctx, node.i, getConstructor(ctx, node.f) + (node.l === 1 ? "(1)" : "()"));
|
|
2367
2611
|
const len = node.a.length;
|
|
2368
2612
|
if (len) {
|
|
2369
2613
|
let values = serialize$1(ctx, node.a[0]);
|
|
@@ -2372,14 +2616,8 @@ function serializeStreamConstructor(ctx, node) {
|
|
|
2372
2616
|
}
|
|
2373
2617
|
return result;
|
|
2374
2618
|
}
|
|
2375
|
-
function
|
|
2376
|
-
return getRefParam(ctx, node.i) + ".
|
|
2377
|
-
}
|
|
2378
|
-
function serializeStreamThrow(ctx, node) {
|
|
2379
|
-
return getRefParam(ctx, node.i) + ".throw(" + serialize$1(ctx, node.f) + ")";
|
|
2380
|
-
}
|
|
2381
|
-
function serializeStreamReturn(ctx, node) {
|
|
2382
|
-
return getRefParam(ctx, node.i) + ".return(" + serialize$1(ctx, node.f) + ")";
|
|
2619
|
+
function serializeStreamCall(ctx, node, method) {
|
|
2620
|
+
return getRefParam(ctx, node.i) + "." + method + "(" + serialize$1(ctx, node.f) + ")";
|
|
2383
2621
|
}
|
|
2384
2622
|
function serializeSequenceItem(ctx, id, index, item) {
|
|
2385
2623
|
const base = ctx.base;
|
|
@@ -2397,7 +2635,7 @@ function serializeSequence(ctx, node) {
|
|
|
2397
2635
|
if (size > 0) {
|
|
2398
2636
|
ctx.base.stack.push(id);
|
|
2399
2637
|
let result = serializeSequenceItem(ctx, id, 0, items[0]);
|
|
2400
|
-
for (let i = 1, item
|
|
2638
|
+
for (let i = 1, item; i < size; i++) {
|
|
2401
2639
|
item = serializeSequenceItem(ctx, id, i, items[i]);
|
|
2402
2640
|
result += (item && result && ",") + item;
|
|
2403
2641
|
}
|
|
@@ -2419,8 +2657,8 @@ function serializeAssignable(ctx, node) {
|
|
|
2419
2657
|
case 8: return serializeMap(ctx, node);
|
|
2420
2658
|
case 19: return serializeArrayBuffer(ctx, node);
|
|
2421
2659
|
case 16:
|
|
2422
|
-
case 15:
|
|
2423
|
-
case 20: return
|
|
2660
|
+
case 15:
|
|
2661
|
+
case 20: return serializeView(ctx, node);
|
|
2424
2662
|
case 14: return serializeAggregateError(ctx, node);
|
|
2425
2663
|
case 13: return serializeError(ctx, node);
|
|
2426
2664
|
case 12: return serializePromise(ctx, node);
|
|
@@ -2440,20 +2678,20 @@ function serialize$1(ctx, node) {
|
|
|
2440
2678
|
case 1: return "\"" + node.s + "\"";
|
|
2441
2679
|
case 3: return node.s + "n";
|
|
2442
2680
|
case 4: return getRefParam(ctx, node.i);
|
|
2443
|
-
case 23:
|
|
2444
|
-
case 24: return
|
|
2681
|
+
case 23:
|
|
2682
|
+
case 24: return serializePromiseResult(ctx, node);
|
|
2445
2683
|
case 27: return serializeIteratorFactory(ctx, node);
|
|
2446
|
-
case 28:
|
|
2684
|
+
case 28:
|
|
2685
|
+
case 30: return serializeIteratorFactoryInstance(ctx, node);
|
|
2447
2686
|
case 29: return serializeAsyncIteratorFactory(ctx, node);
|
|
2448
|
-
case 30: return serializeAsyncIteratorFactoryInstance(ctx, node);
|
|
2449
2687
|
case 31: return serializeStreamConstructor(ctx, node);
|
|
2450
|
-
case 32: return
|
|
2451
|
-
case 33: return
|
|
2452
|
-
case 34: return
|
|
2688
|
+
case 32: return serializeStreamCall(ctx, node, "next");
|
|
2689
|
+
case 33: return serializeStreamCall(ctx, node, "throw");
|
|
2690
|
+
case 34: return serializeStreamCall(ctx, node, "return");
|
|
2453
2691
|
default: return assignIndexedValue(ctx, node.i, serializeAssignable(ctx, node));
|
|
2454
2692
|
}
|
|
2455
2693
|
}
|
|
2456
|
-
function
|
|
2694
|
+
function serializeVanilla(ctx, tree) {
|
|
2457
2695
|
const result = serialize$1(ctx, tree);
|
|
2458
2696
|
if (tree.i != null && ctx.state.vars.length) {
|
|
2459
2697
|
const patches = resolvePatches(ctx.base);
|
|
@@ -2464,12 +2702,18 @@ function serializeTopVanilla(ctx, tree) {
|
|
|
2464
2702
|
if (!result.startsWith(index + "=")) body = index + "=" + body;
|
|
2465
2703
|
body = "(" + body + ")";
|
|
2466
2704
|
}
|
|
2705
|
+
const sentinels = ctx.state.sentinels;
|
|
2706
|
+
if (sentinels.size) {
|
|
2707
|
+
let declarations = "";
|
|
2708
|
+
for (const index of sentinels) declarations += ctx.state.vars[index] + "=[],";
|
|
2709
|
+
body = "(" + declarations + body + ")";
|
|
2710
|
+
}
|
|
2467
2711
|
return "(" + createFunction(ctx.state.vars, body) + ")()";
|
|
2468
2712
|
}
|
|
2469
2713
|
if (tree.t === 10) return "(" + result + ")";
|
|
2470
2714
|
return result;
|
|
2471
2715
|
}
|
|
2472
|
-
function
|
|
2716
|
+
function serializeCross(ctx, tree) {
|
|
2473
2717
|
const result = serialize$1(ctx, tree);
|
|
2474
2718
|
const id = tree.i;
|
|
2475
2719
|
if (id == null) return result;
|
|
@@ -2477,7 +2721,11 @@ function serializeTopCross(ctx, tree) {
|
|
|
2477
2721
|
const ref = getRefParam(ctx, id);
|
|
2478
2722
|
const scopeId = ctx.state.scopeId;
|
|
2479
2723
|
const params = scopeId == null ? "" : "$R";
|
|
2480
|
-
|
|
2724
|
+
let body = result;
|
|
2725
|
+
if (patches) {
|
|
2726
|
+
if (!ctx.base.assignAll && !result.startsWith(ref + "=")) body = ref + "=" + result;
|
|
2727
|
+
body = "(" + body + "," + patches + ref + ")";
|
|
2728
|
+
}
|
|
2481
2729
|
if (params === "") {
|
|
2482
2730
|
if (tree.t === 10 && !patches) return "(" + body + ")";
|
|
2483
2731
|
return body;
|
|
@@ -2485,76 +2733,35 @@ function serializeTopCross(ctx, tree) {
|
|
|
2485
2733
|
const args = scopeId == null ? "()" : "($R[\"" + serializeString(scopeId) + "\"])";
|
|
2486
2734
|
return "(" + createFunction([params], body) + ")" + args;
|
|
2487
2735
|
}
|
|
2488
|
-
|
|
2489
|
-
|
|
2490
|
-
function createSyncParserContext(mode, options) {
|
|
2491
|
-
return {
|
|
2492
|
-
type: 1,
|
|
2493
|
-
base: createBaseParserContext(mode, options),
|
|
2494
|
-
child: void 0
|
|
2495
|
-
};
|
|
2736
|
+
function wrapSerializationError(error) {
|
|
2737
|
+
return error instanceof SerovalSerializationError ? error : new SerovalSerializationError(error);
|
|
2496
2738
|
}
|
|
2497
|
-
|
|
2498
|
-
|
|
2499
|
-
|
|
2500
|
-
|
|
2501
|
-
|
|
2502
|
-
parse(current) {
|
|
2503
|
-
return parseSOS(this._p, this.depth, current);
|
|
2504
|
-
}
|
|
2505
|
-
};
|
|
2506
|
-
var StreamParsePluginContext = class {
|
|
2507
|
-
constructor(_p, depth) {
|
|
2508
|
-
this._p = _p;
|
|
2509
|
-
this.depth = depth;
|
|
2510
|
-
}
|
|
2511
|
-
parse(current) {
|
|
2512
|
-
return parseSOS(this._p, this.depth, current);
|
|
2513
|
-
}
|
|
2514
|
-
parseWithError(current) {
|
|
2515
|
-
return parseWithError(this._p, this.depth, current);
|
|
2516
|
-
}
|
|
2517
|
-
isAlive() {
|
|
2518
|
-
return this._p.state.alive;
|
|
2519
|
-
}
|
|
2520
|
-
pushPendingState() {
|
|
2521
|
-
pushPendingState(this._p);
|
|
2522
|
-
}
|
|
2523
|
-
popPendingState() {
|
|
2524
|
-
popPendingState(this._p);
|
|
2525
|
-
}
|
|
2526
|
-
onParse(node) {
|
|
2527
|
-
onParse(this._p, node);
|
|
2528
|
-
}
|
|
2529
|
-
onError(error) {
|
|
2530
|
-
onError(this._p, error);
|
|
2739
|
+
function serializeTopVanilla(ctx, tree) {
|
|
2740
|
+
try {
|
|
2741
|
+
return serializeVanilla(ctx, tree);
|
|
2742
|
+
} catch (error) {
|
|
2743
|
+
throw wrapSerializationError(error);
|
|
2531
2744
|
}
|
|
2532
|
-
|
|
2533
|
-
|
|
2745
|
+
}
|
|
2746
|
+
function serializeTopCross(ctx, tree) {
|
|
2747
|
+
try {
|
|
2748
|
+
return serializeCross(ctx, tree);
|
|
2749
|
+
} catch (error) {
|
|
2750
|
+
throw wrapSerializationError(error);
|
|
2534
2751
|
}
|
|
2535
|
-
};
|
|
2536
|
-
function createStreamParserState(options) {
|
|
2537
|
-
return {
|
|
2538
|
-
alive: true,
|
|
2539
|
-
pending: 0,
|
|
2540
|
-
initial: true,
|
|
2541
|
-
buffer: [],
|
|
2542
|
-
onParse: options.onParse,
|
|
2543
|
-
onError: options.onError,
|
|
2544
|
-
onDone: options.onDone,
|
|
2545
|
-
cleanups: []
|
|
2546
|
-
};
|
|
2547
2752
|
}
|
|
2548
|
-
|
|
2753
|
+
//#endregion
|
|
2754
|
+
//#region src/core/context/sync-parser.ts
|
|
2755
|
+
function createSyncParserContext(options) {
|
|
2549
2756
|
return {
|
|
2550
|
-
type:
|
|
2551
|
-
base: createBaseParserContext(
|
|
2552
|
-
state: createStreamParserState(options)
|
|
2757
|
+
type: 1,
|
|
2758
|
+
base: createBaseParserContext(options)
|
|
2553
2759
|
};
|
|
2554
2760
|
}
|
|
2555
2761
|
function parseItems(ctx, depth, current) {
|
|
2556
|
-
const
|
|
2557
|
-
|
|
2762
|
+
const len = current.length;
|
|
2763
|
+
const nodes = new Array(len);
|
|
2764
|
+
for (let i = 0; i < len; i++) if (i in current) nodes[i] = parseSOS(ctx, depth, current[i]);
|
|
2558
2765
|
else nodes[i] = 0;
|
|
2559
2766
|
return nodes;
|
|
2560
2767
|
}
|
|
@@ -2562,20 +2769,22 @@ function parseArray(ctx, depth, id, current) {
|
|
|
2562
2769
|
return createArrayNode(id, current, parseItems(ctx, depth, current));
|
|
2563
2770
|
}
|
|
2564
2771
|
function parseProperties(ctx, depth, properties) {
|
|
2565
|
-
const
|
|
2566
|
-
const
|
|
2567
|
-
const
|
|
2568
|
-
|
|
2569
|
-
|
|
2570
|
-
|
|
2772
|
+
const keys = Object.keys(properties);
|
|
2773
|
+
const len = keys.length;
|
|
2774
|
+
const keyNodes = new Array(len);
|
|
2775
|
+
const valueNodes = new Array(len);
|
|
2776
|
+
for (let i = 0, key; i < len; i++) {
|
|
2777
|
+
key = keys[i];
|
|
2778
|
+
keyNodes[i] = serializeString(key);
|
|
2779
|
+
valueNodes[i] = parseSOS(ctx, depth, properties[key]);
|
|
2571
2780
|
}
|
|
2572
2781
|
if (SYM_ITERATOR in properties) {
|
|
2573
2782
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_ITERATOR));
|
|
2574
|
-
valueNodes.push(createIteratorFactoryInstanceNode(parseIteratorFactory(ctx.base), parseSOS(ctx, depth, createSequenceFromIterable(properties))));
|
|
2783
|
+
valueNodes.push(createIteratorFactoryInstanceNode(28, parseIteratorFactory(ctx.base), parseSOS(ctx, depth, createSequenceFromIterable(properties))));
|
|
2575
2784
|
}
|
|
2576
2785
|
if (SYM_ASYNC_ITERATOR in properties) {
|
|
2577
2786
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_ASYNC_ITERATOR));
|
|
2578
|
-
valueNodes.push(
|
|
2787
|
+
valueNodes.push(createIteratorFactoryInstanceNode(30, parseAsyncIteratorFactory(ctx.base), parseAsyncIterable(ctx, depth, properties)));
|
|
2579
2788
|
}
|
|
2580
2789
|
if (SYM_TO_STRING_TAG in properties) {
|
|
2581
2790
|
keyNodes.push(parseWellKnownSymbol(ctx.base, SYM_TO_STRING_TAG));
|
|
@@ -2590,187 +2799,111 @@ function parseProperties(ctx, depth, properties) {
|
|
|
2590
2799
|
v: valueNodes
|
|
2591
2800
|
};
|
|
2592
2801
|
}
|
|
2802
|
+
function parseAsyncIterable(ctx, depth, current) {
|
|
2803
|
+
const id = createIndexForValue(ctx.base, {});
|
|
2804
|
+
const result = createStreamConstructorNode(id, parseSpecialReference(ctx.base, 4), []);
|
|
2805
|
+
if (ctx.type === 2) ctx.state.iterable(ctx, depth, id, current);
|
|
2806
|
+
return result;
|
|
2807
|
+
}
|
|
2593
2808
|
function parsePlainObject(ctx, depth, id, current, empty) {
|
|
2594
2809
|
return createObjectNode(id, current, empty, parseProperties(ctx, depth, current));
|
|
2595
2810
|
}
|
|
2596
2811
|
function parseBoxed(ctx, depth, id, current) {
|
|
2597
2812
|
return createBoxedNode(id, parseSOS(ctx, depth, current.valueOf()));
|
|
2598
2813
|
}
|
|
2599
|
-
function
|
|
2600
|
-
current = getArrayBufferView(ctx.base, current);
|
|
2601
|
-
return createTypedArrayNode(id, current, parseSOS(ctx, depth, current.buffer));
|
|
2602
|
-
}
|
|
2603
|
-
function parseBigIntTypedArray(ctx, depth, id, current) {
|
|
2814
|
+
function parseView(ctx, depth, type, id, current) {
|
|
2604
2815
|
current = getArrayBufferView(ctx.base, current);
|
|
2605
|
-
return
|
|
2606
|
-
}
|
|
2607
|
-
function parseDataView(ctx, depth, id, current) {
|
|
2608
|
-
current = getArrayBufferView(ctx.base, current);
|
|
2609
|
-
return createDataViewNode(id, current, parseSOS(ctx, depth, current.buffer));
|
|
2610
|
-
}
|
|
2611
|
-
function parseError(ctx, depth, id, current) {
|
|
2612
|
-
const options = getErrorOptions(current, ctx.base.features);
|
|
2613
|
-
return createErrorNode(id, current, options ? parseProperties(ctx, depth, options) : void 0);
|
|
2816
|
+
return createViewNode(type, id, current, parseSOS(ctx, depth, current.buffer));
|
|
2614
2817
|
}
|
|
2615
|
-
function
|
|
2818
|
+
function parseError(ctx, depth, type, id, current) {
|
|
2616
2819
|
const options = getErrorOptions(current, ctx.base.features);
|
|
2617
|
-
return
|
|
2820
|
+
return createErrorNode(type, id, current, options ? parseProperties(ctx, depth, options) : void 0);
|
|
2618
2821
|
}
|
|
2619
2822
|
function parseMap(ctx, depth, id, current) {
|
|
2620
|
-
const
|
|
2621
|
-
const
|
|
2823
|
+
const sentinel = parseMapSentinel(ctx.base);
|
|
2824
|
+
const keyNodes = new Array(current.size);
|
|
2825
|
+
const valueNodes = new Array(current.size);
|
|
2826
|
+
let i = 0;
|
|
2622
2827
|
for (const [key, value] of current.entries()) {
|
|
2623
|
-
keyNodes
|
|
2624
|
-
valueNodes
|
|
2828
|
+
keyNodes[i] = parseSOS(ctx, depth, key);
|
|
2829
|
+
valueNodes[i] = parseSOS(ctx, depth, value);
|
|
2830
|
+
i++;
|
|
2625
2831
|
}
|
|
2626
|
-
return createMapNode(
|
|
2832
|
+
return createMapNode(id, sentinel, keyNodes, valueNodes);
|
|
2627
2833
|
}
|
|
2628
2834
|
function parseSet(ctx, depth, id, current) {
|
|
2629
|
-
const items =
|
|
2630
|
-
|
|
2835
|
+
const items = new Array(current.size);
|
|
2836
|
+
let i = 0;
|
|
2837
|
+
for (const item of current.keys()) items[i++] = parseSOS(ctx, depth, item);
|
|
2631
2838
|
return createSetNode(id, items);
|
|
2632
2839
|
}
|
|
2633
2840
|
function parseStream(ctx, depth, id, current) {
|
|
2634
2841
|
const result = createStreamConstructorNode(id, parseSpecialReference(ctx.base, 4), []);
|
|
2635
|
-
if (ctx.type ===
|
|
2636
|
-
pushPendingState(ctx);
|
|
2637
|
-
current.on({
|
|
2638
|
-
next: (value) => {
|
|
2639
|
-
if (ctx.state.alive) {
|
|
2640
|
-
const parsed = parseWithError(ctx, depth, value);
|
|
2641
|
-
if (parsed) onParse(ctx, createStreamNextNode(id, parsed));
|
|
2642
|
-
}
|
|
2643
|
-
},
|
|
2644
|
-
throw: (value) => {
|
|
2645
|
-
if (ctx.state.alive) {
|
|
2646
|
-
const parsed = parseWithError(ctx, depth, value);
|
|
2647
|
-
if (parsed) onParse(ctx, createStreamThrowNode(id, parsed));
|
|
2648
|
-
}
|
|
2649
|
-
popPendingState(ctx);
|
|
2650
|
-
},
|
|
2651
|
-
return: (value) => {
|
|
2652
|
-
if (ctx.state.alive) {
|
|
2653
|
-
const parsed = parseWithError(ctx, depth, value);
|
|
2654
|
-
if (parsed) onParse(ctx, createStreamReturnNode(id, parsed));
|
|
2655
|
-
}
|
|
2656
|
-
popPendingState(ctx);
|
|
2657
|
-
}
|
|
2658
|
-
});
|
|
2842
|
+
if (ctx.type === 2) ctx.state.stream(ctx, depth, id, current);
|
|
2659
2843
|
return result;
|
|
2660
2844
|
}
|
|
2661
|
-
function
|
|
2662
|
-
|
|
2663
|
-
|
|
2664
|
-
|
|
2665
|
-
|
|
2666
|
-
}
|
|
2667
|
-
}
|
|
2668
|
-
function handlePromiseFailure(id, depth, data) {
|
|
2669
|
-
if (this.state.alive) {
|
|
2670
|
-
const parsed = parseWithError(this, depth, data);
|
|
2671
|
-
if (parsed) onParse(this, createSerovalNode(24, id, void 0, void 0, void 0, void 0, void 0, [parseSpecialReference(this.base, 3), parsed], void 0, void 0, void 0, void 0));
|
|
2672
|
-
}
|
|
2673
|
-
popPendingState(this);
|
|
2845
|
+
function parseLiveStream(ctx, depth, id, current) {
|
|
2846
|
+
const stream = ctx.type === 2;
|
|
2847
|
+
const result = createStreamConstructorNode(id, parseSpecialReference(ctx.base, 4), [], stream ? 1 : void 0);
|
|
2848
|
+
if (stream) ctx.state.live(ctx, depth, id, current);
|
|
2849
|
+
return result;
|
|
2674
2850
|
}
|
|
2675
2851
|
function parsePromise(ctx, depth, id, current) {
|
|
2852
|
+
if (ctx.type !== 2) throw new SerovalUnsupportedTypeError(current);
|
|
2676
2853
|
const resolver = createIndexForValue(ctx.base, {});
|
|
2677
|
-
|
|
2678
|
-
pushPendingState(ctx);
|
|
2679
|
-
current.then(handlePromiseSuccess.bind(ctx, resolver, depth), handlePromiseFailure.bind(ctx, resolver, depth));
|
|
2680
|
-
}
|
|
2854
|
+
ctx.state.promise(ctx, resolver, depth, current);
|
|
2681
2855
|
return createPromiseConstructorNode(ctx.base, id, resolver);
|
|
2682
2856
|
}
|
|
2683
2857
|
function parsePluginSync(ctx, depth, id, current, currentPlugins) {
|
|
2684
2858
|
for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
2685
2859
|
const plugin = currentPlugins[i];
|
|
2686
|
-
if (plugin.parse.sync && plugin.test(current)) return createPluginNode(id, plugin.tag, plugin.parse.sync(current,
|
|
2860
|
+
if (plugin.parse.sync && plugin.test(current)) return createPluginNode(id, plugin.tag, plugin.parse.sync(current, { parse: (value) => parseSOS(ctx, depth, value) }, { id }));
|
|
2687
2861
|
}
|
|
2688
2862
|
}
|
|
2689
|
-
function
|
|
2690
|
-
|
|
2691
|
-
const plugin = currentPlugins[i];
|
|
2692
|
-
if (plugin.parse.stream && plugin.test(current)) return createPluginNode(id, plugin.tag, plugin.parse.stream(current, new StreamParsePluginContext(ctx, depth), { id }));
|
|
2693
|
-
}
|
|
2694
|
-
}
|
|
2695
|
-
function parsePlugin(ctx, depth, id, current) {
|
|
2696
|
-
const currentPlugins = ctx.base.plugins;
|
|
2697
|
-
if (currentPlugins) return ctx.type === 1 ? parsePluginSync(ctx, depth, id, current, currentPlugins) : parsePluginStream(ctx, depth, id, current, currentPlugins);
|
|
2863
|
+
function parsePlugin(ctx, depth, id, current, currentPlugins) {
|
|
2864
|
+
if (currentPlugins) return ctx.type === 1 ? parsePluginSync(ctx, depth, id, current, currentPlugins) : ctx.state.plugin(ctx, depth, id, current, currentPlugins);
|
|
2698
2865
|
}
|
|
2699
2866
|
function parseSequence(ctx, depth, id, current) {
|
|
2700
|
-
const
|
|
2701
|
-
|
|
2867
|
+
const len = current.v.length;
|
|
2868
|
+
const nodes = new Array(len);
|
|
2869
|
+
for (let i = 0; i < len; i++) nodes[i] = parseSOS(ctx, depth, current.v[i]);
|
|
2702
2870
|
return createSequenceNode(id, nodes, current.t, current.d);
|
|
2703
2871
|
}
|
|
2704
2872
|
function parseObjectPhase2(ctx, depth, id, current, currentClass) {
|
|
2705
|
-
|
|
2706
|
-
|
|
2707
|
-
case
|
|
2708
|
-
case
|
|
2709
|
-
case
|
|
2710
|
-
case
|
|
2711
|
-
case
|
|
2712
|
-
case
|
|
2713
|
-
case
|
|
2714
|
-
case
|
|
2715
|
-
case
|
|
2716
|
-
case
|
|
2717
|
-
case
|
|
2718
|
-
case
|
|
2719
|
-
case
|
|
2720
|
-
case
|
|
2721
|
-
case
|
|
2722
|
-
|
|
2723
|
-
|
|
2724
|
-
case Uint8Array:
|
|
2725
|
-
case Uint16Array:
|
|
2726
|
-
case Uint32Array:
|
|
2727
|
-
case Uint8ClampedArray:
|
|
2728
|
-
case Float32Array:
|
|
2729
|
-
case Float64Array: return parseTypedArray(ctx, depth, id, current);
|
|
2730
|
-
case DataView: return parseDataView(ctx, depth, id, current);
|
|
2731
|
-
case Map: return parseMap(ctx, depth, id, current);
|
|
2732
|
-
case Set: return parseSet(ctx, depth, id, current);
|
|
2733
|
-
}
|
|
2734
|
-
if (currentClass === Promise || current instanceof Promise) return parsePromise(ctx, depth, id, current);
|
|
2735
|
-
const currentFeatures = ctx.base.features;
|
|
2736
|
-
if (currentFeatures & 32 && currentClass === RegExp) return createRegExpNode(id, current);
|
|
2737
|
-
if (currentFeatures & 16) switch (currentClass) {
|
|
2738
|
-
case BigInt64Array:
|
|
2739
|
-
case BigUint64Array: return parseBigIntTypedArray(ctx, depth, id, current);
|
|
2740
|
-
}
|
|
2741
|
-
if (currentFeatures & 1 && typeof AggregateError !== "undefined" && (currentClass === AggregateError || current instanceof AggregateError)) return parseAggregateError(ctx, depth, id, current);
|
|
2742
|
-
if (currentFeatures & 64 && typeof Temporal !== "undefined") switch (currentClass) {
|
|
2743
|
-
case Temporal.Instant: return createTemporalNode(id, 0, current);
|
|
2744
|
-
case Temporal.Duration: return createTemporalNode(id, 1, current);
|
|
2745
|
-
case Temporal.PlainDate: return createTemporalNode(id, 2, current);
|
|
2746
|
-
case Temporal.PlainDateTime: return createTemporalNode(id, 3, current);
|
|
2747
|
-
case Temporal.PlainMonthDay: return createTemporalNode(id, 4, current);
|
|
2748
|
-
case Temporal.PlainTime: return createTemporalNode(id, 5, current);
|
|
2749
|
-
case Temporal.PlainYearMonth: return createTemporalNode(id, 6, current);
|
|
2750
|
-
case Temporal.ZonedDateTime: return createTemporalNode(id, 7, current);
|
|
2751
|
-
}
|
|
2752
|
-
if (current instanceof Error) return parseError(ctx, depth, id, current);
|
|
2753
|
-
if (SYM_ITERATOR in current || SYM_ASYNC_ITERATOR in current) return parsePlainObject(ctx, depth, id, current, !!currentClass);
|
|
2754
|
-
throw new SerovalUnsupportedTypeError(current);
|
|
2873
|
+
if (currentClass === Object) return parsePlainObject(ctx, depth, id, current, false);
|
|
2874
|
+
switch (getObjectKind(current, currentClass, ctx.base.features)) {
|
|
2875
|
+
case 2: return parsePlainObject(ctx, depth, id, current, true);
|
|
2876
|
+
case 3: return createDateNode(id, current);
|
|
2877
|
+
case 4: return parseError(ctx, depth, 13, id, current);
|
|
2878
|
+
case 5: return parseError(ctx, depth, 14, id, current);
|
|
2879
|
+
case 6: return parseBoxed(ctx, depth, id, current);
|
|
2880
|
+
case 7: return createArrayBufferNode(ctx.base, id, current);
|
|
2881
|
+
case 8: return parseView(ctx, depth, 15, id, current);
|
|
2882
|
+
case 9: return parseView(ctx, depth, 16, id, current);
|
|
2883
|
+
case 10: return parseView(ctx, depth, 20, id, current);
|
|
2884
|
+
case 11: return parseMap(ctx, depth, id, current);
|
|
2885
|
+
case 12: return parseSet(ctx, depth, id, current);
|
|
2886
|
+
case 13: return parsePromise(ctx, depth, id, current);
|
|
2887
|
+
case 14: return createRegExpNode(id, current);
|
|
2888
|
+
case 15: return createTemporalNode(id, getTemporalType(currentClass), current);
|
|
2889
|
+
case 16: return parsePlainObject(ctx, depth, id, current, !!currentClass);
|
|
2890
|
+
default: throw new SerovalUnsupportedTypeError(current);
|
|
2891
|
+
}
|
|
2755
2892
|
}
|
|
2756
2893
|
function parseObject(ctx, depth, id, current) {
|
|
2757
2894
|
if (Array.isArray(current)) return parseArray(ctx, depth, id, current);
|
|
2758
|
-
if (isStream(current)) return parseStream(ctx, depth, id, current);
|
|
2895
|
+
if (isStream(current)) return isLiveStream(current) ? parseLiveStream(ctx, depth, id, current) : parseStream(ctx, depth, id, current);
|
|
2759
2896
|
if (isSequence(current)) return parseSequence(ctx, depth, id, current);
|
|
2760
|
-
|
|
2761
|
-
if (currentClass !== void 0 && typeof currentClass !== "function") {
|
|
2762
|
-
const proto = Object.getPrototypeOf(current);
|
|
2763
|
-
currentClass = proto === null ? void 0 : proto.constructor;
|
|
2764
|
-
}
|
|
2897
|
+
const currentClass = getObjectClass(current);
|
|
2765
2898
|
if (currentClass === OpaqueReference) return parseSOS(ctx, depth, current.replacement);
|
|
2766
|
-
const parsed = parsePlugin(ctx, depth, id, current);
|
|
2899
|
+
const parsed = parsePlugin(ctx, depth, id, current, getObjectPlugins(ctx.base, current, currentClass));
|
|
2767
2900
|
if (parsed) return parsed;
|
|
2768
2901
|
return parseObjectPhase2(ctx, depth, id, current, currentClass);
|
|
2769
2902
|
}
|
|
2770
2903
|
function parseFunction(ctx, depth, current) {
|
|
2771
2904
|
const ref = getReferenceNode(ctx.base, current);
|
|
2772
|
-
if (ref
|
|
2773
|
-
const plugin = parsePlugin(ctx, depth, ref
|
|
2905
|
+
if (typeof ref !== "number") return ref;
|
|
2906
|
+
const plugin = parsePlugin(ctx, depth, ref, current, ctx.base.plugins);
|
|
2774
2907
|
if (plugin) return plugin;
|
|
2775
2908
|
throw new SerovalUnsupportedTypeError(current);
|
|
2776
2909
|
}
|
|
@@ -2785,7 +2918,7 @@ function parseSOS(ctx, depth, current) {
|
|
|
2785
2918
|
case "object":
|
|
2786
2919
|
if (current) {
|
|
2787
2920
|
const ref = getReferenceNode(ctx.base, current);
|
|
2788
|
-
return ref
|
|
2921
|
+
return typeof ref === "number" ? parseObject(ctx, depth + 1, ref, current) : ref;
|
|
2789
2922
|
}
|
|
2790
2923
|
return NULL_NODE;
|
|
2791
2924
|
case "symbol": return parseWellKnownSymbol(ctx.base, current);
|
|
@@ -2800,63 +2933,431 @@ function parseTop(ctx, current) {
|
|
|
2800
2933
|
throw error instanceof SerovalParserError ? error : new SerovalParserError(error);
|
|
2801
2934
|
}
|
|
2802
2935
|
}
|
|
2803
|
-
|
|
2804
|
-
|
|
2805
|
-
|
|
2936
|
+
//#endregion
|
|
2937
|
+
//#region src/core/context/stream-parser.ts
|
|
2938
|
+
/**
|
|
2939
|
+
* Streaming parse mode. Everything here is reached through the function
|
|
2940
|
+
* fields of the stream parser state, which only `createStreamParserContext`
|
|
2941
|
+
* sets, so synchronous consumers (`serialize`, `toJSON`) never bundle it.
|
|
2942
|
+
*/
|
|
2943
|
+
function createStreamParsePluginContext(ctx, depth) {
|
|
2944
|
+
const state = ctx.state;
|
|
2945
|
+
function parse(current) {
|
|
2946
|
+
state.parsing++;
|
|
2947
|
+
try {
|
|
2948
|
+
return parseSOS(ctx, depth, current);
|
|
2949
|
+
} finally {
|
|
2950
|
+
state.parsing--;
|
|
2951
|
+
if (!state.alive) releaseParserValues(ctx);
|
|
2952
|
+
}
|
|
2953
|
+
}
|
|
2954
|
+
return {
|
|
2955
|
+
parse,
|
|
2956
|
+
parseStreamSource(current) {
|
|
2957
|
+
state.parsing++;
|
|
2958
|
+
try {
|
|
2959
|
+
if (depth >= ctx.base.depthLimit) throw new SerovalDepthLimitError(ctx.base.depthLimit);
|
|
2960
|
+
const id = createIndexForValue(ctx.base, {});
|
|
2961
|
+
const node = createStreamConstructorNode(id, parseSpecialReference(ctx.base, 4), [], 1);
|
|
2962
|
+
iterateAsync(ctx, depth + 1, id, current, true);
|
|
2963
|
+
return node;
|
|
2964
|
+
} finally {
|
|
2965
|
+
state.parsing--;
|
|
2966
|
+
if (!state.alive) releaseParserValues(ctx);
|
|
2967
|
+
}
|
|
2968
|
+
},
|
|
2969
|
+
parseWithError(current) {
|
|
2970
|
+
try {
|
|
2971
|
+
return parse(current);
|
|
2972
|
+
} catch (error) {
|
|
2973
|
+
stopStreamParse(ctx, 1, error);
|
|
2974
|
+
return;
|
|
2975
|
+
}
|
|
2976
|
+
},
|
|
2977
|
+
isAlive: () => state.alive,
|
|
2978
|
+
pushPendingState: () => {
|
|
2979
|
+
pushPendingState(ctx);
|
|
2980
|
+
},
|
|
2981
|
+
popPendingState: () => {
|
|
2982
|
+
popPendingState(ctx);
|
|
2983
|
+
},
|
|
2984
|
+
onParse(node) {
|
|
2985
|
+
if (state.alive) {
|
|
2986
|
+
state.queue.push({
|
|
2987
|
+
node,
|
|
2988
|
+
initial: false,
|
|
2989
|
+
accept: void 0
|
|
2990
|
+
});
|
|
2991
|
+
drainOutput(ctx);
|
|
2992
|
+
}
|
|
2993
|
+
},
|
|
2994
|
+
onError(error) {
|
|
2995
|
+
stopStreamParse(ctx, 1, error);
|
|
2996
|
+
},
|
|
2997
|
+
addCleanup(callback) {
|
|
2998
|
+
addCleanup(ctx, callback);
|
|
2999
|
+
}
|
|
3000
|
+
};
|
|
3001
|
+
}
|
|
3002
|
+
function getStreamParsePluginContext(ctx, depth) {
|
|
3003
|
+
const contexts = ctx.state.pluginContexts;
|
|
3004
|
+
return contexts[depth] ?? (contexts[depth] = createStreamParsePluginContext(ctx, depth));
|
|
2806
3005
|
}
|
|
2807
|
-
function
|
|
2808
|
-
if (ctx.state.
|
|
2809
|
-
else
|
|
3006
|
+
function addCleanup(ctx, callback) {
|
|
3007
|
+
if (ctx.state.alive) ctx.state.cleanups.push(callback);
|
|
3008
|
+
else callback();
|
|
2810
3009
|
}
|
|
2811
|
-
function
|
|
2812
|
-
|
|
2813
|
-
|
|
3010
|
+
function parsePluginStream(ctx, depth, id, current, currentPlugins) {
|
|
3011
|
+
for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
3012
|
+
const plugin = currentPlugins[i];
|
|
3013
|
+
if (plugin.parse.stream && plugin.test(current)) return createPluginNode(id, plugin.tag, plugin.parse.stream(current, getStreamParsePluginContext(ctx, depth), { id }));
|
|
3014
|
+
}
|
|
3015
|
+
}
|
|
3016
|
+
/**
|
|
3017
|
+
* One listener shape serves both `Stream.on` (no accept) and
|
|
3018
|
+
* `LiveStream.pump` (accept tied to record acceptance). Handlers return the
|
|
3019
|
+
* parse error so the pump can stop the source.
|
|
3020
|
+
*/
|
|
3021
|
+
function streamListener(ctx, depth, id, subscription) {
|
|
3022
|
+
const handle = (type, terminal) => (value, accept) => {
|
|
3023
|
+
let failure = void 0;
|
|
3024
|
+
if (ctx.state.alive) try {
|
|
3025
|
+
failure = parseEvent(ctx, depth, value, createStreamEventNode.bind(null, type, id), accept);
|
|
3026
|
+
} catch (error) {
|
|
3027
|
+
if (!subscription?.active) throw error;
|
|
3028
|
+
subscription.failure ?? (subscription.failure = { value: error });
|
|
3029
|
+
failure = error;
|
|
3030
|
+
}
|
|
3031
|
+
if (terminal && !accept) popPendingState(ctx);
|
|
3032
|
+
return failure;
|
|
3033
|
+
};
|
|
3034
|
+
return {
|
|
3035
|
+
next: handle(32, false),
|
|
3036
|
+
throw: handle(33, true),
|
|
3037
|
+
return: handle(34, true),
|
|
3038
|
+
done() {
|
|
3039
|
+
popPendingState(ctx);
|
|
3040
|
+
},
|
|
3041
|
+
error(reason) {
|
|
3042
|
+
if (ctx.state.alive) stopStreamParse(ctx, 1, reason);
|
|
3043
|
+
}
|
|
3044
|
+
};
|
|
2814
3045
|
}
|
|
2815
|
-
function
|
|
3046
|
+
function subscribeStream(ctx, depth, id, current) {
|
|
3047
|
+
pushPendingState(ctx);
|
|
3048
|
+
const subscription = {
|
|
3049
|
+
active: true,
|
|
3050
|
+
failure: void 0
|
|
3051
|
+
};
|
|
3052
|
+
let cleanup;
|
|
3053
|
+
try {
|
|
3054
|
+
cleanup = current.on(streamListener(ctx, depth, id, subscription));
|
|
3055
|
+
} finally {
|
|
3056
|
+
subscription.active = false;
|
|
3057
|
+
}
|
|
2816
3058
|
try {
|
|
2817
|
-
ctx
|
|
3059
|
+
addCleanup(ctx, cleanup);
|
|
2818
3060
|
} catch (error) {
|
|
2819
|
-
|
|
3061
|
+
subscription.failure ?? (subscription.failure = { value: error });
|
|
2820
3062
|
}
|
|
3063
|
+
const failure = subscription.failure;
|
|
3064
|
+
subscription.failure = void 0;
|
|
3065
|
+
if (failure) throw failure.value;
|
|
3066
|
+
}
|
|
3067
|
+
function consumeLiveStream(ctx, depth, id, current) {
|
|
3068
|
+
const cancel = current.pump(streamListener(ctx, depth, id));
|
|
3069
|
+
pushPendingState(ctx);
|
|
3070
|
+
addCleanup(ctx, () => {
|
|
3071
|
+
cancel(ctx.state.reason);
|
|
3072
|
+
});
|
|
3073
|
+
}
|
|
3074
|
+
function wrapPromiseResult(ctx, type, id, node) {
|
|
3075
|
+
return createSerovalNode(type, id, void 0, void 0, void 0, void 0, void 0, [parseSpecialReference(ctx.base, type === 23 ? 2 : 3), node], void 0, void 0, void 0, void 0);
|
|
3076
|
+
}
|
|
3077
|
+
function handlePromise(type, id, depth, data) {
|
|
3078
|
+
if (this.state.alive) parseEvent(this, depth, data, wrapPromiseResult.bind(null, this, type, id), void 0);
|
|
3079
|
+
popPendingState(this);
|
|
3080
|
+
}
|
|
3081
|
+
function watchPromise(ctx, resolver, depth, current) {
|
|
3082
|
+
pushPendingState(ctx);
|
|
3083
|
+
current.then(handlePromise.bind(ctx, 23, resolver, depth), handlePromise.bind(ctx, 24, resolver, depth));
|
|
3084
|
+
}
|
|
3085
|
+
function returnIterator(iterator) {
|
|
3086
|
+
Promise.resolve().then(() => iterator.return?.()).catch(() => {});
|
|
3087
|
+
}
|
|
3088
|
+
/**
|
|
3089
|
+
* Drives an async iterator directly. The next value is pulled only after the
|
|
3090
|
+
* record for the previous one has been accepted, and cancellation returns
|
|
3091
|
+
* the iterator once.
|
|
3092
|
+
*/
|
|
3093
|
+
function iterateAsync(ctx, depth, id, current, forwardReason) {
|
|
3094
|
+
const iterator = current[SYM_ASYNC_ITERATOR]();
|
|
3095
|
+
const listener = streamListener(ctx, depth, id);
|
|
3096
|
+
let active = true;
|
|
3097
|
+
function stop() {
|
|
3098
|
+
if (active) {
|
|
3099
|
+
active = false;
|
|
3100
|
+
if (forwardReason) try {
|
|
3101
|
+
Promise.resolve(iterator.return?.(ctx.state.reason)).catch(() => {});
|
|
3102
|
+
} catch {}
|
|
3103
|
+
else returnIterator(iterator);
|
|
3104
|
+
}
|
|
3105
|
+
}
|
|
3106
|
+
function pull() {
|
|
3107
|
+
if (active) iterator.next().then((result) => {
|
|
3108
|
+
if (active) {
|
|
3109
|
+
if (result.done) {
|
|
3110
|
+
active = false;
|
|
3111
|
+
listener.return(result.value, void 0);
|
|
3112
|
+
} else if (listener.next(result.value, pull) !== void 0) {
|
|
3113
|
+
stop();
|
|
3114
|
+
listener.done();
|
|
3115
|
+
}
|
|
3116
|
+
}
|
|
3117
|
+
}, (error) => {
|
|
3118
|
+
if (active) {
|
|
3119
|
+
active = false;
|
|
3120
|
+
listener.throw(error, void 0);
|
|
3121
|
+
}
|
|
3122
|
+
});
|
|
3123
|
+
}
|
|
3124
|
+
pushPendingState(ctx);
|
|
3125
|
+
addCleanup(ctx, stop);
|
|
3126
|
+
pull();
|
|
3127
|
+
}
|
|
3128
|
+
function createStreamParserState(options) {
|
|
3129
|
+
return {
|
|
3130
|
+
alive: true,
|
|
3131
|
+
pending: 0,
|
|
3132
|
+
parsing: 0,
|
|
3133
|
+
queue: [],
|
|
3134
|
+
writing: false,
|
|
3135
|
+
inFlight: void 0,
|
|
3136
|
+
reason: void 0,
|
|
3137
|
+
onParse: options.onParse,
|
|
3138
|
+
onError: options.onError,
|
|
3139
|
+
onDone: options.onDone,
|
|
3140
|
+
cleanups: [],
|
|
3141
|
+
pluginContexts: [],
|
|
3142
|
+
stream: subscribeStream,
|
|
3143
|
+
live: consumeLiveStream,
|
|
3144
|
+
promise: watchPromise,
|
|
3145
|
+
iterable: iterateAsync,
|
|
3146
|
+
plugin: parsePluginStream
|
|
3147
|
+
};
|
|
3148
|
+
}
|
|
3149
|
+
function createStreamParserContext(options) {
|
|
3150
|
+
return {
|
|
3151
|
+
type: 2,
|
|
3152
|
+
base: createBaseParserContext(options),
|
|
3153
|
+
state: createStreamParserState(options)
|
|
3154
|
+
};
|
|
2821
3155
|
}
|
|
2822
3156
|
function pushPendingState(ctx) {
|
|
2823
|
-
ctx.state.pending++;
|
|
3157
|
+
if (ctx.state.alive) ctx.state.pending++;
|
|
2824
3158
|
}
|
|
2825
3159
|
function popPendingState(ctx) {
|
|
2826
|
-
if (
|
|
3160
|
+
if (ctx.state.alive) {
|
|
3161
|
+
ctx.state.pending--;
|
|
3162
|
+
checkStreamParse(ctx);
|
|
3163
|
+
}
|
|
2827
3164
|
}
|
|
2828
|
-
|
|
3165
|
+
/**
|
|
3166
|
+
* Parses a value that arrived after the root. Its record is queued before
|
|
3167
|
+
* parsing starts so that records discovered inside it follow it, and it is
|
|
3168
|
+
* dropped again if parsing fails. Returns the parse error after reporting
|
|
3169
|
+
* it, or `undefined`.
|
|
3170
|
+
*/
|
|
3171
|
+
function parseEvent(ctx, depth, value, wrap, accept) {
|
|
3172
|
+
const state = ctx.state;
|
|
3173
|
+
const record = {
|
|
3174
|
+
node: void 0,
|
|
3175
|
+
initial: false,
|
|
3176
|
+
accept
|
|
3177
|
+
};
|
|
3178
|
+
let failure;
|
|
3179
|
+
state.queue.push(record);
|
|
3180
|
+
state.parsing++;
|
|
2829
3181
|
try {
|
|
2830
|
-
|
|
2831
|
-
} catch (
|
|
2832
|
-
|
|
2833
|
-
|
|
3182
|
+
record.node = wrap(parseSOS(ctx, depth, value));
|
|
3183
|
+
} catch (error) {
|
|
3184
|
+
failure = { value: error };
|
|
3185
|
+
} finally {
|
|
3186
|
+
state.parsing--;
|
|
3187
|
+
if (!state.alive) releaseParserValues(ctx);
|
|
2834
3188
|
}
|
|
3189
|
+
if (failure) stopStreamParse(ctx, 1, failure.value);
|
|
3190
|
+
else drainOutput(ctx);
|
|
3191
|
+
return failure?.value;
|
|
3192
|
+
}
|
|
3193
|
+
/**
|
|
3194
|
+
* Emits queued records one at a time. A callback that returns a promise
|
|
3195
|
+
* pauses emission until it settles; the source event behind the record is
|
|
3196
|
+
* accepted only after that.
|
|
3197
|
+
*/
|
|
3198
|
+
function drainOutput(ctx) {
|
|
3199
|
+
const state = ctx.state;
|
|
3200
|
+
if (state.writing || state.parsing > 0) return;
|
|
3201
|
+
while (state.alive && state.queue.length > 0) {
|
|
3202
|
+
const record = state.queue.shift();
|
|
3203
|
+
if (!record.node) continue;
|
|
3204
|
+
let pending;
|
|
3205
|
+
state.writing = true;
|
|
3206
|
+
state.inFlight = record;
|
|
3207
|
+
state.parsing++;
|
|
3208
|
+
try {
|
|
3209
|
+
if (!state.onParse) throw new Error("Stream output callback is unavailable");
|
|
3210
|
+
const result = state.onParse(record.node, record.initial);
|
|
3211
|
+
if (result !== null && (typeof result === "object" || typeof result === "function")) {
|
|
3212
|
+
const then = Reflect.get(result, "then");
|
|
3213
|
+
if (typeof then === "function") pending = new Promise((resolve, reject) => {
|
|
3214
|
+
Reflect.apply(then, result, [resolve, reject]);
|
|
3215
|
+
});
|
|
3216
|
+
}
|
|
3217
|
+
} catch (error) {
|
|
3218
|
+
releaseRecord(record);
|
|
3219
|
+
stopStreamParse(ctx, 1, error);
|
|
3220
|
+
return;
|
|
3221
|
+
} finally {
|
|
3222
|
+
state.parsing--;
|
|
3223
|
+
if (!state.alive) releaseParserValues(ctx);
|
|
3224
|
+
}
|
|
3225
|
+
record.node = void 0;
|
|
3226
|
+
if (pending) {
|
|
3227
|
+
if (!state.alive) releaseRecord(record);
|
|
3228
|
+
pending.then(() => {
|
|
3229
|
+
state.writing = false;
|
|
3230
|
+
state.inFlight = void 0;
|
|
3231
|
+
if (state.alive) {
|
|
3232
|
+
const accept = record.accept;
|
|
3233
|
+
releaseRecord(record);
|
|
3234
|
+
accept?.();
|
|
3235
|
+
drainOutput(ctx);
|
|
3236
|
+
}
|
|
3237
|
+
}, (error) => {
|
|
3238
|
+
state.writing = false;
|
|
3239
|
+
state.inFlight = void 0;
|
|
3240
|
+
releaseRecord(record);
|
|
3241
|
+
stopStreamParse(ctx, 1, error);
|
|
3242
|
+
});
|
|
3243
|
+
return;
|
|
3244
|
+
}
|
|
3245
|
+
if (!state.alive) {
|
|
3246
|
+
releaseRecord(record);
|
|
3247
|
+
return;
|
|
3248
|
+
}
|
|
3249
|
+
state.writing = false;
|
|
3250
|
+
state.inFlight = void 0;
|
|
3251
|
+
const accept = record.accept;
|
|
3252
|
+
releaseRecord(record);
|
|
3253
|
+
accept?.();
|
|
3254
|
+
}
|
|
3255
|
+
checkStreamParse(ctx);
|
|
3256
|
+
}
|
|
3257
|
+
function checkStreamParse(ctx) {
|
|
3258
|
+
const state = ctx.state;
|
|
3259
|
+
if (state.alive && state.parsing === 0 && state.pending <= 0 && state.queue.length === 0 && !state.writing) stopStreamParse(ctx, 0);
|
|
2835
3260
|
}
|
|
2836
3261
|
function startStreamParse(ctx, current) {
|
|
2837
|
-
const
|
|
2838
|
-
|
|
2839
|
-
|
|
2840
|
-
|
|
2841
|
-
|
|
2842
|
-
|
|
3262
|
+
const state = ctx.state;
|
|
3263
|
+
let parsed;
|
|
3264
|
+
let failure;
|
|
3265
|
+
state.parsing++;
|
|
3266
|
+
try {
|
|
3267
|
+
parsed = parseSOS(ctx, 0, current);
|
|
3268
|
+
} catch (error) {
|
|
3269
|
+
failure = { value: error };
|
|
3270
|
+
} finally {
|
|
3271
|
+
state.parsing--;
|
|
3272
|
+
if (!state.alive) releaseParserValues(ctx);
|
|
3273
|
+
}
|
|
3274
|
+
if (failure) {
|
|
3275
|
+
if (state.alive) stopStreamParse(ctx, 1, failure.value);
|
|
3276
|
+
else throw failure.value;
|
|
3277
|
+
} else if (parsed && state.alive) {
|
|
3278
|
+
state.queue.unshift({
|
|
3279
|
+
node: parsed,
|
|
3280
|
+
initial: true,
|
|
3281
|
+
accept: void 0
|
|
3282
|
+
});
|
|
3283
|
+
drainOutput(ctx);
|
|
3284
|
+
}
|
|
3285
|
+
}
|
|
3286
|
+
function runCleanups(state) {
|
|
3287
|
+
const cleanups = state.cleanups;
|
|
3288
|
+
let failure;
|
|
3289
|
+
state.cleanups = [];
|
|
3290
|
+
for (const record of state.queue) releaseRecord(record);
|
|
3291
|
+
state.queue.length = 0;
|
|
3292
|
+
if (state.inFlight) releaseRecord(state.inFlight);
|
|
3293
|
+
state.inFlight = void 0;
|
|
3294
|
+
for (let i = 0, len = cleanups.length; i < len; i++) try {
|
|
3295
|
+
cleanups[i]();
|
|
3296
|
+
} catch (error) {
|
|
3297
|
+
failure ?? (failure = { value: error });
|
|
2843
3298
|
}
|
|
3299
|
+
if (failure) throw failure.value;
|
|
2844
3300
|
}
|
|
2845
|
-
function
|
|
2846
|
-
|
|
3301
|
+
function releaseRecord(record) {
|
|
3302
|
+
record.node = void 0;
|
|
3303
|
+
record.accept = void 0;
|
|
2847
3304
|
}
|
|
2848
|
-
function
|
|
2849
|
-
|
|
2850
|
-
|
|
2851
|
-
|
|
3305
|
+
function releaseParserValues(ctx) {
|
|
3306
|
+
ctx.base.refs = /* @__PURE__ */ new Map();
|
|
3307
|
+
ctx.base.marked.clear();
|
|
3308
|
+
ctx.base.plugins = void 0;
|
|
3309
|
+
ctx.base.plainObjectPlugins = void 0;
|
|
3310
|
+
ctx.state.pluginContexts = [];
|
|
3311
|
+
if (ctx.state.parsing === 0) ctx.state.reason = void 0;
|
|
3312
|
+
}
|
|
3313
|
+
/**
|
|
3314
|
+
* Ends the parse once: `onDone` on success, `onError` on failure, and every
|
|
3315
|
+
* cleanup either way.
|
|
3316
|
+
*/
|
|
3317
|
+
function stopStreamParse(ctx, mode, reason) {
|
|
3318
|
+
const state = ctx.state;
|
|
3319
|
+
if (state.alive) {
|
|
3320
|
+
state.alive = false;
|
|
3321
|
+
const onError = state.onError;
|
|
3322
|
+
const onDone = state.onDone;
|
|
3323
|
+
if (mode === 1 && !onError && !(reason instanceof SerovalParserError)) reason = new SerovalParserError(reason);
|
|
3324
|
+
state.reason = reason;
|
|
3325
|
+
state.onParse = void 0;
|
|
3326
|
+
state.onError = void 0;
|
|
3327
|
+
state.onDone = void 0;
|
|
3328
|
+
state.writing = false;
|
|
3329
|
+
state.parsing++;
|
|
3330
|
+
let failure;
|
|
3331
|
+
try {
|
|
3332
|
+
if (mode === 1) {
|
|
3333
|
+
if (onError) onError(reason);
|
|
3334
|
+
else throw reason;
|
|
3335
|
+
} else if (mode === 0) onDone?.();
|
|
3336
|
+
} catch (error) {
|
|
3337
|
+
failure = { value: error };
|
|
3338
|
+
}
|
|
3339
|
+
try {
|
|
3340
|
+
runCleanups(state);
|
|
3341
|
+
} catch (error) {
|
|
3342
|
+
failure ?? (failure = { value: error });
|
|
3343
|
+
} finally {
|
|
3344
|
+
state.parsing--;
|
|
3345
|
+
releaseParserValues(ctx);
|
|
3346
|
+
state.pending = 0;
|
|
3347
|
+
}
|
|
3348
|
+
if (failure) throw failure.value;
|
|
2852
3349
|
}
|
|
2853
3350
|
}
|
|
3351
|
+
function destroyStreamParse(ctx, reason) {
|
|
3352
|
+
stopStreamParse(ctx, 2, reason);
|
|
3353
|
+
}
|
|
2854
3354
|
//#endregion
|
|
2855
3355
|
//#region src/core/cross/index.ts
|
|
2856
3356
|
function crossSerialize(source, options = {}) {
|
|
2857
3357
|
const plugins = resolvePlugins(options.plugins);
|
|
2858
|
-
const ctx = createSyncParserContext(
|
|
3358
|
+
const ctx = createSyncParserContext({
|
|
2859
3359
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3360
|
+
depthLimit: options.depthLimit,
|
|
2860
3361
|
plugins,
|
|
2861
3362
|
disabledFeatures: options.disabledFeatures,
|
|
2862
3363
|
refs: options.refs
|
|
@@ -2866,13 +3367,15 @@ function crossSerialize(source, options = {}) {
|
|
|
2866
3367
|
plugins,
|
|
2867
3368
|
features: ctx.base.features,
|
|
2868
3369
|
scopeId: options.scopeId,
|
|
2869
|
-
markedRefs: ctx.base.marked
|
|
3370
|
+
markedRefs: ctx.base.marked,
|
|
3371
|
+
assignSharedRefsOnly: options.assignSharedRefsOnly
|
|
2870
3372
|
}), tree);
|
|
2871
3373
|
}
|
|
2872
3374
|
async function crossSerializeAsync(source, options = {}) {
|
|
2873
3375
|
const plugins = resolvePlugins(options.plugins);
|
|
2874
|
-
const ctx = createAsyncParserContext(
|
|
3376
|
+
const ctx = createAsyncParserContext({
|
|
2875
3377
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3378
|
+
depthLimit: options.depthLimit,
|
|
2876
3379
|
plugins,
|
|
2877
3380
|
disabledFeatures: options.disabledFeatures,
|
|
2878
3381
|
refs: options.refs
|
|
@@ -2882,13 +3385,15 @@ async function crossSerializeAsync(source, options = {}) {
|
|
|
2882
3385
|
plugins,
|
|
2883
3386
|
features: ctx.base.features,
|
|
2884
3387
|
scopeId: options.scopeId,
|
|
2885
|
-
markedRefs: ctx.base.marked
|
|
3388
|
+
markedRefs: ctx.base.marked,
|
|
3389
|
+
assignSharedRefsOnly: options.assignSharedRefsOnly
|
|
2886
3390
|
}), tree);
|
|
2887
3391
|
}
|
|
2888
3392
|
function toCrossJSON(source, options = {}) {
|
|
2889
3393
|
const plugins = resolvePlugins(options.plugins);
|
|
2890
|
-
return parseTop(createSyncParserContext(
|
|
3394
|
+
return parseTop(createSyncParserContext({
|
|
2891
3395
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3396
|
+
depthLimit: options.depthLimit,
|
|
2892
3397
|
plugins,
|
|
2893
3398
|
disabledFeatures: options.disabledFeatures,
|
|
2894
3399
|
refs: options.refs
|
|
@@ -2896,8 +3401,9 @@ function toCrossJSON(source, options = {}) {
|
|
|
2896
3401
|
}
|
|
2897
3402
|
async function toCrossJSONAsync(source, options = {}) {
|
|
2898
3403
|
const plugins = resolvePlugins(options.plugins);
|
|
2899
|
-
return await parseTopAsync(createAsyncParserContext(
|
|
3404
|
+
return await parseTopAsync(createAsyncParserContext({
|
|
2900
3405
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3406
|
+
depthLimit: options.depthLimit,
|
|
2901
3407
|
plugins,
|
|
2902
3408
|
disabledFeatures: options.disabledFeatures,
|
|
2903
3409
|
refs: options.refs
|
|
@@ -2905,8 +3411,11 @@ async function toCrossJSONAsync(source, options = {}) {
|
|
|
2905
3411
|
}
|
|
2906
3412
|
function crossSerializeStream(source, options) {
|
|
2907
3413
|
const plugins = resolvePlugins(options.plugins);
|
|
3414
|
+
const onSerialize = options.onSerialize;
|
|
3415
|
+
const scopeId = options.scopeId;
|
|
2908
3416
|
const ctx = createStreamParserContext({
|
|
2909
3417
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3418
|
+
depthLimit: options.depthLimit,
|
|
2910
3419
|
plugins,
|
|
2911
3420
|
refs: options.refs,
|
|
2912
3421
|
disabledFeatures: options.disabledFeatures,
|
|
@@ -2914,17 +3423,10 @@ function crossSerializeStream(source, options) {
|
|
|
2914
3423
|
const serial = createCrossSerializerContext({
|
|
2915
3424
|
plugins,
|
|
2916
3425
|
features: ctx.base.features,
|
|
2917
|
-
scopeId
|
|
3426
|
+
scopeId,
|
|
2918
3427
|
markedRefs: ctx.base.marked
|
|
2919
3428
|
});
|
|
2920
|
-
|
|
2921
|
-
try {
|
|
2922
|
-
serialized = serializeTopCross(serial, node);
|
|
2923
|
-
} catch (err) {
|
|
2924
|
-
if (options.onError) options.onError(err);
|
|
2925
|
-
return;
|
|
2926
|
-
}
|
|
2927
|
-
options.onSerialize(serialized, initial);
|
|
3429
|
+
return onSerialize(serializeTopCross(serial, node), initial);
|
|
2928
3430
|
},
|
|
2929
3431
|
onError: options.onError,
|
|
2930
3432
|
onDone: options.onDone
|
|
@@ -2947,22 +3449,39 @@ function toCrossJSONStream(source, options) {
|
|
|
2947
3449
|
startStreamParse(ctx, source);
|
|
2948
3450
|
return destroyStreamParse.bind(null, ctx);
|
|
2949
3451
|
}
|
|
2950
|
-
function
|
|
2951
|
-
|
|
2952
|
-
return deserializeTop(createCrossDeserializerContext({
|
|
3452
|
+
function createFromCrossJSONContext(options) {
|
|
3453
|
+
return createCrossDeserializerContext({
|
|
2953
3454
|
maxBase64Length: options.maxBase64Length,
|
|
2954
|
-
plugins,
|
|
3455
|
+
plugins: resolvePlugins(options.plugins),
|
|
2955
3456
|
refs: options.refs,
|
|
2956
3457
|
features: options.features,
|
|
2957
3458
|
disabledFeatures: options.disabledFeatures,
|
|
2958
3459
|
depthLimit: options.depthLimit
|
|
2959
|
-
})
|
|
3460
|
+
});
|
|
3461
|
+
}
|
|
3462
|
+
function fromCrossJSON(source, options) {
|
|
3463
|
+
return deserializeTop(createFromCrossJSONContext(options), source);
|
|
3464
|
+
}
|
|
3465
|
+
function createCrossDeserializer(options) {
|
|
3466
|
+
const ctx = createFromCrossJSONContext(options);
|
|
3467
|
+
ctx.base.pending = /* @__PURE__ */ new Set();
|
|
3468
|
+
return {
|
|
3469
|
+
deserialize(node) {
|
|
3470
|
+
if (!ctx.base.pending) throw new SerovalAbortedError();
|
|
3471
|
+
return deserializeTop(ctx, node);
|
|
3472
|
+
},
|
|
3473
|
+
get pending() {
|
|
3474
|
+
return ctx.base.pending?.size ?? 0;
|
|
3475
|
+
},
|
|
3476
|
+
abort(reason) {
|
|
3477
|
+
abortDeferred(ctx, reason);
|
|
3478
|
+
}
|
|
3479
|
+
};
|
|
2960
3480
|
}
|
|
2961
3481
|
//#endregion
|
|
2962
3482
|
//#region src/core/Serializer.ts
|
|
2963
3483
|
var Serializer = class {
|
|
2964
3484
|
constructor(options) {
|
|
2965
|
-
this.options = options;
|
|
2966
3485
|
this.alive = true;
|
|
2967
3486
|
this.flushed = false;
|
|
2968
3487
|
this.done = false;
|
|
@@ -2971,32 +3490,52 @@ var Serializer = class {
|
|
|
2971
3490
|
this.refs = /* @__PURE__ */ new Map();
|
|
2972
3491
|
this.keys = /* @__PURE__ */ new Set();
|
|
2973
3492
|
this.ids = 0;
|
|
3493
|
+
this.options = options;
|
|
2974
3494
|
this.plugins = resolvePlugins(options.plugins);
|
|
2975
3495
|
}
|
|
2976
3496
|
write(key, value) {
|
|
2977
|
-
|
|
3497
|
+
const options = this.options;
|
|
3498
|
+
if (this.alive && !this.flushed && options) {
|
|
2978
3499
|
this.pending++;
|
|
2979
3500
|
this.keys.add(key);
|
|
2980
|
-
|
|
3501
|
+
const cleanup = crossSerializeStream(value, {
|
|
2981
3502
|
plugins: this.plugins,
|
|
2982
|
-
scopeId:
|
|
3503
|
+
scopeId: options.scopeId,
|
|
2983
3504
|
refs: this.refs,
|
|
2984
|
-
disabledFeatures:
|
|
2985
|
-
compactArrayBufferViews:
|
|
2986
|
-
|
|
3505
|
+
disabledFeatures: options.disabledFeatures,
|
|
3506
|
+
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3507
|
+
depthLimit: options.depthLimit,
|
|
3508
|
+
onError: (error) => {
|
|
3509
|
+
let failure;
|
|
3510
|
+
try {
|
|
3511
|
+
if (options.onError) options.onError(error);
|
|
3512
|
+
else throw error instanceof SerovalParserError ? error : new SerovalParserError(error);
|
|
3513
|
+
} catch (handlerError) {
|
|
3514
|
+
failure = { value: handlerError };
|
|
3515
|
+
}
|
|
3516
|
+
try {
|
|
3517
|
+
this.finishWrite();
|
|
3518
|
+
} catch (finishError) {
|
|
3519
|
+
failure ?? (failure = { value: finishError });
|
|
3520
|
+
}
|
|
3521
|
+
if (failure) throw failure.value;
|
|
3522
|
+
},
|
|
2987
3523
|
onSerialize: (data, initial) => {
|
|
2988
|
-
|
|
3524
|
+
const current = this.options;
|
|
3525
|
+
if (this.alive && current) current.onData(initial ? current.globalIdentifier + "[\"" + serializeString(key) + "\"]=" + data : data);
|
|
2989
3526
|
},
|
|
2990
3527
|
onDone: () => {
|
|
2991
|
-
|
|
2992
|
-
this.pending--;
|
|
2993
|
-
if (this.pending <= 0 && this.flushed && !this.done && this.options.onDone) {
|
|
2994
|
-
this.options.onDone();
|
|
2995
|
-
this.done = true;
|
|
2996
|
-
}
|
|
2997
|
-
}
|
|
3528
|
+
this.finishWrite();
|
|
2998
3529
|
}
|
|
2999
|
-
})
|
|
3530
|
+
});
|
|
3531
|
+
if (this.alive) this.cleanups.push(cleanup);
|
|
3532
|
+
else cleanup();
|
|
3533
|
+
}
|
|
3534
|
+
}
|
|
3535
|
+
finishWrite() {
|
|
3536
|
+
if (this.alive) {
|
|
3537
|
+
this.pending--;
|
|
3538
|
+
if (this.pending <= 0 && this.flushed && !this.done) this.close();
|
|
3000
3539
|
}
|
|
3001
3540
|
}
|
|
3002
3541
|
getNextID() {
|
|
@@ -3011,20 +3550,36 @@ var Serializer = class {
|
|
|
3011
3550
|
flush() {
|
|
3012
3551
|
if (this.alive) {
|
|
3013
3552
|
this.flushed = true;
|
|
3014
|
-
if (this.pending <= 0 && !this.done
|
|
3015
|
-
this.options.onDone();
|
|
3016
|
-
this.done = true;
|
|
3017
|
-
}
|
|
3553
|
+
if (this.pending <= 0 && !this.done) this.close();
|
|
3018
3554
|
}
|
|
3019
3555
|
}
|
|
3020
3556
|
close() {
|
|
3557
|
+
this.finish();
|
|
3558
|
+
}
|
|
3559
|
+
finish() {
|
|
3021
3560
|
if (this.alive) {
|
|
3022
|
-
|
|
3023
|
-
|
|
3024
|
-
|
|
3561
|
+
this.alive = false;
|
|
3562
|
+
const options = this.options;
|
|
3563
|
+
this.options = void 0;
|
|
3564
|
+
this.plugins = void 0;
|
|
3565
|
+
const cleanups = this.cleanups;
|
|
3566
|
+
this.cleanups = [];
|
|
3567
|
+
let failure;
|
|
3568
|
+
for (let index = 0, length = cleanups.length; index < length; index++) try {
|
|
3569
|
+
cleanups[index]();
|
|
3570
|
+
} catch (error) {
|
|
3571
|
+
failure ?? (failure = { value: error });
|
|
3572
|
+
}
|
|
3573
|
+
this.refs.clear();
|
|
3574
|
+
if (!this.done) {
|
|
3025
3575
|
this.done = true;
|
|
3576
|
+
try {
|
|
3577
|
+
options?.onDone?.();
|
|
3578
|
+
} catch (error) {
|
|
3579
|
+
failure ?? (failure = { value: error });
|
|
3580
|
+
}
|
|
3026
3581
|
}
|
|
3027
|
-
|
|
3582
|
+
if (failure) throw failure.value;
|
|
3028
3583
|
}
|
|
3029
3584
|
}
|
|
3030
3585
|
};
|
|
@@ -3032,8 +3587,9 @@ var Serializer = class {
|
|
|
3032
3587
|
//#region src/core/tree/index.ts
|
|
3033
3588
|
function serialize(source, options = {}) {
|
|
3034
3589
|
const plugins = resolvePlugins(options.plugins);
|
|
3035
|
-
const ctx = createSyncParserContext(
|
|
3590
|
+
const ctx = createSyncParserContext({
|
|
3036
3591
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3592
|
+
depthLimit: options.depthLimit,
|
|
3037
3593
|
plugins,
|
|
3038
3594
|
disabledFeatures: options.disabledFeatures
|
|
3039
3595
|
});
|
|
@@ -3046,8 +3602,9 @@ function serialize(source, options = {}) {
|
|
|
3046
3602
|
}
|
|
3047
3603
|
async function serializeAsync(source, options = {}) {
|
|
3048
3604
|
const plugins = resolvePlugins(options.plugins);
|
|
3049
|
-
const ctx = createAsyncParserContext(
|
|
3605
|
+
const ctx = createAsyncParserContext({
|
|
3050
3606
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3607
|
+
depthLimit: options.depthLimit,
|
|
3051
3608
|
plugins,
|
|
3052
3609
|
disabledFeatures: options.disabledFeatures
|
|
3053
3610
|
});
|
|
@@ -3063,8 +3620,9 @@ function deserialize(source) {
|
|
|
3063
3620
|
}
|
|
3064
3621
|
function toJSON(source, options = {}) {
|
|
3065
3622
|
const plugins = resolvePlugins(options.plugins);
|
|
3066
|
-
const ctx = createSyncParserContext(
|
|
3623
|
+
const ctx = createSyncParserContext({
|
|
3067
3624
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3625
|
+
depthLimit: options.depthLimit,
|
|
3068
3626
|
plugins,
|
|
3069
3627
|
disabledFeatures: options.disabledFeatures
|
|
3070
3628
|
});
|
|
@@ -3076,8 +3634,9 @@ function toJSON(source, options = {}) {
|
|
|
3076
3634
|
}
|
|
3077
3635
|
async function toJSONAsync(source, options = {}) {
|
|
3078
3636
|
const plugins = resolvePlugins(options.plugins);
|
|
3079
|
-
const ctx = createAsyncParserContext(
|
|
3637
|
+
const ctx = createAsyncParserContext({
|
|
3080
3638
|
compactArrayBufferViews: options.compactArrayBufferViews,
|
|
3639
|
+
depthLimit: options.depthLimit,
|
|
3081
3640
|
plugins,
|
|
3082
3641
|
disabledFeatures: options.disabledFeatures
|
|
3083
3642
|
});
|
|
@@ -3095,11 +3654,11 @@ function compileJSON(source, options = {}) {
|
|
|
3095
3654
|
}), source.t);
|
|
3096
3655
|
}
|
|
3097
3656
|
function fromJSON(source, options = {}) {
|
|
3098
|
-
var _source$f;
|
|
3099
3657
|
const plugins = resolvePlugins(options.plugins);
|
|
3100
|
-
const disabledFeatures = options.disabledFeatures
|
|
3101
|
-
const sourceFeatures =
|
|
3658
|
+
const disabledFeatures = options.disabledFeatures ?? 0;
|
|
3659
|
+
const sourceFeatures = source.f ?? 127;
|
|
3102
3660
|
return deserializeTop(createVanillaDeserializerContext({
|
|
3661
|
+
depthLimit: options.depthLimit,
|
|
3103
3662
|
maxBase64Length: options.maxBase64Length,
|
|
3104
3663
|
plugins,
|
|
3105
3664
|
markedRefs: source.m,
|
|
@@ -3109,12 +3668,16 @@ function fromJSON(source, options = {}) {
|
|
|
3109
3668
|
}
|
|
3110
3669
|
//#endregion
|
|
3111
3670
|
exports.Feature = Feature;
|
|
3671
|
+
exports.LiveStream = LiveStream;
|
|
3112
3672
|
exports.OpaqueReference = OpaqueReference;
|
|
3673
|
+
exports.Sequence = Sequence;
|
|
3113
3674
|
exports.Serializer = Serializer;
|
|
3675
|
+
exports.SerovalAbortedError = SerovalAbortedError;
|
|
3114
3676
|
exports.SerovalConflictedNodeIdError = SerovalConflictedNodeIdError;
|
|
3115
3677
|
exports.SerovalDepthLimitError = SerovalDepthLimitError;
|
|
3116
3678
|
exports.SerovalDeserializationError = SerovalDeserializationError;
|
|
3117
3679
|
exports.SerovalError = SerovalError;
|
|
3680
|
+
exports.SerovalLiveStreamError = SerovalLiveStreamError;
|
|
3118
3681
|
exports.SerovalMalformedNodeError = SerovalMalformedNodeError;
|
|
3119
3682
|
exports.SerovalMissingInstanceError = SerovalMissingInstanceError;
|
|
3120
3683
|
exports.SerovalMissingPluginError = SerovalMissingPluginError;
|
|
@@ -3126,7 +3689,10 @@ exports.SerovalSerializationError = SerovalSerializationError;
|
|
|
3126
3689
|
exports.SerovalUnknownTypedArrayError = SerovalUnknownTypedArrayError;
|
|
3127
3690
|
exports.SerovalUnsupportedNodeError = SerovalUnsupportedNodeError;
|
|
3128
3691
|
exports.SerovalUnsupportedTypeError = SerovalUnsupportedTypeError;
|
|
3692
|
+
exports.Stream = Stream;
|
|
3129
3693
|
exports.compileJSON = compileJSON;
|
|
3694
|
+
exports.createCrossDeserializer = createCrossDeserializer;
|
|
3695
|
+
exports.createLiveStream = createLiveStream;
|
|
3130
3696
|
exports.createPlugin = createPlugin;
|
|
3131
3697
|
exports.createReference = createReference;
|
|
3132
3698
|
exports.createStream = createStream;
|
|
@@ -3137,6 +3703,8 @@ exports.deserialize = deserialize;
|
|
|
3137
3703
|
exports.fromCrossJSON = fromCrossJSON;
|
|
3138
3704
|
exports.fromJSON = fromJSON;
|
|
3139
3705
|
exports.getCrossReferenceHeader = getCrossReferenceHeader;
|
|
3706
|
+
exports.getPlainObjectPlugins = getPlainObjectPlugins;
|
|
3707
|
+
exports.isLiveStream = isLiveStream;
|
|
3140
3708
|
exports.isStream = isStream;
|
|
3141
3709
|
exports.resolvePlugins = resolvePlugins;
|
|
3142
3710
|
exports.serialize = serialize;
|