seroval 1.3.2 → 1.4.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/dist/cjs/development/index.cjs +2640 -2683
- package/dist/cjs/development/index.cjs.map +4 -4
- package/dist/cjs/production/index.cjs +3 -17
- package/dist/esm/development/index.mjs +2640 -2683
- package/dist/esm/development/index.mjs.map +4 -4
- package/dist/esm/production/index.mjs +3 -17
- package/dist/types/core/base-primitives.d.ts +1 -2
- package/dist/types/core/base-primitives.d.ts.map +1 -1
- package/dist/types/core/compat.d.ts +1 -1
- package/dist/types/core/compat.d.ts.map +1 -1
- package/dist/types/core/constants.d.ts +1 -0
- package/dist/types/core/constants.d.ts.map +1 -1
- package/dist/types/core/constructors.d.ts +54 -0
- package/dist/types/core/constructors.d.ts.map +1 -0
- package/dist/types/core/context/async-parser.d.ts +19 -0
- package/dist/types/core/context/async-parser.d.ts.map +1 -0
- package/dist/types/core/context/deserializer.d.ts +35 -38
- package/dist/types/core/context/deserializer.d.ts.map +1 -1
- package/dist/types/core/context/parser.d.ts +32 -19
- package/dist/types/core/context/parser.d.ts.map +1 -1
- package/dist/types/core/context/serializer.d.ts +38 -99
- package/dist/types/core/context/serializer.d.ts.map +1 -1
- package/dist/types/core/context/sync-parser.d.ts +59 -0
- package/dist/types/core/context/sync-parser.d.ts.map +1 -0
- package/dist/types/core/cross/index.d.ts +12 -13
- package/dist/types/core/cross/index.d.ts.map +1 -1
- package/dist/types/core/errors.d.ts.map +1 -1
- package/dist/types/core/function-string.d.ts +2 -2
- package/dist/types/core/function-string.d.ts.map +1 -1
- package/dist/types/core/plugin.d.ts +13 -11
- package/dist/types/core/plugin.d.ts.map +1 -1
- package/dist/types/core/reference.d.ts.map +1 -1
- package/dist/types/core/special-reference.d.ts +3 -2
- package/dist/types/core/special-reference.d.ts.map +1 -1
- package/dist/types/core/stream.d.ts +1 -2
- package/dist/types/core/stream.d.ts.map +1 -1
- package/dist/types/core/symbols.d.ts +14 -0
- package/dist/types/core/symbols.d.ts.map +1 -0
- package/dist/types/core/tree/index.d.ts +3 -2
- package/dist/types/core/tree/index.d.ts.map +1 -1
- package/dist/types/core/types.d.ts +3 -1
- package/dist/types/core/types.d.ts.map +1 -1
- package/dist/types/core/utils/iterator-to-sequence.d.ts.map +1 -1
- package/dist/types/index.d.ts +10 -5
- package/dist/types/index.d.ts.map +1 -1
- package/package.json +17 -19
- package/src/core/base-primitives.ts +0 -27
- package/src/core/compat.ts +2 -1
- package/src/core/constants.ts +28 -26
- package/src/core/constructors.ts +269 -0
- package/src/core/context/async-parser.ts +586 -0
- package/src/core/context/deserializer.ts +506 -316
- package/src/core/context/parser.ts +243 -180
- package/src/core/context/serializer.ts +1058 -827
- package/src/core/context/sync-parser.ts +833 -0
- package/src/core/cross/index.ts +63 -47
- package/src/core/errors.ts +73 -12
- package/src/core/function-string.ts +11 -10
- package/src/core/plugin.ts +20 -11
- package/src/core/reference.ts +8 -5
- package/src/core/special-reference.ts +18 -90
- package/src/core/stream.ts +18 -152
- package/src/core/symbols.ts +18 -0
- package/src/core/tree/index.ts +45 -31
- package/src/core/types.ts +7 -2
- package/src/core/utils/iterator-to-sequence.ts +6 -28
- package/src/index.ts +29 -11
- package/dist/types/core/context/parser/async.d.ts +0 -24
- package/dist/types/core/context/parser/async.d.ts.map +0 -1
- package/dist/types/core/context/parser/stream.d.ts +0 -43
- package/dist/types/core/context/parser/stream.d.ts.map +0 -1
- package/dist/types/core/context/parser/sync.d.ts +0 -30
- package/dist/types/core/context/parser/sync.d.ts.map +0 -1
- package/dist/types/core/cross/async.d.ts +0 -8
- package/dist/types/core/cross/async.d.ts.map +0 -1
- package/dist/types/core/cross/deserializer.d.ts +0 -9
- package/dist/types/core/cross/deserializer.d.ts.map +0 -1
- package/dist/types/core/cross/parser.d.ts +0 -6
- package/dist/types/core/cross/parser.d.ts.map +0 -1
- package/dist/types/core/cross/serializer.d.ts +0 -16
- package/dist/types/core/cross/serializer.d.ts.map +0 -1
- package/dist/types/core/cross/stream.d.ts +0 -8
- package/dist/types/core/cross/stream.d.ts.map +0 -1
- package/dist/types/core/cross/sync.d.ts +0 -8
- package/dist/types/core/cross/sync.d.ts.map +0 -1
- package/dist/types/core/tree/async.d.ts +0 -8
- package/dist/types/core/tree/async.d.ts.map +0 -1
- package/dist/types/core/tree/deserializer.d.ts +0 -13
- package/dist/types/core/tree/deserializer.d.ts.map +0 -1
- package/dist/types/core/tree/serializer.d.ts +0 -29
- package/dist/types/core/tree/serializer.d.ts.map +0 -1
- package/dist/types/core/tree/sync.d.ts +0 -8
- package/dist/types/core/tree/sync.d.ts.map +0 -1
- package/dist/types/core/utils/assert.d.ts +0 -2
- package/dist/types/core/utils/assert.d.ts.map +0 -1
- package/dist/types/core/utils/deferred.d.ts +0 -7
- package/dist/types/core/utils/deferred.d.ts.map +0 -1
- package/src/core/context/parser/async.ts +0 -495
- package/src/core/context/parser/stream.ts +0 -323
- package/src/core/context/parser/sync.ts +0 -404
- package/src/core/cross/async.ts +0 -9
- package/src/core/cross/deserializer.ts +0 -16
- package/src/core/cross/parser.ts +0 -7
- package/src/core/cross/serializer.ts +0 -72
- package/src/core/cross/stream.ts +0 -9
- package/src/core/cross/sync.ts +0 -9
- package/src/core/tree/async.ts +0 -9
- package/src/core/tree/deserializer.ts +0 -26
- package/src/core/tree/serializer.ts +0 -98
- package/src/core/tree/sync.ts +0 -9
- package/src/core/utils/assert.ts +0 -5
- package/src/core/utils/deferred.ts +0 -22
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"stream.d.ts","sourceRoot":"","sources":["../../../../src/core/cross/stream.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,8BAA8B,EAAE,MAAM,0BAA0B,CAAC;AAC/E,OAAO,uBAAuB,MAAM,0BAA0B,CAAC;AAC/D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAE7C,MAAM,MAAM,+BAA+B,GAAG,8BAA8B,CAAC;AAE7E,MAAM,CAAC,OAAO,OAAO,wBAAyB,SAAQ,uBAAuB;IAC3E,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAW;CACtC"}
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
import BaseSyncParserContext from '../context/parser/sync';
|
|
2
|
-
import type { SerovalMode } from '../plugin';
|
|
3
|
-
import type { CrossParserContextOptions } from './parser';
|
|
4
|
-
export type CrossSyncParserContextOptions = CrossParserContextOptions;
|
|
5
|
-
export default class CrossSyncParserContext extends BaseSyncParserContext {
|
|
6
|
-
readonly mode: SerovalMode;
|
|
7
|
-
}
|
|
8
|
-
//# sourceMappingURL=sync.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../../src/core/cross/sync.ts"],"names":[],"mappings":"AAAA,OAAO,qBAAqB,MAAM,wBAAwB,CAAC;AAC3D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAC7C,OAAO,KAAK,EAAE,yBAAyB,EAAE,MAAM,UAAU,CAAC;AAE1D,MAAM,MAAM,6BAA6B,GAAG,yBAAyB,CAAC;AAEtE,MAAM,CAAC,OAAO,OAAO,sBAAuB,SAAQ,qBAAqB;IACvE,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAW;CACtC"}
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
import type { BaseParserContextOptions } from '../context/parser';
|
|
2
|
-
import BaseAsyncParserContext from '../context/parser/async';
|
|
3
|
-
import type { SerovalMode } from '../plugin';
|
|
4
|
-
export type AsyncParserContextOptions = Omit<BaseParserContextOptions, 'refs'>;
|
|
5
|
-
export default class AsyncParserContext extends BaseAsyncParserContext {
|
|
6
|
-
readonly mode: SerovalMode;
|
|
7
|
-
}
|
|
8
|
-
//# sourceMappingURL=async.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"async.d.ts","sourceRoot":"","sources":["../../../../src/core/tree/async.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,mBAAmB,CAAC;AAClE,OAAO,sBAAsB,MAAM,yBAAyB,CAAC;AAC7D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAE7C,MAAM,MAAM,yBAAyB,GAAG,IAAI,CAAC,wBAAwB,EAAE,MAAM,CAAC,CAAC;AAE/E,MAAM,CAAC,OAAO,OAAO,kBAAmB,SAAQ,sBAAsB;IACpE,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAa;CACxC"}
|
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import type { BaseDeserializerOptions } from '../context/deserializer';
|
|
2
|
-
import BaseDeserializerContext from '../context/deserializer';
|
|
3
|
-
import type { SerovalMode } from '../plugin';
|
|
4
|
-
export interface VanillaDeserializerContextOptions extends Omit<BaseDeserializerOptions, 'refs'> {
|
|
5
|
-
markedRefs: number[] | Set<number>;
|
|
6
|
-
}
|
|
7
|
-
export default class VanillaDeserializerContext extends BaseDeserializerContext {
|
|
8
|
-
readonly mode: SerovalMode;
|
|
9
|
-
marked: Set<number>;
|
|
10
|
-
constructor(options: VanillaDeserializerContextOptions);
|
|
11
|
-
assignIndexedValue<T>(index: number, value: T): T;
|
|
12
|
-
}
|
|
13
|
-
//# sourceMappingURL=deserializer.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"deserializer.d.ts","sourceRoot":"","sources":["../../../../src/core/tree/deserializer.ts"],"names":[],"mappings":"AAAA,OAAO,KAAK,EAAE,uBAAuB,EAAE,MAAM,yBAAyB,CAAC;AACvE,OAAO,uBAAuB,MAAM,yBAAyB,CAAC;AAC9D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAE7C,MAAM,WAAW,iCACf,SAAQ,IAAI,CAAC,uBAAuB,EAAE,MAAM,CAAC;IAC7C,UAAU,EAAE,MAAM,EAAE,GAAG,GAAG,CAAC,MAAM,CAAC,CAAC;CACpC;AAED,MAAM,CAAC,OAAO,OAAO,0BAA2B,SAAQ,uBAAuB;IAC7E,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAa;IAEvC,MAAM,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;gBAER,OAAO,EAAE,iCAAiC;IAKtD,kBAAkB,CAAC,CAAC,EAAE,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,CAAC,GAAG,CAAC;CAMlD"}
|
|
@@ -1,29 +0,0 @@
|
|
|
1
|
-
import type { BaseSerializerContextOptions } from '../context/serializer';
|
|
2
|
-
import BaseSerializerContext from '../context/serializer';
|
|
3
|
-
import type { SerovalMode } from '../plugin';
|
|
4
|
-
import type { SerovalNode, SerovalPromiseConstructorNode, SerovalPromiseRejectNode, SerovalPromiseResolveNode } from '../types';
|
|
5
|
-
export type VanillaSerializerContextOptions = BaseSerializerContextOptions;
|
|
6
|
-
export default class VanillaSerializerContext extends BaseSerializerContext {
|
|
7
|
-
readonly mode: SerovalMode;
|
|
8
|
-
/**
|
|
9
|
-
* Map tree refs to actual refs
|
|
10
|
-
* @private
|
|
11
|
-
*/
|
|
12
|
-
valid: Map<number, number>;
|
|
13
|
-
/**
|
|
14
|
-
* Variables
|
|
15
|
-
* @private
|
|
16
|
-
*/
|
|
17
|
-
vars: string[];
|
|
18
|
-
/**
|
|
19
|
-
* Creates the reference param (identifier) from the given reference ID
|
|
20
|
-
* Calling this function means the value has been referenced somewhere
|
|
21
|
-
*/
|
|
22
|
-
getRefParam(index: number): string;
|
|
23
|
-
protected assignIndexedValue(index: number, value: string): string;
|
|
24
|
-
protected serializePromiseConstructor(node: SerovalPromiseConstructorNode): string;
|
|
25
|
-
protected serializePromiseResolve(node: SerovalPromiseResolveNode): string;
|
|
26
|
-
protected serializePromiseReject(node: SerovalPromiseRejectNode): string;
|
|
27
|
-
serializeTop(tree: SerovalNode): string;
|
|
28
|
-
}
|
|
29
|
-
//# sourceMappingURL=serializer.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"serializer.d.ts","sourceRoot":"","sources":["../../../../src/core/tree/serializer.ts"],"names":[],"mappings":"AACA,OAAO,KAAK,EAAE,4BAA4B,EAAE,MAAM,uBAAuB,CAAC;AAC1E,OAAO,qBAAqB,MAAM,uBAAuB,CAAC;AAE1D,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAC7C,OAAO,KAAK,EACV,WAAW,EACX,6BAA6B,EAC7B,wBAAwB,EACxB,yBAAyB,EAC1B,MAAM,UAAU,CAAC;AAGlB,MAAM,MAAM,+BAA+B,GAAG,4BAA4B,CAAC;AAE3E,MAAM,CAAC,OAAO,OAAO,wBAAyB,SAAQ,qBAAqB;IACzE,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAa;IAEvC;;;OAGG;IACH,KAAK,sBAA6B;IAElC;;;OAGG;IACH,IAAI,EAAE,MAAM,EAAE,CAAM;IAEpB;;;OAGG;IACH,WAAW,CAAC,KAAK,EAAE,MAAM,GAAG,MAAM;IAoBlC,SAAS,CAAC,kBAAkB,CAAC,KAAK,EAAE,MAAM,EAAE,KAAK,EAAE,MAAM,GAAG,MAAM;IAOlE,SAAS,CAAC,2BAA2B,CACnC,IAAI,EAAE,6BAA6B,GAClC,MAAM;IAIT,SAAS,CAAC,uBAAuB,CAAC,IAAI,EAAE,yBAAyB,GAAG,MAAM;IAI1E,SAAS,CAAC,sBAAsB,CAAC,IAAI,EAAE,wBAAwB,GAAG,MAAM;IAIxE,YAAY,CAAC,IAAI,EAAE,WAAW,GAAG,MAAM;CAsBxC"}
|
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
import BaseSyncParserContext from '../context/parser/sync';
|
|
2
|
-
import type { BaseParserContextOptions } from '../context/parser';
|
|
3
|
-
import type { SerovalMode } from '../plugin';
|
|
4
|
-
export type SyncParserContextOptions = Omit<BaseParserContextOptions, 'refs'>;
|
|
5
|
-
export default class SyncParserContext extends BaseSyncParserContext {
|
|
6
|
-
readonly mode: SerovalMode;
|
|
7
|
-
}
|
|
8
|
-
//# sourceMappingURL=sync.d.ts.map
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"sync.d.ts","sourceRoot":"","sources":["../../../../src/core/tree/sync.ts"],"names":[],"mappings":"AAAA,OAAO,qBAAqB,MAAM,wBAAwB,CAAC;AAC3D,OAAO,KAAK,EAAE,wBAAwB,EAAE,MAAM,mBAAmB,CAAC;AAClE,OAAO,KAAK,EAAE,WAAW,EAAE,MAAM,WAAW,CAAC;AAE7C,MAAM,MAAM,wBAAwB,GAAG,IAAI,CAAC,wBAAwB,EAAE,MAAM,CAAC,CAAC;AAE9E,MAAM,CAAC,OAAO,OAAO,iBAAkB,SAAQ,qBAAqB;IAClE,QAAQ,CAAC,IAAI,EAAE,WAAW,CAAa;CACxC"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"assert.d.ts","sourceRoot":"","sources":["../../../../src/core/utils/assert.ts"],"names":[],"mappings":"AAAA,MAAM,CAAC,OAAO,UAAU,MAAM,CAAC,IAAI,EAAE,OAAO,EAAE,KAAK,EAAE,KAAK,GAAG,OAAO,CAAC,IAAI,CAIxE"}
|
|
@@ -1 +0,0 @@
|
|
|
1
|
-
{"version":3,"file":"deferred.d.ts","sourceRoot":"","sources":["../../../../src/core/utils/deferred.ts"],"names":[],"mappings":"AAAA,MAAM,WAAW,QAAQ;IACvB,OAAO,EAAE,OAAO,CAAC,OAAO,CAAC,CAAC;IAC1B,OAAO,CAAC,KAAK,EAAE,OAAO,GAAG,IAAI,CAAC;IAC9B,MAAM,CAAC,KAAK,EAAE,OAAO,GAAG,IAAI,CAAC;CAC9B;AAED,wBAAgB,cAAc,IAAI,QAAQ,CAezC"}
|
|
@@ -1,495 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
createAggregateErrorNode,
|
|
3
|
-
createArrayBufferNode,
|
|
4
|
-
createArrayNode,
|
|
5
|
-
createAsyncIteratorFactoryInstanceNode,
|
|
6
|
-
createBigIntNode,
|
|
7
|
-
createBigIntTypedArrayNode,
|
|
8
|
-
createBoxedNode,
|
|
9
|
-
createDataViewNode,
|
|
10
|
-
createDateNode,
|
|
11
|
-
createErrorNode,
|
|
12
|
-
createIteratorFactoryInstanceNode,
|
|
13
|
-
createNumberNode,
|
|
14
|
-
createPluginNode,
|
|
15
|
-
createRegExpNode,
|
|
16
|
-
createSetNode,
|
|
17
|
-
createStreamConstructorNode,
|
|
18
|
-
createStreamNextNode,
|
|
19
|
-
createStreamReturnNode,
|
|
20
|
-
createStreamThrowNode,
|
|
21
|
-
createStringNode,
|
|
22
|
-
createTypedArrayNode,
|
|
23
|
-
} from '../../base-primitives';
|
|
24
|
-
import { Feature } from '../../compat';
|
|
25
|
-
import { NIL, SerovalNodeType } from '../../constants';
|
|
26
|
-
import { SerovalParserError, SerovalUnsupportedTypeError } from '../../errors';
|
|
27
|
-
import {
|
|
28
|
-
FALSE_NODE,
|
|
29
|
-
NULL_NODE,
|
|
30
|
-
TRUE_NODE,
|
|
31
|
-
UNDEFINED_NODE,
|
|
32
|
-
} from '../../literals';
|
|
33
|
-
import { createSerovalNode } from '../../node';
|
|
34
|
-
import { OpaqueReference } from '../../opaque-reference';
|
|
35
|
-
import { SpecialReference } from '../../special-reference';
|
|
36
|
-
import type { Stream } from '../../stream';
|
|
37
|
-
import { createStreamFromAsyncIterable, isStream } from '../../stream';
|
|
38
|
-
import { serializeString } from '../../string';
|
|
39
|
-
import type {
|
|
40
|
-
SerovalAggregateErrorNode,
|
|
41
|
-
SerovalArrayNode,
|
|
42
|
-
SerovalBigIntTypedArrayNode,
|
|
43
|
-
SerovalBoxedNode,
|
|
44
|
-
SerovalDataViewNode,
|
|
45
|
-
SerovalErrorNode,
|
|
46
|
-
SerovalMapNode,
|
|
47
|
-
SerovalNode,
|
|
48
|
-
SerovalNullConstructorNode,
|
|
49
|
-
SerovalObjectNode,
|
|
50
|
-
SerovalObjectRecordKey,
|
|
51
|
-
SerovalObjectRecordNode,
|
|
52
|
-
SerovalPluginNode,
|
|
53
|
-
SerovalPromiseNode,
|
|
54
|
-
SerovalSetNode,
|
|
55
|
-
SerovalStreamConstructorNode,
|
|
56
|
-
SerovalTypedArrayNode,
|
|
57
|
-
} from '../../types';
|
|
58
|
-
import { getErrorOptions } from '../../utils/error';
|
|
59
|
-
import { iteratorToSequence } from '../../utils/iterator-to-sequence';
|
|
60
|
-
import promiseToResult from '../../utils/promise-to-result';
|
|
61
|
-
import type {
|
|
62
|
-
BigIntTypedArrayValue,
|
|
63
|
-
TypedArrayValue,
|
|
64
|
-
} from '../../utils/typed-array';
|
|
65
|
-
import { BaseParserContext, ParserNodeType } from '../parser';
|
|
66
|
-
|
|
67
|
-
type ObjectLikeNode =
|
|
68
|
-
| SerovalObjectNode
|
|
69
|
-
| SerovalNullConstructorNode
|
|
70
|
-
| SerovalPromiseNode;
|
|
71
|
-
|
|
72
|
-
export default abstract class BaseAsyncParserContext extends BaseParserContext {
|
|
73
|
-
private async parseItems(current: unknown[]): Promise<SerovalNode[]> {
|
|
74
|
-
const nodes = [];
|
|
75
|
-
for (let i = 0, len = current.length; i < len; i++) {
|
|
76
|
-
// For consistency in holes
|
|
77
|
-
if (i in current) {
|
|
78
|
-
nodes[i] = await this.parse(current[i]);
|
|
79
|
-
}
|
|
80
|
-
}
|
|
81
|
-
return nodes;
|
|
82
|
-
}
|
|
83
|
-
|
|
84
|
-
private async parseArray(
|
|
85
|
-
id: number,
|
|
86
|
-
current: unknown[],
|
|
87
|
-
): Promise<SerovalArrayNode> {
|
|
88
|
-
return createArrayNode(id, current, await this.parseItems(current));
|
|
89
|
-
}
|
|
90
|
-
|
|
91
|
-
private async parseProperties(
|
|
92
|
-
properties: Record<string | symbol, unknown>,
|
|
93
|
-
): Promise<SerovalObjectRecordNode> {
|
|
94
|
-
const entries = Object.entries(properties);
|
|
95
|
-
const keyNodes: SerovalObjectRecordKey[] = [];
|
|
96
|
-
const valueNodes: SerovalNode[] = [];
|
|
97
|
-
for (let i = 0, len = entries.length; i < len; i++) {
|
|
98
|
-
keyNodes.push(serializeString(entries[i][0]));
|
|
99
|
-
valueNodes.push(await this.parse(entries[i][1]));
|
|
100
|
-
}
|
|
101
|
-
// Check special properties
|
|
102
|
-
let symbol = Symbol.iterator;
|
|
103
|
-
if (symbol in properties) {
|
|
104
|
-
keyNodes.push(this.parseWellKnownSymbol(symbol));
|
|
105
|
-
valueNodes.push(
|
|
106
|
-
createIteratorFactoryInstanceNode(
|
|
107
|
-
this.parseIteratorFactory(),
|
|
108
|
-
await this.parse(
|
|
109
|
-
iteratorToSequence(properties as unknown as Iterable<unknown>),
|
|
110
|
-
),
|
|
111
|
-
),
|
|
112
|
-
);
|
|
113
|
-
}
|
|
114
|
-
symbol = Symbol.asyncIterator;
|
|
115
|
-
if (symbol in properties) {
|
|
116
|
-
keyNodes.push(this.parseWellKnownSymbol(symbol));
|
|
117
|
-
valueNodes.push(
|
|
118
|
-
createAsyncIteratorFactoryInstanceNode(
|
|
119
|
-
this.parseAsyncIteratorFactory(),
|
|
120
|
-
await this.parse(
|
|
121
|
-
createStreamFromAsyncIterable(
|
|
122
|
-
properties as unknown as AsyncIterable<unknown>,
|
|
123
|
-
),
|
|
124
|
-
),
|
|
125
|
-
),
|
|
126
|
-
);
|
|
127
|
-
}
|
|
128
|
-
symbol = Symbol.toStringTag;
|
|
129
|
-
if (symbol in properties) {
|
|
130
|
-
keyNodes.push(this.parseWellKnownSymbol(symbol));
|
|
131
|
-
valueNodes.push(createStringNode(properties[symbol] as string));
|
|
132
|
-
}
|
|
133
|
-
symbol = Symbol.isConcatSpreadable;
|
|
134
|
-
if (symbol in properties) {
|
|
135
|
-
keyNodes.push(this.parseWellKnownSymbol(symbol));
|
|
136
|
-
valueNodes.push(properties[symbol] ? TRUE_NODE : FALSE_NODE);
|
|
137
|
-
}
|
|
138
|
-
return {
|
|
139
|
-
k: keyNodes,
|
|
140
|
-
v: valueNodes,
|
|
141
|
-
s: keyNodes.length,
|
|
142
|
-
};
|
|
143
|
-
}
|
|
144
|
-
|
|
145
|
-
private async parsePlainObject(
|
|
146
|
-
id: number,
|
|
147
|
-
current: Record<string, unknown>,
|
|
148
|
-
empty: boolean,
|
|
149
|
-
): Promise<ObjectLikeNode> {
|
|
150
|
-
return this.createObjectNode(
|
|
151
|
-
id,
|
|
152
|
-
current,
|
|
153
|
-
empty,
|
|
154
|
-
await this.parseProperties(current),
|
|
155
|
-
);
|
|
156
|
-
}
|
|
157
|
-
|
|
158
|
-
private async parseBoxed(
|
|
159
|
-
id: number,
|
|
160
|
-
current: object,
|
|
161
|
-
): Promise<SerovalBoxedNode> {
|
|
162
|
-
return createBoxedNode(id, await this.parse(current.valueOf()));
|
|
163
|
-
}
|
|
164
|
-
|
|
165
|
-
private async parseTypedArray(
|
|
166
|
-
id: number,
|
|
167
|
-
current: TypedArrayValue,
|
|
168
|
-
): Promise<SerovalTypedArrayNode> {
|
|
169
|
-
return createTypedArrayNode(id, current, await this.parse(current.buffer));
|
|
170
|
-
}
|
|
171
|
-
|
|
172
|
-
private async parseBigIntTypedArray(
|
|
173
|
-
id: number,
|
|
174
|
-
current: BigIntTypedArrayValue,
|
|
175
|
-
): Promise<SerovalBigIntTypedArrayNode> {
|
|
176
|
-
return createBigIntTypedArrayNode(
|
|
177
|
-
id,
|
|
178
|
-
current,
|
|
179
|
-
await this.parse(current.buffer),
|
|
180
|
-
);
|
|
181
|
-
}
|
|
182
|
-
|
|
183
|
-
private async parseDataView(
|
|
184
|
-
id: number,
|
|
185
|
-
current: DataView,
|
|
186
|
-
): Promise<SerovalDataViewNode> {
|
|
187
|
-
return createDataViewNode(id, current, await this.parse(current.buffer));
|
|
188
|
-
}
|
|
189
|
-
|
|
190
|
-
private async parseError(
|
|
191
|
-
id: number,
|
|
192
|
-
current: Error,
|
|
193
|
-
): Promise<SerovalErrorNode> {
|
|
194
|
-
const options = getErrorOptions(current, this.features);
|
|
195
|
-
return createErrorNode(
|
|
196
|
-
id,
|
|
197
|
-
current,
|
|
198
|
-
options ? await this.parseProperties(options) : NIL,
|
|
199
|
-
);
|
|
200
|
-
}
|
|
201
|
-
|
|
202
|
-
private async parseAggregateError(
|
|
203
|
-
id: number,
|
|
204
|
-
current: AggregateError,
|
|
205
|
-
): Promise<SerovalAggregateErrorNode> {
|
|
206
|
-
const options = getErrorOptions(current, this.features);
|
|
207
|
-
return createAggregateErrorNode(
|
|
208
|
-
id,
|
|
209
|
-
current,
|
|
210
|
-
options ? await this.parseProperties(options) : NIL,
|
|
211
|
-
);
|
|
212
|
-
}
|
|
213
|
-
|
|
214
|
-
private async parseMap(
|
|
215
|
-
id: number,
|
|
216
|
-
current: Map<unknown, unknown>,
|
|
217
|
-
): Promise<SerovalMapNode> {
|
|
218
|
-
const keyNodes: SerovalNode[] = [];
|
|
219
|
-
const valueNodes: SerovalNode[] = [];
|
|
220
|
-
for (const [key, value] of current.entries()) {
|
|
221
|
-
keyNodes.push(await this.parse(key));
|
|
222
|
-
valueNodes.push(await this.parse(value));
|
|
223
|
-
}
|
|
224
|
-
return this.createMapNode(id, keyNodes, valueNodes, current.size);
|
|
225
|
-
}
|
|
226
|
-
|
|
227
|
-
private async parseSet(
|
|
228
|
-
id: number,
|
|
229
|
-
current: Set<unknown>,
|
|
230
|
-
): Promise<SerovalSetNode> {
|
|
231
|
-
const items: SerovalNode[] = [];
|
|
232
|
-
for (const item of current.keys()) {
|
|
233
|
-
items.push(await this.parse(item));
|
|
234
|
-
}
|
|
235
|
-
return createSetNode(id, current.size, items);
|
|
236
|
-
}
|
|
237
|
-
|
|
238
|
-
private async parsePromise(
|
|
239
|
-
id: number,
|
|
240
|
-
current: Promise<unknown>,
|
|
241
|
-
): Promise<SerovalPromiseNode> {
|
|
242
|
-
const [status, result] = await promiseToResult(current);
|
|
243
|
-
|
|
244
|
-
return createSerovalNode(
|
|
245
|
-
SerovalNodeType.Promise,
|
|
246
|
-
id,
|
|
247
|
-
status,
|
|
248
|
-
NIL,
|
|
249
|
-
NIL,
|
|
250
|
-
NIL,
|
|
251
|
-
NIL,
|
|
252
|
-
NIL,
|
|
253
|
-
NIL,
|
|
254
|
-
await this.parse(result),
|
|
255
|
-
NIL,
|
|
256
|
-
NIL,
|
|
257
|
-
);
|
|
258
|
-
}
|
|
259
|
-
|
|
260
|
-
private async parsePlugin(
|
|
261
|
-
id: number,
|
|
262
|
-
current: unknown,
|
|
263
|
-
): Promise<SerovalPluginNode | undefined> {
|
|
264
|
-
const currentPlugins = this.plugins;
|
|
265
|
-
if (currentPlugins) {
|
|
266
|
-
for (let i = 0, len = currentPlugins.length; i < len; i++) {
|
|
267
|
-
const plugin = currentPlugins[i];
|
|
268
|
-
if (plugin.parse.async && plugin.test(current)) {
|
|
269
|
-
return createPluginNode(
|
|
270
|
-
id,
|
|
271
|
-
plugin.tag,
|
|
272
|
-
await plugin.parse.async(current, this, {
|
|
273
|
-
id,
|
|
274
|
-
}),
|
|
275
|
-
);
|
|
276
|
-
}
|
|
277
|
-
}
|
|
278
|
-
}
|
|
279
|
-
return NIL;
|
|
280
|
-
}
|
|
281
|
-
|
|
282
|
-
private async parseStream(
|
|
283
|
-
id: number,
|
|
284
|
-
current: Stream<unknown>,
|
|
285
|
-
): Promise<SerovalStreamConstructorNode> {
|
|
286
|
-
return createStreamConstructorNode(
|
|
287
|
-
id,
|
|
288
|
-
this.parseSpecialReference(SpecialReference.StreamConstructor),
|
|
289
|
-
await new Promise<SerovalNode[]>((resolve, reject) => {
|
|
290
|
-
const sequence: SerovalNode[] = [];
|
|
291
|
-
const cleanup = current.on({
|
|
292
|
-
next: value => {
|
|
293
|
-
this.markRef(id);
|
|
294
|
-
this.parse(value).then(
|
|
295
|
-
data => {
|
|
296
|
-
sequence.push(createStreamNextNode(id, data));
|
|
297
|
-
},
|
|
298
|
-
data => {
|
|
299
|
-
reject(data);
|
|
300
|
-
cleanup();
|
|
301
|
-
},
|
|
302
|
-
);
|
|
303
|
-
},
|
|
304
|
-
throw: value => {
|
|
305
|
-
this.markRef(id);
|
|
306
|
-
this.parse(value).then(
|
|
307
|
-
data => {
|
|
308
|
-
sequence.push(createStreamThrowNode(id, data));
|
|
309
|
-
resolve(sequence);
|
|
310
|
-
cleanup();
|
|
311
|
-
},
|
|
312
|
-
data => {
|
|
313
|
-
reject(data);
|
|
314
|
-
cleanup();
|
|
315
|
-
},
|
|
316
|
-
);
|
|
317
|
-
},
|
|
318
|
-
return: value => {
|
|
319
|
-
this.markRef(id);
|
|
320
|
-
this.parse(value).then(
|
|
321
|
-
data => {
|
|
322
|
-
sequence.push(createStreamReturnNode(id, data));
|
|
323
|
-
resolve(sequence);
|
|
324
|
-
cleanup();
|
|
325
|
-
},
|
|
326
|
-
data => {
|
|
327
|
-
reject(data);
|
|
328
|
-
cleanup();
|
|
329
|
-
},
|
|
330
|
-
);
|
|
331
|
-
},
|
|
332
|
-
});
|
|
333
|
-
}),
|
|
334
|
-
);
|
|
335
|
-
}
|
|
336
|
-
|
|
337
|
-
// biome-ignore lint/complexity/noExcessiveCognitiveComplexity: ehh
|
|
338
|
-
private async parseObject(id: number, current: object): Promise<SerovalNode> {
|
|
339
|
-
if (Array.isArray(current)) {
|
|
340
|
-
return this.parseArray(id, current);
|
|
341
|
-
}
|
|
342
|
-
if (isStream(current)) {
|
|
343
|
-
return this.parseStream(id, current);
|
|
344
|
-
}
|
|
345
|
-
const currentClass = current.constructor;
|
|
346
|
-
if (currentClass === OpaqueReference) {
|
|
347
|
-
return this.parse(
|
|
348
|
-
(current as OpaqueReference<unknown, unknown>).replacement,
|
|
349
|
-
);
|
|
350
|
-
}
|
|
351
|
-
const parsed = await this.parsePlugin(id, current);
|
|
352
|
-
if (parsed) {
|
|
353
|
-
return parsed;
|
|
354
|
-
}
|
|
355
|
-
switch (currentClass) {
|
|
356
|
-
case Object:
|
|
357
|
-
return this.parsePlainObject(
|
|
358
|
-
id,
|
|
359
|
-
current as Record<string, unknown>,
|
|
360
|
-
false,
|
|
361
|
-
);
|
|
362
|
-
case NIL:
|
|
363
|
-
return this.parsePlainObject(
|
|
364
|
-
id,
|
|
365
|
-
current as Record<string, unknown>,
|
|
366
|
-
true,
|
|
367
|
-
);
|
|
368
|
-
case Date:
|
|
369
|
-
return createDateNode(id, current as unknown as Date);
|
|
370
|
-
case RegExp:
|
|
371
|
-
return createRegExpNode(id, current as unknown as RegExp);
|
|
372
|
-
case Error:
|
|
373
|
-
case EvalError:
|
|
374
|
-
case RangeError:
|
|
375
|
-
case ReferenceError:
|
|
376
|
-
case SyntaxError:
|
|
377
|
-
case TypeError:
|
|
378
|
-
case URIError:
|
|
379
|
-
return this.parseError(id, current as unknown as Error);
|
|
380
|
-
case Number:
|
|
381
|
-
case Boolean:
|
|
382
|
-
case String:
|
|
383
|
-
case BigInt:
|
|
384
|
-
return this.parseBoxed(id, current);
|
|
385
|
-
case ArrayBuffer:
|
|
386
|
-
return createArrayBufferNode(id, current as unknown as ArrayBuffer);
|
|
387
|
-
case Int8Array:
|
|
388
|
-
case Int16Array:
|
|
389
|
-
case Int32Array:
|
|
390
|
-
case Uint8Array:
|
|
391
|
-
case Uint16Array:
|
|
392
|
-
case Uint32Array:
|
|
393
|
-
case Uint8ClampedArray:
|
|
394
|
-
case Float32Array:
|
|
395
|
-
case Float64Array:
|
|
396
|
-
return this.parseTypedArray(id, current as unknown as TypedArrayValue);
|
|
397
|
-
case DataView:
|
|
398
|
-
return this.parseDataView(id, current as unknown as DataView);
|
|
399
|
-
case Map:
|
|
400
|
-
return this.parseMap(id, current as unknown as Map<unknown, unknown>);
|
|
401
|
-
case Set:
|
|
402
|
-
return this.parseSet(id, current as unknown as Set<unknown>);
|
|
403
|
-
default:
|
|
404
|
-
break;
|
|
405
|
-
}
|
|
406
|
-
// Promises
|
|
407
|
-
if (currentClass === Promise || current instanceof Promise) {
|
|
408
|
-
return this.parsePromise(id, current as unknown as Promise<unknown>);
|
|
409
|
-
}
|
|
410
|
-
const currentFeatures = this.features;
|
|
411
|
-
// BigInt Typed Arrays
|
|
412
|
-
if (currentFeatures & Feature.BigIntTypedArray) {
|
|
413
|
-
switch (currentClass) {
|
|
414
|
-
case BigInt64Array:
|
|
415
|
-
case BigUint64Array:
|
|
416
|
-
return this.parseBigIntTypedArray(
|
|
417
|
-
id,
|
|
418
|
-
current as unknown as BigIntTypedArrayValue,
|
|
419
|
-
);
|
|
420
|
-
default:
|
|
421
|
-
break;
|
|
422
|
-
}
|
|
423
|
-
}
|
|
424
|
-
if (
|
|
425
|
-
currentFeatures & Feature.AggregateError &&
|
|
426
|
-
typeof AggregateError !== 'undefined' &&
|
|
427
|
-
(currentClass === AggregateError || current instanceof AggregateError)
|
|
428
|
-
) {
|
|
429
|
-
return this.parseAggregateError(id, current as unknown as AggregateError);
|
|
430
|
-
}
|
|
431
|
-
// Slow path. We only need to handle Errors and Iterators
|
|
432
|
-
// since they have very broad implementations.
|
|
433
|
-
if (current instanceof Error) {
|
|
434
|
-
return this.parseError(id, current);
|
|
435
|
-
}
|
|
436
|
-
// Generator functions don't have a global constructor
|
|
437
|
-
// despite existing
|
|
438
|
-
if (Symbol.iterator in current || Symbol.asyncIterator in current) {
|
|
439
|
-
return this.parsePlainObject(id, current, !!currentClass);
|
|
440
|
-
}
|
|
441
|
-
throw new SerovalUnsupportedTypeError(current);
|
|
442
|
-
}
|
|
443
|
-
|
|
444
|
-
protected async parseFunction(current: unknown): Promise<SerovalNode> {
|
|
445
|
-
const ref = this.getReference(current);
|
|
446
|
-
if (ref.type !== ParserNodeType.Fresh) {
|
|
447
|
-
return ref.value;
|
|
448
|
-
}
|
|
449
|
-
const plugin = await this.parsePlugin(ref.value, current);
|
|
450
|
-
if (plugin) {
|
|
451
|
-
return plugin;
|
|
452
|
-
}
|
|
453
|
-
throw new SerovalUnsupportedTypeError(current);
|
|
454
|
-
}
|
|
455
|
-
|
|
456
|
-
async parse<T>(current: T): Promise<SerovalNode> {
|
|
457
|
-
switch (typeof current) {
|
|
458
|
-
case 'boolean':
|
|
459
|
-
return current ? TRUE_NODE : FALSE_NODE;
|
|
460
|
-
case 'undefined':
|
|
461
|
-
return UNDEFINED_NODE;
|
|
462
|
-
case 'string':
|
|
463
|
-
return createStringNode(current as string);
|
|
464
|
-
case 'number':
|
|
465
|
-
return createNumberNode(current as number);
|
|
466
|
-
case 'bigint':
|
|
467
|
-
return createBigIntNode(current as bigint);
|
|
468
|
-
case 'object': {
|
|
469
|
-
if (current) {
|
|
470
|
-
const ref = this.getReference(current);
|
|
471
|
-
return ref.type === 0
|
|
472
|
-
? await this.parseObject(ref.value, current as object)
|
|
473
|
-
: ref.value;
|
|
474
|
-
}
|
|
475
|
-
return NULL_NODE;
|
|
476
|
-
}
|
|
477
|
-
case 'symbol':
|
|
478
|
-
return this.parseWellKnownSymbol(current);
|
|
479
|
-
case 'function':
|
|
480
|
-
return this.parseFunction(current);
|
|
481
|
-
default:
|
|
482
|
-
throw new SerovalUnsupportedTypeError(current);
|
|
483
|
-
}
|
|
484
|
-
}
|
|
485
|
-
|
|
486
|
-
async parseTop<T>(current: T): Promise<SerovalNode> {
|
|
487
|
-
try {
|
|
488
|
-
return await this.parse(current);
|
|
489
|
-
} catch (error) {
|
|
490
|
-
throw error instanceof SerovalParserError
|
|
491
|
-
? error
|
|
492
|
-
: new SerovalParserError(error);
|
|
493
|
-
}
|
|
494
|
-
}
|
|
495
|
-
}
|