json-as 1.2.6 → 1.3.1
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +417 -0
- package/README.md +135 -36
- package/assembly/custom/util.ts +24 -70
- package/assembly/deserialize/float.ts +181 -0
- package/assembly/deserialize/helpers/uint.ts +12 -0
- package/assembly/deserialize/index/arbitrary.ts +25 -0
- package/assembly/deserialize/index/array.ts +61 -0
- package/assembly/deserialize/index/bool.ts +1 -0
- package/assembly/deserialize/index/date.ts +1 -0
- package/assembly/deserialize/index/float.ts +1 -0
- package/assembly/deserialize/index/integer.ts +1 -0
- package/assembly/deserialize/index/map.ts +1 -0
- package/assembly/deserialize/index/object.ts +1 -0
- package/assembly/deserialize/index/raw.ts +1 -0
- package/assembly/deserialize/index/set.ts +1 -0
- package/assembly/deserialize/index/staticarray.ts +1 -0
- package/assembly/deserialize/index/string.ts +15 -0
- package/assembly/deserialize/index/struct.ts +1 -0
- package/assembly/deserialize/index/typedarray.ts +15 -0
- package/assembly/deserialize/index/unsigned.ts +1 -0
- package/assembly/deserialize/index.ts +14 -0
- package/assembly/deserialize/integer.ts +42 -0
- package/assembly/deserialize/simd/array/integer.ts +307 -0
- package/assembly/deserialize/simd/string.ts +130 -11
- package/assembly/deserialize/simple/arbitrary.ts +5 -12
- package/assembly/deserialize/simple/array/arbitrary.ts +12 -36
- package/assembly/deserialize/simple/array/array.ts +2 -8
- package/assembly/deserialize/simple/array/bool.ts +2 -8
- package/assembly/deserialize/simple/array/box.ts +2 -8
- package/assembly/deserialize/simple/array/float.ts +2 -8
- package/assembly/deserialize/simple/array/integer.ts +2 -8
- package/assembly/deserialize/simple/array/map.ts +6 -26
- package/assembly/deserialize/simple/array/object.ts +6 -26
- package/assembly/deserialize/simple/array/raw.ts +18 -61
- package/assembly/deserialize/simple/array/string.ts +5 -10
- package/assembly/deserialize/simple/array/struct.ts +6 -26
- package/assembly/deserialize/simple/array.ts +2 -5
- package/assembly/deserialize/simple/bool.ts +2 -6
- package/assembly/deserialize/simple/map.ts +29 -102
- package/assembly/deserialize/simple/object.ts +24 -81
- package/assembly/deserialize/simple/raw.ts +1 -4
- package/assembly/deserialize/simple/set.ts +11 -37
- package/assembly/deserialize/simple/staticarray/array.ts +1 -1
- package/assembly/deserialize/simple/staticarray/bool.ts +1 -1
- package/assembly/deserialize/simple/staticarray/float.ts +1 -1
- package/assembly/deserialize/simple/staticarray/integer.ts +1 -1
- package/assembly/deserialize/simple/staticarray/string.ts +7 -14
- package/assembly/deserialize/simple/staticarray/struct.ts +1 -1
- package/assembly/deserialize/simple/staticarray.ts +57 -21
- package/assembly/deserialize/simple/string.ts +90 -10
- package/assembly/deserialize/simple/struct.ts +25 -121
- package/assembly/deserialize/simple/typedarray.ts +94 -0
- package/assembly/deserialize/swar/array/arbitrary.ts +8 -0
- package/assembly/deserialize/swar/array/array.ts +39 -0
- package/assembly/deserialize/swar/array/bool.ts +47 -0
- package/assembly/deserialize/swar/array/box.ts +8 -0
- package/assembly/deserialize/swar/array/float.ts +39 -0
- package/assembly/deserialize/swar/array/integer.ts +461 -0
- package/assembly/deserialize/swar/array/map.ts +7 -0
- package/assembly/deserialize/swar/array/object.ts +44 -0
- package/assembly/deserialize/swar/array/raw.ts +8 -0
- package/assembly/deserialize/swar/array/shared.ts +96 -0
- package/assembly/deserialize/swar/array/string.ts +39 -0
- package/assembly/deserialize/swar/array/struct.ts +44 -0
- package/assembly/deserialize/swar/array.ts +49 -0
- package/assembly/deserialize/swar/string.ts +648 -15
- package/assembly/deserialize/unsigned.ts +75 -0
- package/assembly/index.d.ts +1 -3
- package/assembly/index.ts +316 -374
- package/assembly/serialize/index/arbitrary.ts +75 -0
- package/assembly/serialize/index/array.ts +1 -0
- package/assembly/serialize/index/bool.ts +1 -0
- package/assembly/serialize/index/date.ts +1 -0
- package/assembly/serialize/index/float.ts +1 -0
- package/assembly/serialize/index/integer.ts +1 -0
- package/assembly/serialize/index/map.ts +1 -0
- package/assembly/serialize/index/object.ts +46 -0
- package/assembly/serialize/index/raw.ts +1 -0
- package/assembly/serialize/index/set.ts +1 -0
- package/assembly/serialize/index/staticarray.ts +1 -0
- package/assembly/serialize/index/string.ts +15 -0
- package/assembly/serialize/index/struct.ts +1 -0
- package/assembly/serialize/index/typedarray.ts +66 -0
- package/assembly/serialize/index.ts +13 -0
- package/assembly/serialize/simd/string.ts +4 -13
- package/assembly/serialize/simple/arbitrary.ts +6 -0
- package/assembly/serialize/simple/raw.ts +1 -5
- package/assembly/serialize/simple/string.ts +3 -11
- package/assembly/serialize/simple/typedarray.ts +63 -0
- package/assembly/serialize/swar/string.ts +6 -21
- package/assembly/util/concat.ts +1 -5
- package/assembly/util/index.ts +1 -0
- package/assembly/util/masks.ts +12 -18
- package/assembly/util/memory.ts +0 -0
- package/assembly/util/snp.ts +1 -4
- package/assembly/util/stringScan.ts +24 -0
- package/assembly/util/swar.ts +50 -6
- package/lib/as-bs.ts +137 -127
- package/package.json +26 -5
- package/transform/lib/builder.d.ts.map +1 -1
- package/transform/lib/builder.js +5 -13
- package/transform/lib/builder.js.map +1 -1
- package/transform/lib/index.d.ts +1 -0
- package/transform/lib/index.d.ts.map +1 -1
- package/transform/lib/index.js +672 -757
- package/transform/lib/index.js.map +1 -1
- package/transform/lib/linkers/alias.d.ts.map +1 -1
- package/transform/lib/linkers/alias.js.map +1 -1
- package/transform/lib/linkers/custom.d.ts.map +1 -1
- package/transform/lib/linkers/custom.js +8 -9
- package/transform/lib/linkers/custom.js.map +1 -1
- package/transform/lib/linkers/imports.d.ts.map +1 -1
- package/transform/lib/linkers/imports.js.map +1 -1
- package/transform/lib/types.d.ts +6 -0
- package/transform/lib/types.d.ts.map +1 -1
- package/transform/lib/types.js +83 -21
- package/transform/lib/types.js.map +1 -1
- package/transform/lib/util.d.ts.map +1 -1
- package/transform/lib/util.js +1 -1
- package/transform/lib/util.js.map +1 -1
- package/transform/lib/visitor.d.ts.map +1 -1
- package/transform/lib/visitor.js +1 -2
- package/transform/lib/visitor.js.map +1 -1
- package/.prettierrc +0 -3
- package/ARCHITECTURE.md +0 -320
- package/CONTRIBUTING.md +0 -238
- package/TODO +0 -1
- package/assembly/deserialize/simple/float.ts +0 -11
- package/assembly/deserialize/simple/integer.ts +0 -9
- package/assembly/test.ts +0 -30
- package/eslint.config.js +0 -60
- package/lib/tsconfig.json +0 -8
- package/tools/assemblyscript-eslint-local.js +0 -29
- package/tools/assemblyscript-eslint.js +0 -29
- package/transform/tsconfig.json +0 -35
package/assembly/index.ts
CHANGED
|
@@ -1,46 +1,40 @@
|
|
|
1
1
|
/// <reference path="./index.d.ts" />
|
|
2
2
|
|
|
3
3
|
import { bs } from "../lib/as-bs";
|
|
4
|
-
import {
|
|
5
|
-
import {
|
|
6
|
-
import {
|
|
7
|
-
import {
|
|
8
|
-
import {
|
|
9
|
-
import {
|
|
10
|
-
import {
|
|
11
|
-
import {
|
|
12
|
-
import {
|
|
13
|
-
import {
|
|
14
|
-
import {
|
|
15
|
-
import {
|
|
16
|
-
import {
|
|
17
|
-
import {
|
|
4
|
+
import { OBJECT, TOTAL_OVERHEAD } from "rt/common";
|
|
5
|
+
import { serializeArray } from "./serialize/index/array";
|
|
6
|
+
import { serializeMap } from "./serialize/index/map";
|
|
7
|
+
import { serializeDate } from "./serialize/index/date";
|
|
8
|
+
import { deserializeBoolean } from "./deserialize/index/bool";
|
|
9
|
+
import { deserializeArray } from "./deserialize/index/array";
|
|
10
|
+
import { deserializeFloat } from "./deserialize/index/float";
|
|
11
|
+
import { deserializeMap } from "./deserialize/index/map";
|
|
12
|
+
import { deserializeDate } from "./deserialize/index/date";
|
|
13
|
+
import { deserializeInteger } from "./deserialize/index/integer";
|
|
14
|
+
import { deserializeUnsigned } from "./deserialize/index/unsigned";
|
|
15
|
+
import { serializeArbitrary } from "./serialize/index/arbitrary";
|
|
16
|
+
import { serializeSet } from "./serialize/index/set";
|
|
17
|
+
import { deserializeSet } from "./deserialize/index/set";
|
|
18
|
+
import { serializeStaticArray } from "./serialize/index/staticarray";
|
|
19
|
+
import { deserializeStaticArray } from "./deserialize/index/staticarray";
|
|
18
20
|
|
|
19
|
-
import {
|
|
20
|
-
NULL_WORD,
|
|
21
|
-
QUOTE,
|
|
22
|
-
NULL_WORD_U64,
|
|
23
|
-
TRUE_WORD_U64,
|
|
24
|
-
FALSE_WORD_U64,
|
|
25
|
-
} from "./custom/chars";
|
|
21
|
+
import { NULL_WORD, QUOTE, NULL_WORD_U64, TRUE_WORD_U64, FALSE_WORD_U64 } from "./custom/chars";
|
|
26
22
|
import { dtoa_buffered, itoa_buffered } from "util/number";
|
|
27
|
-
import { serializeBool } from "./serialize/
|
|
28
|
-
import { serializeInteger } from "./serialize/
|
|
29
|
-
import { serializeFloat } from "./serialize/
|
|
30
|
-
import { serializeStruct } from "./serialize/
|
|
23
|
+
import { serializeBool } from "./serialize/index/bool";
|
|
24
|
+
import { serializeInteger } from "./serialize/index/integer";
|
|
25
|
+
import { serializeFloat } from "./serialize/index/float";
|
|
26
|
+
import { serializeStruct } from "./serialize/index/struct";
|
|
31
27
|
import { ptrToStr } from "./util/ptrToStr";
|
|
32
28
|
import { atoi, bytes } from "./util";
|
|
33
|
-
import { deserializeArbitrary } from "./deserialize/
|
|
34
|
-
import { serializeObject } from "./serialize/
|
|
35
|
-
import { deserializeObject } from "./deserialize/
|
|
36
|
-
import { serializeRaw } from "./serialize/
|
|
37
|
-
import { deserializeRaw } from "./deserialize/
|
|
38
|
-
import {
|
|
39
|
-
import {
|
|
40
|
-
import {
|
|
41
|
-
import {
|
|
42
|
-
import { serializeString } from "./serialize/simple/string";
|
|
43
|
-
import { deserializeString_SIMD } from "./deserialize/simd/string";
|
|
29
|
+
import { deserializeArbitrary } from "./deserialize/index/arbitrary";
|
|
30
|
+
import { serializeObject } from "./serialize/index/object";
|
|
31
|
+
import { deserializeObject } from "./deserialize/index/object";
|
|
32
|
+
import { serializeRaw } from "./serialize/index/raw";
|
|
33
|
+
import { deserializeRaw } from "./deserialize/index/raw";
|
|
34
|
+
import { deserializeString } from "./deserialize/index/string";
|
|
35
|
+
import { serializeString } from "./serialize/index/string";
|
|
36
|
+
import { deserializeArrayBuffer, deserializeTypedArray } from "./deserialize/index/typedarray";
|
|
37
|
+
import { serializeArrayBufferUnsafe, serializeDynamic, serializeTypedArray } from "./serialize/index/typedarray";
|
|
44
38
|
|
|
45
39
|
/**
|
|
46
40
|
* Offset of the 'storage' property in the JSON.Value class.
|
|
@@ -65,7 +59,7 @@ export namespace JSON {
|
|
|
65
59
|
* ```
|
|
66
60
|
*/
|
|
67
61
|
export function shrink(): void {
|
|
68
|
-
bs.
|
|
62
|
+
bs.shrink();
|
|
69
63
|
}
|
|
70
64
|
}
|
|
71
65
|
/**
|
|
@@ -77,10 +71,7 @@ export namespace JSON {
|
|
|
77
71
|
* @returns string
|
|
78
72
|
*/
|
|
79
73
|
// @ts-expect-error: inline
|
|
80
|
-
@inline export function stringify<T>(
|
|
81
|
-
data: T,
|
|
82
|
-
out: string | null = null,
|
|
83
|
-
): string {
|
|
74
|
+
@inline export function stringify<T>(data: T, out: string | null = null): string {
|
|
84
75
|
if (isBoolean<T>()) {
|
|
85
76
|
if (out) {
|
|
86
77
|
if (<bool>data == true) {
|
|
@@ -94,12 +85,7 @@ export namespace JSON {
|
|
|
94
85
|
return out;
|
|
95
86
|
}
|
|
96
87
|
return data ? "true" : "false";
|
|
97
|
-
} else if (
|
|
98
|
-
isInteger<T>() &&
|
|
99
|
-
!isSigned<T>() &&
|
|
100
|
-
nameof<T>() == "usize" &&
|
|
101
|
-
data == 0
|
|
102
|
-
) {
|
|
88
|
+
} else if (isInteger<T>() && !isSigned<T>() && nameof<T>() == "usize" && data == 0) {
|
|
103
89
|
if (out) {
|
|
104
90
|
out = changetype<string>(__renew(changetype<usize>(out), 8));
|
|
105
91
|
store<u64>(changetype<usize>(out), NULL_WORD_U64);
|
|
@@ -108,14 +94,10 @@ export namespace JSON {
|
|
|
108
94
|
return NULL_WORD;
|
|
109
95
|
} else if (isInteger<T>(data)) {
|
|
110
96
|
if (out) {
|
|
111
|
-
out = changetype<string>(
|
|
112
|
-
__renew(changetype<usize>(out), sizeof<T>() << 3),
|
|
113
|
-
);
|
|
97
|
+
out = changetype<string>(__renew(changetype<usize>(out), sizeof<T>() << 3));
|
|
114
98
|
|
|
115
99
|
const bytes = itoa_buffered(changetype<usize>(out), data) << 1;
|
|
116
|
-
return (out = changetype<string>(
|
|
117
|
-
__renew(changetype<usize>(out), bytes),
|
|
118
|
-
));
|
|
100
|
+
return (out = changetype<string>(__renew(changetype<usize>(out), bytes)));
|
|
119
101
|
}
|
|
120
102
|
return data.toString();
|
|
121
103
|
} else if (isFloat<T>(data)) {
|
|
@@ -123,9 +105,7 @@ export namespace JSON {
|
|
|
123
105
|
out = changetype<string>(__renew(changetype<usize>(out), 64));
|
|
124
106
|
|
|
125
107
|
const bytes = dtoa_buffered(changetype<usize>(out), data) << 1;
|
|
126
|
-
return (out = changetype<string>(
|
|
127
|
-
__renew(changetype<usize>(out), bytes),
|
|
128
|
-
));
|
|
108
|
+
return (out = changetype<string>(__renew(changetype<usize>(out), bytes)));
|
|
129
109
|
}
|
|
130
110
|
return data.toString();
|
|
131
111
|
} else if (isNullable<T>() && changetype<usize>(data) == <usize>0) {
|
|
@@ -136,30 +116,23 @@ export namespace JSON {
|
|
|
136
116
|
}
|
|
137
117
|
return NULL_WORD;
|
|
138
118
|
} else if (isString<nonnull<T>>()) {
|
|
139
|
-
|
|
140
|
-
|
|
141
|
-
|
|
142
|
-
|
|
143
|
-
|
|
144
|
-
|
|
145
|
-
}
|
|
119
|
+
serializeString(data as string);
|
|
120
|
+
return bs.out<string>();
|
|
121
|
+
// @ts-expect-error: Defined by transform
|
|
122
|
+
} else if (isDefined(data.__SERIALIZE_CUSTOM)) {
|
|
123
|
+
// @ts-expect-error: Defined by transform
|
|
124
|
+
data.__SERIALIZE_CUSTOM();
|
|
146
125
|
return bs.out<string>();
|
|
147
|
-
// @ts-expect-error:
|
|
126
|
+
// @ts-expect-error: Defined by transform
|
|
148
127
|
} else if (isDefined(data.__SERIALIZE)) {
|
|
149
|
-
// @ts-expect-error
|
|
128
|
+
// @ts-expect-error: Defined by transform
|
|
150
129
|
inline.always(data.__SERIALIZE(changetype<usize>(data)));
|
|
151
130
|
return bs.out<string>();
|
|
152
131
|
} else if (data instanceof Date) {
|
|
153
|
-
out = out
|
|
154
|
-
? changetype<string>(__renew(changetype<usize>(out), 52))
|
|
155
|
-
: changetype<string>(__new(52, idof<string>()));
|
|
132
|
+
out = out ? changetype<string>(__renew(changetype<usize>(out), 52)) : changetype<string>(__new(52, idof<string>()));
|
|
156
133
|
|
|
157
134
|
store<u16>(changetype<usize>(out), QUOTE);
|
|
158
|
-
memory.copy(
|
|
159
|
-
changetype<usize>(out) + 2,
|
|
160
|
-
changetype<usize>(data.toISOString()),
|
|
161
|
-
48,
|
|
162
|
-
);
|
|
135
|
+
memory.copy(changetype<usize>(out) + 2, changetype<usize>(data.toISOString()), 48);
|
|
163
136
|
store<u16>(changetype<usize>(out), QUOTE, 50);
|
|
164
137
|
return changetype<string>(out);
|
|
165
138
|
} else if (data instanceof Array) {
|
|
@@ -170,6 +143,43 @@ export namespace JSON {
|
|
|
170
143
|
// @ts-expect-error
|
|
171
144
|
inline.always(serializeStaticArray(changetype<nonnull<T>>(data)));
|
|
172
145
|
return bs.out<string>();
|
|
146
|
+
} else if (data instanceof Int8Array) {
|
|
147
|
+
inline.always(serializeTypedArray<Int8Array>(data));
|
|
148
|
+
return bs.out<string>();
|
|
149
|
+
} else if (data instanceof Uint8Array) {
|
|
150
|
+
inline.always(serializeTypedArray<Uint8Array>(data));
|
|
151
|
+
return bs.out<string>();
|
|
152
|
+
} else if (data instanceof Uint8ClampedArray) {
|
|
153
|
+
inline.always(serializeTypedArray<Uint8ClampedArray>(data));
|
|
154
|
+
return bs.out<string>();
|
|
155
|
+
} else if (data instanceof Int16Array) {
|
|
156
|
+
inline.always(serializeTypedArray<Int16Array>(data));
|
|
157
|
+
return bs.out<string>();
|
|
158
|
+
} else if (data instanceof Uint16Array) {
|
|
159
|
+
inline.always(serializeTypedArray<Uint16Array>(data));
|
|
160
|
+
return bs.out<string>();
|
|
161
|
+
} else if (data instanceof Int32Array) {
|
|
162
|
+
inline.always(serializeTypedArray<Int32Array>(data));
|
|
163
|
+
return bs.out<string>();
|
|
164
|
+
} else if (data instanceof Uint32Array) {
|
|
165
|
+
inline.always(serializeTypedArray<Uint32Array>(data));
|
|
166
|
+
return bs.out<string>();
|
|
167
|
+
} else if (data instanceof Int64Array) {
|
|
168
|
+
inline.always(serializeTypedArray<Int64Array>(data));
|
|
169
|
+
return bs.out<string>();
|
|
170
|
+
} else if (data instanceof Uint64Array) {
|
|
171
|
+
inline.always(serializeTypedArray<Uint64Array>(data));
|
|
172
|
+
return bs.out<string>();
|
|
173
|
+
} else if (data instanceof Float32Array) {
|
|
174
|
+
inline.always(serializeTypedArray<Float32Array>(data));
|
|
175
|
+
return bs.out<string>();
|
|
176
|
+
} else if (data instanceof Float64Array) {
|
|
177
|
+
inline.always(serializeTypedArray<Float64Array>(data));
|
|
178
|
+
return bs.out<string>();
|
|
179
|
+
} else if (data instanceof ArrayBuffer) {
|
|
180
|
+
const dataStart = changetype<usize>(data);
|
|
181
|
+
serializeArrayBufferUnsafe(dataStart, changetype<OBJECT>(dataStart - TOTAL_OVERHEAD).rtSize);
|
|
182
|
+
return bs.out<string>();
|
|
173
183
|
} else if (data instanceof Set) {
|
|
174
184
|
// @ts-expect-error
|
|
175
185
|
inline.always(serializeSet(changetype<nonnull<T>>(data)));
|
|
@@ -190,11 +200,7 @@ export namespace JSON {
|
|
|
190
200
|
} else if (data instanceof JSON.Box) {
|
|
191
201
|
return JSON.stringify(data.value);
|
|
192
202
|
} else {
|
|
193
|
-
throw new Error(
|
|
194
|
-
`Could not serialize data of type '${nameof<T>()}'. ` +
|
|
195
|
-
`If this is a custom class, add the @json decorator: @json class ${nameof<T>()} { ... }. ` +
|
|
196
|
-
`Supported types: primitives, string, Array, Map, Date, and @json decorated classes.`,
|
|
197
|
-
);
|
|
203
|
+
throw new Error(`Could not serialize data of type '${nameof<T>()}'. ` + `If this is a custom class, add the @json decorator: @json class ${nameof<T>()} { ... }. ` + `Supported types: primitives, string, Array, StaticArray, TypedArray, ArrayBuffer, Map, Date, and @json decorated classes.`);
|
|
198
204
|
}
|
|
199
205
|
}
|
|
200
206
|
|
|
@@ -213,61 +219,65 @@ export namespace JSON {
|
|
|
213
219
|
if (isBoolean<T>()) {
|
|
214
220
|
return deserializeBoolean(dataPtr, dataPtr + dataSize) as T;
|
|
215
221
|
} else if (isInteger<T>()) {
|
|
216
|
-
return deserializeInteger<T>(dataPtr, dataPtr + dataSize);
|
|
222
|
+
return isSigned<T>() ? deserializeInteger<T>(dataPtr, dataPtr + dataSize) : deserializeUnsigned<T>(dataPtr, dataPtr + dataSize);
|
|
217
223
|
} else if (isFloat<T>()) {
|
|
218
224
|
return deserializeFloat<T>(dataPtr, dataPtr + dataSize);
|
|
219
|
-
} else if (
|
|
220
|
-
isNullable<T>() &&
|
|
221
|
-
dataSize == 8 &&
|
|
222
|
-
load<u64>(dataPtr) == NULL_WORD_U64
|
|
223
|
-
) {
|
|
225
|
+
} else if (isNullable<T>() && dataSize == 8 && load<u64>(dataPtr) == NULL_WORD_U64) {
|
|
224
226
|
return null;
|
|
225
227
|
} else if (isString<T>()) {
|
|
226
|
-
|
|
227
|
-
// @ts-expect-error: type
|
|
228
|
-
return deserializeString(dataPtr, dataPtr + dataSize);
|
|
229
|
-
} else if (JSON_MODE === JSONMode.SWAR) {
|
|
230
|
-
// @ts-expect-error: type
|
|
231
|
-
return deserializeString_SWAR(dataPtr, dataPtr + dataSize);
|
|
232
|
-
} else if (JSON_MODE === JSONMode.SIMD) {
|
|
233
|
-
// @ts-expect-error: type
|
|
234
|
-
return deserializeString_SIMD(dataPtr, dataPtr + dataSize);
|
|
235
|
-
}
|
|
228
|
+
return deserializeString(dataPtr, dataPtr + dataSize) as T;
|
|
236
229
|
} else {
|
|
237
230
|
let type: nonnull<T> = changetype<nonnull<T>>(0);
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
241
|
-
deserializeStaticArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0),
|
|
242
|
-
);
|
|
243
|
-
} else if (type instanceof Array) {
|
|
244
|
-
// @ts-expect-error
|
|
245
|
-
return inline.always(
|
|
246
|
-
deserializeArray<nonnull<T>>(
|
|
247
|
-
dataPtr,
|
|
248
|
-
dataPtr + dataSize,
|
|
249
|
-
changetype<usize>(instantiate<T>()),
|
|
250
|
-
),
|
|
251
|
-
);
|
|
252
|
-
} else if (type instanceof Set) {
|
|
231
|
+
// @ts-expect-error: Defined by transform
|
|
232
|
+
if (isDefined(type.__DESERIALIZE_CUSTOM)) {
|
|
233
|
+
const out = changetype<nonnull<T>>(0);
|
|
253
234
|
// @ts-expect-error
|
|
254
|
-
return
|
|
255
|
-
deserializeSet<nonnull<T>>(dataPtr, dataPtr + dataSize, 0),
|
|
256
|
-
);
|
|
235
|
+
return out.__DESERIALIZE_CUSTOM(data);
|
|
257
236
|
// @ts-expect-error: Defined by transform
|
|
258
237
|
} else if (isDefined(type.__DESERIALIZE)) {
|
|
259
|
-
const out = changetype<nonnull<T>>(
|
|
260
|
-
__new(offsetof<nonnull<T>>(), idof<nonnull<T>>()),
|
|
261
|
-
);
|
|
238
|
+
const out = changetype<nonnull<T>>(__new(offsetof<nonnull<T>>(), idof<nonnull<T>>()));
|
|
262
239
|
// @ts-expect-error: Defined by transform
|
|
263
240
|
if (isDefined(type.__INITIALIZE)) out.__INITIALIZE();
|
|
241
|
+
// @ts-expect-error: Defined by transform
|
|
242
|
+
out.__DESERIALIZE(dataPtr, dataPtr + dataSize, out);
|
|
243
|
+
return out;
|
|
244
|
+
}
|
|
245
|
+
if (type instanceof StaticArray) {
|
|
246
|
+
// @ts-expect-error
|
|
247
|
+
return inline.always(deserializeStaticArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0));
|
|
248
|
+
} else if (type instanceof Array) {
|
|
264
249
|
// @ts-expect-error
|
|
265
|
-
return
|
|
250
|
+
return inline.always(deserializeArray<nonnull<T>>(dataPtr, dataPtr + dataSize, changetype<usize>(instantiate<T>())));
|
|
251
|
+
} else if (type instanceof Int8Array) {
|
|
252
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
253
|
+
} else if (type instanceof Uint8Array) {
|
|
254
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
255
|
+
} else if (type instanceof Uint8ClampedArray) {
|
|
256
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
257
|
+
} else if (type instanceof Int16Array) {
|
|
258
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
259
|
+
} else if (type instanceof Uint16Array) {
|
|
260
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
261
|
+
} else if (type instanceof Int32Array) {
|
|
262
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
263
|
+
} else if (type instanceof Uint32Array) {
|
|
264
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
265
|
+
} else if (type instanceof Int64Array) {
|
|
266
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
267
|
+
} else if (type instanceof Uint64Array) {
|
|
268
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
269
|
+
} else if (type instanceof Float32Array) {
|
|
270
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
271
|
+
} else if (type instanceof Float64Array) {
|
|
272
|
+
return deserializeTypedArray<nonnull<T>>(dataPtr, dataPtr + dataSize, 0) as T;
|
|
273
|
+
} else if (type instanceof ArrayBuffer) {
|
|
274
|
+
return deserializeArrayBuffer(dataPtr, dataPtr + dataSize, 0) as T;
|
|
275
|
+
} else if (type instanceof Set) {
|
|
276
|
+
// @ts-expect-error
|
|
277
|
+
return inline.always(deserializeSet<nonnull<T>>(dataPtr, dataPtr + dataSize, 0));
|
|
266
278
|
} else if (type instanceof Map) {
|
|
267
279
|
// @ts-expect-error
|
|
268
|
-
return inline.always(
|
|
269
|
-
deserializeMap<nonnull<T>>(dataPtr, dataPtr + dataSize, 0),
|
|
270
|
-
);
|
|
280
|
+
return inline.always(deserializeMap<nonnull<T>>(dataPtr, dataPtr + dataSize, 0));
|
|
271
281
|
} else if (type instanceof Date) {
|
|
272
282
|
// @ts-expect-error
|
|
273
283
|
return deserializeDate(dataPtr, dataPtr + dataSize);
|
|
@@ -276,9 +286,7 @@ export namespace JSON {
|
|
|
276
286
|
return deserializeRaw(dataPtr, dataPtr + dataSize);
|
|
277
287
|
} else if (type instanceof JSON.Value) {
|
|
278
288
|
// @ts-expect-error
|
|
279
|
-
return inline.always(
|
|
280
|
-
deserializeArbitrary(dataPtr, dataPtr + dataSize, 0),
|
|
281
|
-
);
|
|
289
|
+
return inline.always(deserializeArbitrary(dataPtr, dataPtr + dataSize, 0));
|
|
282
290
|
} else if (type instanceof JSON.Obj) {
|
|
283
291
|
// @ts-expect-error
|
|
284
292
|
return inline.always(deserializeObject(dataPtr, dataPtr + dataSize, 0));
|
|
@@ -286,11 +294,7 @@ export namespace JSON {
|
|
|
286
294
|
// @ts-expect-error
|
|
287
295
|
return new JSON.Box(parseBox(data, changetype<nonnull<T>>(0).value));
|
|
288
296
|
} else {
|
|
289
|
-
throw new Error(
|
|
290
|
-
`Could not deserialize JSON to type '${nameof<T>()}'. ` +
|
|
291
|
-
`If this is a custom class, ensure it has the @json decorator: @json class ${nameof<T>()} { ... }. ` +
|
|
292
|
-
`Input: "${data.length > 50 ? data.slice(0, 50) + "..." : data}"`,
|
|
293
|
-
);
|
|
297
|
+
throw new Error(`Could not deserialize JSON to type '${nameof<T>()}'. ` + `If this is a custom class, ensure it has the @json decorator: @json class ${nameof<T>()} { ... }. ` + `Input: "${data.length > 50 ? data.slice(0, 50) + "..." : data}"`);
|
|
294
298
|
}
|
|
295
299
|
}
|
|
296
300
|
}
|
|
@@ -304,7 +308,7 @@ export namespace JSON {
|
|
|
304
308
|
* Enum-like namespace representing the different types supported by JSON.Value.
|
|
305
309
|
*
|
|
306
310
|
* Used internally to track the runtime type of values stored in JSON.Value instances.
|
|
307
|
-
* Types 0-
|
|
311
|
+
* Types 0-19 are reserved for built-in types; custom @json classes use idof<T>() + Struct.
|
|
308
312
|
*/
|
|
309
313
|
export namespace Types {
|
|
310
314
|
/** Represents a null value */
|
|
@@ -345,6 +349,10 @@ export namespace JSON {
|
|
|
345
349
|
@inline export const Map: u16 = 16;
|
|
346
350
|
// @ts-expect-error
|
|
347
351
|
@inline export const Struct: u16 = 17;
|
|
352
|
+
// @ts-expect-error
|
|
353
|
+
@inline export const TypedArray: u16 = 18;
|
|
354
|
+
// @ts-expect-error
|
|
355
|
+
@inline export const ArrayBuffer: u16 = 19;
|
|
348
356
|
}
|
|
349
357
|
|
|
350
358
|
/**
|
|
@@ -437,9 +445,7 @@ export namespace JSON {
|
|
|
437
445
|
* @returns An instance of JSON.Value.
|
|
438
446
|
*/
|
|
439
447
|
@inline static empty(): JSON.Value {
|
|
440
|
-
return changetype<JSON.Value>(
|
|
441
|
-
__new(offsetof<JSON.Value>(), idof<JSON.Value>()),
|
|
442
|
-
);
|
|
448
|
+
return changetype<JSON.Value>(__new(offsetof<JSON.Value>(), idof<JSON.Value>()));
|
|
443
449
|
}
|
|
444
450
|
|
|
445
451
|
/**
|
|
@@ -449,9 +455,7 @@ export namespace JSON {
|
|
|
449
455
|
*/
|
|
450
456
|
@inline static from<T>(value: T): JSON.Value {
|
|
451
457
|
if (value instanceof JSON.Value) return value;
|
|
452
|
-
const out = changetype<JSON.Value>(
|
|
453
|
-
__new(offsetof<JSON.Value>(), idof<JSON.Value>()),
|
|
454
|
-
);
|
|
458
|
+
const out = changetype<JSON.Value>(__new(offsetof<JSON.Value>(), idof<JSON.Value>()));
|
|
455
459
|
out.set<T>(value);
|
|
456
460
|
return out;
|
|
457
461
|
}
|
|
@@ -462,38 +466,40 @@ export namespace JSON {
|
|
|
462
466
|
* @returns JSON.Types
|
|
463
467
|
*/
|
|
464
468
|
@inline getType<T>(value: T): JSON.Types {
|
|
465
|
-
if (isNullable<T>() && changetype<usize>(value) === 0)
|
|
466
|
-
return JSON.Types.Null;
|
|
469
|
+
if (isNullable<T>() && changetype<usize>(value) === 0) return JSON.Types.Null;
|
|
467
470
|
if (isBoolean<T>()) return JSON.Types.Bool;
|
|
468
|
-
if (
|
|
469
|
-
isInteger<T>() &&
|
|
470
|
-
!isSigned<T>() &&
|
|
471
|
-
changetype<usize>(value) == 0 &&
|
|
472
|
-
nameof<T>() == "usize"
|
|
473
|
-
)
|
|
474
|
-
return JSON.Types.Null;
|
|
471
|
+
if (isInteger<T>() && !isSigned<T>() && changetype<usize>(value) == 0 && nameof<T>() == "usize") return JSON.Types.Null;
|
|
475
472
|
if (isString<T>()) return JSON.Types.String;
|
|
476
473
|
// @ts-expect-error: can assume that T is ArrayLike based on previous condition
|
|
477
|
-
if (isArray<T>() && idof<valueof<T>>() == idof<JSON.Value>())
|
|
478
|
-
return JSON.Types.Array;
|
|
474
|
+
if (isArray<T>() && idof<valueof<T>>() == idof<JSON.Value>()) return JSON.Types.Array;
|
|
479
475
|
if (value instanceof JSON.Box) return this.getType(value.value);
|
|
480
|
-
if (value instanceof u8 || value instanceof i8) return JSON.Types.U8;
|
|
481
|
-
if (value instanceof u16 || value instanceof i16) return JSON.Types.U16;
|
|
482
|
-
if (value instanceof u32 || value instanceof i32) return JSON.Types.U32;
|
|
483
|
-
if (value instanceof u64 || value instanceof i64) return JSON.Types.U64;
|
|
484
476
|
if (value instanceof i8) return JSON.Types.I8;
|
|
485
477
|
if (value instanceof i16) return JSON.Types.I16;
|
|
486
478
|
if (value instanceof i32) return JSON.Types.I32;
|
|
487
479
|
if (value instanceof i64) return JSON.Types.I64;
|
|
480
|
+
if (value instanceof u8) return JSON.Types.U8;
|
|
481
|
+
if (value instanceof u16) return JSON.Types.U16;
|
|
482
|
+
if (value instanceof u32) return JSON.Types.U32;
|
|
483
|
+
if (value instanceof u64) return JSON.Types.U64;
|
|
488
484
|
if (value instanceof f32) return JSON.Types.F32;
|
|
489
485
|
if (value instanceof f64) return JSON.Types.F64;
|
|
486
|
+
// @ts-expect-error: supplied by transform
|
|
487
|
+
if (isDefined(value.__SERIALIZE) && isManaged<T>(value)) return u16(idof<T>()) + JSON.Types.Struct;
|
|
488
|
+
if (value instanceof Int8Array) return JSON.Types.TypedArray;
|
|
489
|
+
if (value instanceof Uint8Array) return JSON.Types.TypedArray;
|
|
490
|
+
if (value instanceof Uint8ClampedArray) return JSON.Types.TypedArray;
|
|
491
|
+
if (value instanceof Int16Array) return JSON.Types.TypedArray;
|
|
492
|
+
if (value instanceof Uint16Array) return JSON.Types.TypedArray;
|
|
493
|
+
if (value instanceof Int32Array) return JSON.Types.TypedArray;
|
|
494
|
+
if (value instanceof Uint32Array) return JSON.Types.TypedArray;
|
|
495
|
+
if (value instanceof Int64Array) return JSON.Types.TypedArray;
|
|
496
|
+
if (value instanceof Uint64Array) return JSON.Types.TypedArray;
|
|
497
|
+
if (value instanceof Float32Array) return JSON.Types.TypedArray;
|
|
498
|
+
if (value instanceof Float64Array) return JSON.Types.TypedArray;
|
|
499
|
+
if (value instanceof ArrayBuffer) return JSON.Types.ArrayBuffer;
|
|
490
500
|
if (value instanceof Map) return JSON.Types.Map;
|
|
491
501
|
if (value instanceof JSON.Raw) return JSON.Types.Raw;
|
|
492
502
|
if (value instanceof JSON.Obj) return JSON.Types.Object;
|
|
493
|
-
|
|
494
|
-
// @ts-expect-error: supplied by transform
|
|
495
|
-
if (isDefined(value.__SERIALIZE) && isManaged<T>(value))
|
|
496
|
-
return u16(idof<T>()) + JSON.Types.Struct;
|
|
497
503
|
return JSON.Types.Null;
|
|
498
504
|
}
|
|
499
505
|
/**
|
|
@@ -504,37 +510,34 @@ export namespace JSON {
|
|
|
504
510
|
this.type = this.getType<T>(value);
|
|
505
511
|
|
|
506
512
|
if (value instanceof JSON.Box) this.set(value.value);
|
|
507
|
-
else if (isBoolean<T>())
|
|
508
|
-
|
|
509
|
-
else if (
|
|
510
|
-
|
|
511
|
-
!isSigned<T>() &&
|
|
512
|
-
changetype<usize>(value) == 0 &&
|
|
513
|
-
nameof<T>() == "usize"
|
|
514
|
-
)
|
|
515
|
-
store<usize>(changetype<usize>(this), 0, STORAGE);
|
|
516
|
-
else if (isInteger<T>() || isFloat<T>())
|
|
517
|
-
store<T>(changetype<usize>(this), value, STORAGE);
|
|
518
|
-
else if (isNullable<T>() && changetype<usize>(value) === 0)
|
|
519
|
-
store<usize>(changetype<usize>(this), 0, STORAGE);
|
|
513
|
+
else if (isBoolean<T>()) store<T>(changetype<usize>(this), value, STORAGE);
|
|
514
|
+
else if (isInteger<T>() && !isSigned<T>() && changetype<usize>(value) == 0 && nameof<T>() == "usize") store<usize>(changetype<usize>(this), 0, STORAGE);
|
|
515
|
+
else if (isInteger<T>() || isFloat<T>()) store<T>(changetype<usize>(this), value, STORAGE);
|
|
516
|
+
else if (isNullable<T>() && changetype<usize>(value) === 0) store<usize>(changetype<usize>(this), 0, STORAGE);
|
|
520
517
|
else if (isString<T>()) store<T>(changetype<usize>(this), value, STORAGE);
|
|
521
|
-
else if (value instanceof JSON.Raw)
|
|
522
|
-
|
|
518
|
+
else if (value instanceof JSON.Raw) store<T>(changetype<usize>(this), value, STORAGE);
|
|
519
|
+
// @ts-expect-error: supplied by transform
|
|
520
|
+
else if (isDefined(value.__SERIALIZE) && isManaged<T>(value)) {
|
|
521
|
+
// @ts-expect-error
|
|
522
|
+
if (!JSON.Value.METHODS.has(idof<T>())) JSON.Value.METHODS.set(idof<T>(), value.__SERIALIZE.index);
|
|
523
|
+
store<usize>(changetype<usize>(this), changetype<usize>(value), STORAGE);
|
|
524
|
+
} else if (value instanceof Int8Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
525
|
+
else if (value instanceof Uint8Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
526
|
+
else if (value instanceof Uint8ClampedArray) store<T>(changetype<usize>(this), value, STORAGE);
|
|
527
|
+
else if (value instanceof Int16Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
528
|
+
else if (value instanceof Uint16Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
529
|
+
else if (value instanceof Int32Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
530
|
+
else if (value instanceof Uint32Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
531
|
+
else if (value instanceof Int64Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
532
|
+
else if (value instanceof Uint64Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
533
|
+
else if (value instanceof Float32Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
534
|
+
else if (value instanceof Float64Array) store<T>(changetype<usize>(this), value, STORAGE);
|
|
535
|
+
else if (value instanceof ArrayBuffer) store<T>(changetype<usize>(this), value, STORAGE);
|
|
523
536
|
else if (value instanceof Map) {
|
|
524
537
|
if (idof<T>() !== idof<Map<string, JSON.Value>>()) {
|
|
525
538
|
abort("Maps must be of type Map<string, JSON.Value>!");
|
|
526
539
|
}
|
|
527
540
|
store<T>(changetype<usize>(this), value, STORAGE);
|
|
528
|
-
// @ts-expect-error: supplied by transform
|
|
529
|
-
} else if (isDefined(value.__SERIALIZE) && isManaged<T>(value)) {
|
|
530
|
-
// @ts-expect-error
|
|
531
|
-
if (!JSON.Value.METHODS.has(idof<T>()))
|
|
532
|
-
JSON.Value.METHODS.set(idof<T>(), value.__SERIALIZE.index);
|
|
533
|
-
store<usize>(
|
|
534
|
-
changetype<usize>(this),
|
|
535
|
-
changetype<usize>(value),
|
|
536
|
-
STORAGE,
|
|
537
|
-
);
|
|
538
541
|
} else if (value instanceof JSON.Obj) {
|
|
539
542
|
store<T>(changetype<usize>(this), value, STORAGE);
|
|
540
543
|
// @ts-expect-error
|
|
@@ -586,6 +589,14 @@ export namespace JSON {
|
|
|
586
589
|
return this.get<u32>().toString();
|
|
587
590
|
case JSON.Types.U64:
|
|
588
591
|
return this.get<u64>().toString();
|
|
592
|
+
case JSON.Types.I8:
|
|
593
|
+
return this.get<i8>().toString();
|
|
594
|
+
case JSON.Types.I16:
|
|
595
|
+
return this.get<i16>().toString();
|
|
596
|
+
case JSON.Types.I32:
|
|
597
|
+
return this.get<i32>().toString();
|
|
598
|
+
case JSON.Types.I64:
|
|
599
|
+
return this.get<i64>().toString();
|
|
589
600
|
case JSON.Types.F32:
|
|
590
601
|
return this.get<f32>().toString();
|
|
591
602
|
case JSON.Types.F64:
|
|
@@ -612,6 +623,11 @@ export namespace JSON {
|
|
|
612
623
|
|
|
613
624
|
return out.toString();
|
|
614
625
|
}
|
|
626
|
+
case JSON.Types.TypedArray:
|
|
627
|
+
case JSON.Types.ArrayBuffer: {
|
|
628
|
+
serializeDynamic(this.type, this.get<usize>());
|
|
629
|
+
return bs.out<string>();
|
|
630
|
+
}
|
|
615
631
|
case JSON.Types.Object: {
|
|
616
632
|
return JSON.stringify(this.get<JSON.Obj>());
|
|
617
633
|
}
|
|
@@ -732,11 +748,25 @@ export namespace JSON {
|
|
|
732
748
|
*/
|
|
733
749
|
@inline static from<T>(value: T): JSON.Obj {
|
|
734
750
|
if (value instanceof JSON.Obj) return value;
|
|
735
|
-
const out = new JSON.Obj();
|
|
736
|
-
|
|
737
751
|
if (value instanceof Map) {
|
|
752
|
+
const out = new JSON.Obj();
|
|
753
|
+
if (!isString<indexof<T>>()) {
|
|
754
|
+
throw new Error("JSON.Obj.from only supports maps with string keys");
|
|
755
|
+
}
|
|
756
|
+
|
|
757
|
+
const keys = value.keys();
|
|
758
|
+
const values = value.values();
|
|
759
|
+
for (let i = 0; i < keys.length; i++) {
|
|
760
|
+
out.set(unchecked(keys[i]), unchecked(values[i]));
|
|
761
|
+
}
|
|
762
|
+
return out;
|
|
738
763
|
}
|
|
739
|
-
|
|
764
|
+
|
|
765
|
+
const parsed = JSON.parse<JSON.Value>(JSON.stringify(value));
|
|
766
|
+
if (parsed.type != JSON.Types.Object) {
|
|
767
|
+
throw new Error("JSON.Obj.from expects a value that serializes to a JSON object");
|
|
768
|
+
}
|
|
769
|
+
return parsed.get<JSON.Obj>();
|
|
740
770
|
}
|
|
741
771
|
}
|
|
742
772
|
/**
|
|
@@ -744,8 +774,7 @@ export namespace JSON {
|
|
|
744
774
|
*/
|
|
745
775
|
export class Box<T> {
|
|
746
776
|
constructor(public value: T) {
|
|
747
|
-
if (!isInteger<T>() && !isFloat<T>())
|
|
748
|
-
ERROR("JSON.Box should only hold primitive types!");
|
|
777
|
+
if (!isInteger<T>() && !isFloat<T>() && !isBoolean<T>()) ERROR("JSON.Box should only hold primitive types!");
|
|
749
778
|
}
|
|
750
779
|
/**
|
|
751
780
|
* Set the internal value of Box to new value
|
|
@@ -768,11 +797,9 @@ export namespace JSON {
|
|
|
768
797
|
* @returns Box<T> | null
|
|
769
798
|
*/
|
|
770
799
|
@inline static fromValue<T>(value: JSON.Value): Box<T> | null {
|
|
771
|
-
if (!(value instanceof JSON.Value))
|
|
772
|
-
throw new Error("value must be of type JSON.Value");
|
|
800
|
+
if (!(value instanceof JSON.Value)) throw new Error("value must be of type JSON.Value");
|
|
773
801
|
if (value.type === JSON.Types.Null) return null;
|
|
774
|
-
const v =
|
|
775
|
-
value.type === JSON.Types.F64 ? value.get<f64>() : value.get<T>();
|
|
802
|
+
const v = value.type === JSON.Types.F64 ? value.get<f64>() : value.get<T>();
|
|
776
803
|
// @ts-expect-error
|
|
777
804
|
return new Box(isInteger<T>() || isFloat<T>() ? <T>v : v);
|
|
778
805
|
}
|
|
@@ -821,20 +848,14 @@ export namespace JSON {
|
|
|
821
848
|
store<u64>(bs.offset, NULL_WORD_U64);
|
|
822
849
|
bs.offset += 8;
|
|
823
850
|
} else if (isString<nonnull<T>>()) {
|
|
824
|
-
|
|
825
|
-
|
|
826
|
-
} else if (JSON_MODE === JSONMode.SWAR) {
|
|
827
|
-
serializeString_SWAR(data as string);
|
|
828
|
-
} else {
|
|
829
|
-
serializeString(data as string);
|
|
830
|
-
}
|
|
831
|
-
// @ts-expect-error: Supplied by transform
|
|
851
|
+
serializeString(data as string);
|
|
852
|
+
// @ts-expect-error: Defined by transform
|
|
832
853
|
} else if (isDefined(data.__SERIALIZE_CUSTOM)) {
|
|
833
854
|
// @ts-expect-error
|
|
834
855
|
return data.__SERIALIZE_CUSTOM();
|
|
835
|
-
// @ts-expect-error:
|
|
856
|
+
// @ts-expect-error: Defined by transform
|
|
836
857
|
} else if (isDefined(data.__SERIALIZE)) {
|
|
837
|
-
// @ts-expect-error
|
|
858
|
+
// @ts-expect-error: type
|
|
838
859
|
serializeStruct(changetype<nonnull<T>>(data));
|
|
839
860
|
} else if (data instanceof Date) {
|
|
840
861
|
// @ts-expect-error
|
|
@@ -845,6 +866,31 @@ export namespace JSON {
|
|
|
845
866
|
} else if (data instanceof StaticArray) {
|
|
846
867
|
// @ts-expect-error
|
|
847
868
|
serializeStaticArray(changetype<nonnull<T>>(data));
|
|
869
|
+
} else if (data instanceof Int8Array) {
|
|
870
|
+
serializeTypedArray<Int8Array>(data);
|
|
871
|
+
} else if (data instanceof Uint8Array) {
|
|
872
|
+
serializeTypedArray<Uint8Array>(data);
|
|
873
|
+
} else if (data instanceof Uint8ClampedArray) {
|
|
874
|
+
serializeTypedArray<Uint8ClampedArray>(data);
|
|
875
|
+
} else if (data instanceof Int16Array) {
|
|
876
|
+
serializeTypedArray<Int16Array>(data);
|
|
877
|
+
} else if (data instanceof Uint16Array) {
|
|
878
|
+
serializeTypedArray<Uint16Array>(data);
|
|
879
|
+
} else if (data instanceof Int32Array) {
|
|
880
|
+
serializeTypedArray<Int32Array>(data);
|
|
881
|
+
} else if (data instanceof Uint32Array) {
|
|
882
|
+
serializeTypedArray<Uint32Array>(data);
|
|
883
|
+
} else if (data instanceof Int64Array) {
|
|
884
|
+
serializeTypedArray<Int64Array>(data);
|
|
885
|
+
} else if (data instanceof Uint64Array) {
|
|
886
|
+
serializeTypedArray<Uint64Array>(data);
|
|
887
|
+
} else if (data instanceof Float32Array) {
|
|
888
|
+
serializeTypedArray<Float32Array>(data);
|
|
889
|
+
} else if (data instanceof Float64Array) {
|
|
890
|
+
serializeTypedArray<Float64Array>(data);
|
|
891
|
+
} else if (data instanceof ArrayBuffer) {
|
|
892
|
+
const dataStart = changetype<usize>(data);
|
|
893
|
+
serializeArrayBufferUnsafe(dataStart, changetype<OBJECT>(dataStart - TOTAL_OVERHEAD).rtSize);
|
|
848
894
|
} else if (data instanceof Set) {
|
|
849
895
|
// @ts-expect-error
|
|
850
896
|
serializeSet(changetype<nonnull<T>>(data));
|
|
@@ -860,11 +906,7 @@ export namespace JSON {
|
|
|
860
906
|
} else if (data instanceof JSON.Box) {
|
|
861
907
|
__serialize(data.value);
|
|
862
908
|
} else {
|
|
863
|
-
throw new Error(
|
|
864
|
-
`Could not serialize data of type '${nameof<T>()}'. ` +
|
|
865
|
-
`If this is a custom class, add the @json decorator: @json class ${nameof<T>()} { ... }. ` +
|
|
866
|
-
`Supported types: primitives, string, Array, Map, Date, and @json decorated classes.`,
|
|
867
|
-
);
|
|
909
|
+
throw new Error(`Could not serialize data of type '${nameof<T>()}'. ` + `If this is a custom class, add the @json decorator: @json class ${nameof<T>()} { ... }. ` + `Supported types: primitives, string, Array, StaticArray, TypedArray, ArrayBuffer, Map, Date, and @json decorated classes.`);
|
|
868
910
|
}
|
|
869
911
|
}
|
|
870
912
|
|
|
@@ -876,52 +918,69 @@ export namespace JSON {
|
|
|
876
918
|
* @param dst - usize
|
|
877
919
|
* @returns void
|
|
878
920
|
*/
|
|
879
|
-
export function __deserialize<T>(
|
|
880
|
-
srcStart: usize,
|
|
881
|
-
srcEnd: usize,
|
|
882
|
-
dst: usize = 0,
|
|
883
|
-
): T {
|
|
921
|
+
export function __deserialize<T>(srcStart: usize, srcEnd: usize, dst: usize = 0): T {
|
|
884
922
|
if (isBoolean<T>()) {
|
|
885
923
|
// @ts-expect-error: type
|
|
886
924
|
return deserializeBoolean(srcStart, srcEnd);
|
|
887
925
|
} else if (isInteger<T>()) {
|
|
888
|
-
return
|
|
926
|
+
return isSigned<T>() ? deserializeInteger<T>(srcStart, srcEnd) : deserializeUnsigned<T>(srcStart, srcEnd);
|
|
889
927
|
} else if (isFloat<T>()) {
|
|
890
928
|
return deserializeFloat<T>(srcStart, srcEnd);
|
|
891
929
|
} else if (isString<T>()) {
|
|
892
|
-
if (srcEnd - srcStart < 4)
|
|
893
|
-
throw new Error(
|
|
894
|
-
"Cannot parse data as string because it was formatted incorrectly!",
|
|
895
|
-
);
|
|
930
|
+
if (srcEnd - srcStart < 4) throw new Error("Cannot parse data as string because it was formatted incorrectly!");
|
|
896
931
|
|
|
897
|
-
|
|
898
|
-
|
|
899
|
-
} else if (
|
|
900
|
-
isNullable<T>() &&
|
|
901
|
-
srcEnd - srcStart == 8 &&
|
|
902
|
-
load<u64>(srcStart) == NULL_WORD_U64
|
|
903
|
-
) {
|
|
932
|
+
return deserializeString(srcStart, srcEnd) as T;
|
|
933
|
+
} else if (isNullable<T>() && srcEnd - srcStart == 8 && load<u64>(srcStart) == NULL_WORD_U64) {
|
|
904
934
|
return null;
|
|
905
935
|
} else {
|
|
906
936
|
let type: nonnull<T> = changetype<nonnull<T>>(0);
|
|
937
|
+
// @ts-expect-error: Defined by transform
|
|
938
|
+
if (isDefined(type.__DESERIALIZE_CUSTOM)) {
|
|
939
|
+
const out = changetype<nonnull<T>>(0);
|
|
940
|
+
// @ts-expect-error: Defined by transform
|
|
941
|
+
return out.__DESERIALIZE_CUSTOM(ptrToStr(srcStart, srcEnd));
|
|
942
|
+
// @ts-expect-error: Defined by transform
|
|
943
|
+
} else if (isDefined(type.__DESERIALIZE)) {
|
|
944
|
+
const out = changetype<nonnull<T>>(dst || __new(offsetof<nonnull<T>>(), idof<nonnull<T>>()));
|
|
945
|
+
// @ts-expect-error: Defined by transform
|
|
946
|
+
if (isDefined(type.__INITIALIZE)) out.__INITIALIZE();
|
|
947
|
+
// @ts-expect-error: Defined by transform
|
|
948
|
+
out.__DESERIALIZE(srcStart, srcEnd, out);
|
|
949
|
+
return out;
|
|
950
|
+
}
|
|
907
951
|
if (type instanceof StaticArray) {
|
|
908
952
|
// @ts-expect-error: type
|
|
909
953
|
return deserializeStaticArray<T>(srcStart, srcEnd, dst);
|
|
910
954
|
} else if (type instanceof Array) {
|
|
911
955
|
// @ts-expect-error: type
|
|
912
956
|
return deserializeArray<T>(srcStart, srcEnd, dst);
|
|
957
|
+
} else if (type instanceof Int8Array) {
|
|
958
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
959
|
+
} else if (type instanceof Uint8Array) {
|
|
960
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
961
|
+
} else if (type instanceof Uint8ClampedArray) {
|
|
962
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
963
|
+
} else if (type instanceof Int16Array) {
|
|
964
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
965
|
+
} else if (type instanceof Uint16Array) {
|
|
966
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
967
|
+
} else if (type instanceof Int32Array) {
|
|
968
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
969
|
+
} else if (type instanceof Uint32Array) {
|
|
970
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
971
|
+
} else if (type instanceof Int64Array) {
|
|
972
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
973
|
+
} else if (type instanceof Uint64Array) {
|
|
974
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
975
|
+
} else if (type instanceof Float32Array) {
|
|
976
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
977
|
+
} else if (type instanceof Float64Array) {
|
|
978
|
+
return deserializeTypedArray<nonnull<T>>(srcStart, srcEnd, dst) as T;
|
|
979
|
+
} else if (type instanceof ArrayBuffer) {
|
|
980
|
+
return deserializeArrayBuffer(srcStart, srcEnd, dst) as T;
|
|
913
981
|
} else if (type instanceof Set) {
|
|
914
982
|
// @ts-expect-error: type
|
|
915
983
|
return deserializeSet<T>(srcStart, srcEnd, dst);
|
|
916
|
-
// @ts-expect-error: Defined by transform
|
|
917
|
-
} else if (isDefined(type.__DESERIALIZE)) {
|
|
918
|
-
const out = changetype<nonnull<T>>(
|
|
919
|
-
dst || __new(offsetof<nonnull<T>>(), idof<nonnull<T>>()),
|
|
920
|
-
);
|
|
921
|
-
// @ts-expect-error: Defined by transform
|
|
922
|
-
if (isDefined(type.__INITIALIZE)) out.__INITIALIZE();
|
|
923
|
-
// @ts-expect-error: Defined by transform
|
|
924
|
-
return out.__DESERIALIZE(srcStart, srcEnd, out);
|
|
925
984
|
} else if (type instanceof Map) {
|
|
926
985
|
// @ts-expect-error: type
|
|
927
986
|
return deserializeMap<T>(srcStart, srcEnd, dst);
|
|
@@ -939,22 +998,11 @@ export namespace JSON {
|
|
|
939
998
|
return deserializeObject(srcStart, srcEnd, 0);
|
|
940
999
|
} else if (type instanceof JSON.Box) {
|
|
941
1000
|
// @ts-expect-error: type
|
|
942
|
-
return new JSON.Box(
|
|
943
|
-
deserializeBox(
|
|
944
|
-
srcStart,
|
|
945
|
-
srcEnd,
|
|
946
|
-
dst,
|
|
947
|
-
changetype<nonnull<T>>(0).value,
|
|
948
|
-
),
|
|
949
|
-
);
|
|
1001
|
+
return new JSON.Box(deserializeBox(srcStart, srcEnd, dst, changetype<nonnull<T>>(0).value));
|
|
950
1002
|
}
|
|
951
1003
|
}
|
|
952
1004
|
const snippet = ptrToStr(srcStart, srcEnd);
|
|
953
|
-
throw new Error(
|
|
954
|
-
`Could not deserialize JSON to type '${nameof<T>()}'. ` +
|
|
955
|
-
`If this is a custom class, ensure it has the @json decorator: @json class ${nameof<T>()} { ... }. ` +
|
|
956
|
-
`Input: "${snippet.length > 50 ? snippet.slice(0, 50) + "..." : snippet}"`,
|
|
957
|
-
);
|
|
1005
|
+
throw new Error(`Could not deserialize JSON to type '${nameof<T>()}'. ` + `If this is a custom class, ensure it has the @json decorator: @json class ${nameof<T>()} { ... }. ` + `Input: "${snippet.length > 50 ? snippet.slice(0, 50) + "..." : snippet}"`);
|
|
958
1006
|
}
|
|
959
1007
|
export namespace Util {
|
|
960
1008
|
// @ts-expect-error: decorator
|
|
@@ -970,7 +1018,8 @@ export namespace JSON {
|
|
|
970
1018
|
}
|
|
971
1019
|
}
|
|
972
1020
|
/**
|
|
973
|
-
* Methods for use when using JSON methods inside another JSON method or custom serializer/deserializer
|
|
1021
|
+
* Methods for use when using JSON methods inside another JSON method or custom serializer/deserializer
|
|
1022
|
+
* Transform will automatically convert JSON.x calls to JSON.internal.x when in a custom (de)serializer
|
|
974
1023
|
*/
|
|
975
1024
|
export namespace internal {
|
|
976
1025
|
/**
|
|
@@ -980,133 +1029,31 @@ export namespace JSON {
|
|
|
980
1029
|
* @returns - string
|
|
981
1030
|
*/
|
|
982
1031
|
// @ts-expect-error: inline
|
|
983
|
-
@inline export function stringify<T>(
|
|
984
|
-
|
|
985
|
-
|
|
986
|
-
|
|
987
|
-
if (
|
|
988
|
-
|
|
989
|
-
|
|
990
|
-
|
|
991
|
-
|
|
992
|
-
} else {
|
|
993
|
-
out = changetype<string>(__renew(changetype<usize>(out), 10));
|
|
994
|
-
store<u64>(changetype<usize>(out), FALSE_WORD_U64);
|
|
995
|
-
store<u16>(changetype<usize>(out), 101, 8);
|
|
996
|
-
}
|
|
997
|
-
return out;
|
|
998
|
-
}
|
|
999
|
-
return data ? "true" : "false";
|
|
1000
|
-
} else if (
|
|
1001
|
-
isInteger<T>() &&
|
|
1002
|
-
!isSigned<T>() &&
|
|
1003
|
-
nameof<T>() == "usize" &&
|
|
1004
|
-
data == 0
|
|
1005
|
-
) {
|
|
1006
|
-
if (out) {
|
|
1007
|
-
out = changetype<string>(__renew(changetype<usize>(out), 8));
|
|
1008
|
-
store<u64>(changetype<usize>(out), NULL_WORD_U64);
|
|
1009
|
-
return out;
|
|
1010
|
-
}
|
|
1011
|
-
return NULL_WORD;
|
|
1012
|
-
} else if (isInteger<T>(data)) {
|
|
1013
|
-
if (out) {
|
|
1014
|
-
out = changetype<string>(
|
|
1015
|
-
__renew(changetype<usize>(out), sizeof<T>() << 3),
|
|
1016
|
-
);
|
|
1017
|
-
|
|
1018
|
-
const bytes = itoa_buffered(changetype<usize>(out), data) << 1;
|
|
1019
|
-
return (out = changetype<string>(
|
|
1020
|
-
__renew(changetype<usize>(out), bytes),
|
|
1021
|
-
));
|
|
1022
|
-
}
|
|
1023
|
-
return data.toString();
|
|
1024
|
-
} else if (isFloat<T>(data)) {
|
|
1025
|
-
if (out) {
|
|
1026
|
-
out = changetype<string>(__renew(changetype<usize>(out), 64));
|
|
1027
|
-
|
|
1028
|
-
const bytes = dtoa_buffered(changetype<usize>(out), data) << 1;
|
|
1029
|
-
return (out = changetype<string>(
|
|
1030
|
-
__renew(changetype<usize>(out), bytes),
|
|
1031
|
-
));
|
|
1032
|
-
}
|
|
1033
|
-
return data.toString();
|
|
1034
|
-
} else if (isNullable<T>() && changetype<usize>(data) == <usize>0) {
|
|
1035
|
-
if (out) {
|
|
1036
|
-
out = changetype<string>(__renew(changetype<usize>(out), 8));
|
|
1037
|
-
store<u64>(changetype<usize>(out), NULL_WORD_U64);
|
|
1038
|
-
return out;
|
|
1039
|
-
}
|
|
1040
|
-
return NULL_WORD;
|
|
1041
|
-
} else if (isString<nonnull<T>>()) {
|
|
1042
|
-
if (JSON_MODE === JSONMode.SIMD) {
|
|
1043
|
-
serializeString_SIMD(data as string);
|
|
1044
|
-
} else if (JSON_MODE === JSONMode.SWAR) {
|
|
1045
|
-
serializeString_SWAR(data as string);
|
|
1046
|
-
} else {
|
|
1047
|
-
serializeString(data as string);
|
|
1048
|
-
}
|
|
1049
|
-
return bs.cpyOut<string>();
|
|
1050
|
-
// @ts-expect-error: Supplied by transform
|
|
1051
|
-
} else if (isDefined(data.__SERIALIZE)) {
|
|
1052
|
-
bs.saveState();
|
|
1053
|
-
// @ts-expect-error
|
|
1054
|
-
inline.always(data.__SERIALIZE(changetype<usize>(data)));
|
|
1055
|
-
return bs.cpyOut<string>();
|
|
1056
|
-
} else if (data instanceof Date) {
|
|
1057
|
-
out = out
|
|
1058
|
-
? changetype<string>(__renew(changetype<usize>(out), 52))
|
|
1059
|
-
: changetype<string>(__new(52, idof<string>()));
|
|
1060
|
-
|
|
1061
|
-
store<u16>(changetype<usize>(out), QUOTE);
|
|
1062
|
-
memory.copy(
|
|
1063
|
-
changetype<usize>(out) + 2,
|
|
1064
|
-
changetype<usize>(data.toISOString()),
|
|
1065
|
-
48,
|
|
1066
|
-
);
|
|
1067
|
-
store<u16>(changetype<usize>(out), QUOTE, 50);
|
|
1068
|
-
return changetype<string>(out);
|
|
1069
|
-
} else if (data instanceof Array) {
|
|
1070
|
-
bs.saveState();
|
|
1071
|
-
// @ts-expect-error
|
|
1072
|
-
inline.always(serializeArray(changetype<nonnull<T>>(data)));
|
|
1073
|
-
return bs.cpyOut<string>();
|
|
1074
|
-
} else if (data instanceof StaticArray) {
|
|
1075
|
-
bs.saveState();
|
|
1076
|
-
// @ts-expect-error
|
|
1077
|
-
inline.always(serializeStaticArray(changetype<nonnull<T>>(data)));
|
|
1078
|
-
return bs.cpyOut<string>();
|
|
1079
|
-
} else if (data instanceof Set) {
|
|
1080
|
-
bs.saveState();
|
|
1081
|
-
// @ts-expect-error
|
|
1082
|
-
inline.always(serializeSet(changetype<nonnull<T>>(data)));
|
|
1083
|
-
return bs.cpyOut<string>();
|
|
1084
|
-
} else if (data instanceof Map) {
|
|
1085
|
-
bs.saveState();
|
|
1086
|
-
// @ts-expect-error
|
|
1087
|
-
inline.always(serializeMap(changetype<nonnull<T>>(data)));
|
|
1088
|
-
return bs.cpyOut<string>();
|
|
1089
|
-
} else if (data instanceof JSON.Raw) {
|
|
1090
|
-
bs.saveState();
|
|
1091
|
-
serializeRaw(data);
|
|
1092
|
-
return bs.cpyOut<string>();
|
|
1093
|
-
} else if (data instanceof JSON.Value) {
|
|
1094
|
-
bs.saveState();
|
|
1095
|
-
inline.always(serializeArbitrary(data));
|
|
1096
|
-
return bs.cpyOut<string>();
|
|
1097
|
-
} else if (data instanceof JSON.Obj) {
|
|
1098
|
-
bs.saveState();
|
|
1099
|
-
inline.always(serializeObject(data));
|
|
1100
|
-
return bs.cpyOut<string>();
|
|
1101
|
-
} else if (data instanceof JSON.Box) {
|
|
1102
|
-
return JSON.internal.stringify(data.value);
|
|
1103
|
-
} else {
|
|
1104
|
-
throw new Error(
|
|
1105
|
-
`Could not serialize data of type '${nameof<T>()}'. ` +
|
|
1106
|
-
`If this is a custom class, add the @json decorator: @json class ${nameof<T>()} { ... }. ` +
|
|
1107
|
-
`Supported types: primitives, string, Array, Map, Date, and @json decorated classes.`,
|
|
1108
|
-
);
|
|
1032
|
+
@inline export function stringify<T>(data: T, out: string | null = null): string {
|
|
1033
|
+
bs.saveState();
|
|
1034
|
+
JSON.__serialize<T>(data);
|
|
1035
|
+
const result = bs.cpyOut<string>();
|
|
1036
|
+
if (out) {
|
|
1037
|
+
const len = bytes(result);
|
|
1038
|
+
out = changetype<string>(__renew(changetype<usize>(out), len));
|
|
1039
|
+
memory.copy(changetype<usize>(out), changetype<usize>(result), len);
|
|
1040
|
+
return out;
|
|
1109
1041
|
}
|
|
1042
|
+
return result;
|
|
1043
|
+
}
|
|
1044
|
+
|
|
1045
|
+
/**
|
|
1046
|
+
* Parses JSON data without mutating the caller's active serialization buffer state.
|
|
1047
|
+
* Don't use this directly, use `JSON.parse` instead.
|
|
1048
|
+
* @param data - string
|
|
1049
|
+
* @returns - T
|
|
1050
|
+
*/
|
|
1051
|
+
// @ts-expect-error: inline
|
|
1052
|
+
@inline export function parse<T>(data: string): T {
|
|
1053
|
+
bs.saveState();
|
|
1054
|
+
const result = JSON.parse<T>(data);
|
|
1055
|
+
bs.loadState();
|
|
1056
|
+
return result;
|
|
1110
1057
|
}
|
|
1111
1058
|
}
|
|
1112
1059
|
}
|
|
@@ -1122,12 +1069,7 @@ export enum JSONMode {
|
|
|
1122
1069
|
return JSON.parse<T>(data);
|
|
1123
1070
|
}
|
|
1124
1071
|
// @ts-expect-error: inline
|
|
1125
|
-
@inline function deserializeBox<T>(
|
|
1126
|
-
srcStart: usize,
|
|
1127
|
-
srcEnd: usize,
|
|
1128
|
-
dst: usize,
|
|
1129
|
-
ty: T,
|
|
1130
|
-
): T {
|
|
1072
|
+
@inline function deserializeBox<T>(srcStart: usize, srcEnd: usize, dst: usize, ty: T): T {
|
|
1131
1073
|
return JSON.__deserialize<T>(srcStart, srcEnd, dst);
|
|
1132
1074
|
}
|
|
1133
1075
|
|