This is an automated email from the ASF dual-hosted git repository.
wangweipeng pushed a commit to branch main
in repository https://gitbox.apache.org/repos/asf/incubator-fury.git
The following commit(s) were added to refs/heads/main by this push:
new 53ee111c feat(javascript): Implement Xlang map (#1549)
53ee111c is described below
commit 53ee111c312debb362a61fc5045db709d876e9ce
Author: weipeng <[email protected]>
AuthorDate: Mon Apr 22 23:44:59 2024 +0800
feat(javascript): Implement Xlang map (#1549)
## What does this PR do?
1. Implement the map protocol.
2. Cache the primitive type serializer, guess serializer by data type
every time is unnecessary.
In this PR , the code generator is simple call the AnySerializer which
is much more slower then jit code, I will implement the code generator
next PR.
## Does this PR introduce any user-facing change?
No user-facing change.
## Benchmark
Before:
| (index) | Values |
|-------------|--------|
| serialize | 365 |
| deserialize | 193 |
After:
| (index) | Values |
|-------------|--------|
| serialize | 519 |
| deserialize | 238 |
---------
Co-authored-by: wangweipeng <weipeng>
---
javascript/benchmark/map.js | 60 ++++++
javascript/packages/fury/lib/classResolver.ts | 50 +++--
javascript/packages/fury/lib/gen/collection.ts | 13 +-
javascript/packages/fury/lib/gen/map.ts | 276 ++++++++++++++++++++-----
javascript/packages/fury/lib/meta.ts | 17 ++
javascript/packages/fury/lib/writer/index.ts | 8 +
6 files changed, 345 insertions(+), 79 deletions(-)
diff --git a/javascript/benchmark/map.js b/javascript/benchmark/map.js
new file mode 100644
index 00000000..8e4df29f
--- /dev/null
+++ b/javascript/benchmark/map.js
@@ -0,0 +1,60 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements. See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership. The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied. See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+const Fury = require("@furyjs/fury");
+const hps = require('@furyjs/hps');
+const fury = new Fury.default({ hps, refTracking: false, useSliceString: true
});
+const Benchmark = require("benchmark");
+const Type = Fury.Type;
+
+
+
+const { serialize, deserialize, serializeVolatile } =
fury.registerSerializer(Type.map(Type.any(), Type.any()));
+const sample = new Map([["foo", "ba1"],["foo1", "ba1"],["foo2",
"ba1"],["foo3", "ba1"],["foo4", "ba1"],["foo5", "ba1"]]);
+const furyAb = serialize(sample);
+
+
+async function start() {
+
+ let result = {
+ serialize: 0,
+ deserialize: 0
+ }
+
+ {
+ var suite = new Benchmark.Suite();
+ suite
+ .add("serialize", function () {
+ serializeVolatile(sample).dispose()
+ })
+ .add("deserialize", function () {
+ deserialize(furyAb)
+ })
+ .on("complete", function (e) {
+ e.currentTarget.forEach(({ name, hz }) => {
+ result[name] = Math.ceil(hz / 10000);
+ });
+ })
+ .run({ async: false });
+ }
+
+ console.table(result);
+
+}
+start();
diff --git a/javascript/packages/fury/lib/classResolver.ts
b/javascript/packages/fury/lib/classResolver.ts
index c2d0f4c4..27dbbc64 100644
--- a/javascript/packages/fury/lib/classResolver.ts
+++ b/javascript/packages/fury/lib/classResolver.ts
@@ -72,6 +72,7 @@ const uninitSerialize = {
fixedSize: 0,
type: InternalSerializerType.ANY,
needToWriteRef: false,
+ typeId: null,
},
};
@@ -114,8 +115,26 @@ export default class SerializerResolver {
this.registerSerializer(fury, Type.float16Array());
this.registerSerializer(fury, Type.float32Array());
this.registerSerializer(fury, Type.float64Array());
+
+ this.numberSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.FLOAT64));
+ this.int64Serializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.INT64));
+ this.boolSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.BOOL));
+ this.dateSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.TIMESTAMP));
+ this.stringSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.STRING));
+ this.setSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.SET));
+ this.arraySerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.ARRAY));
+ this.mapSerializer =
this.getSerializerById(SerializerResolver.getTypeIdByInternalSerializerType(InternalSerializerType.MAP));
}
+ private numberSerializer: null | Serializer = null;
+ private int64Serializer: null | Serializer = null;
+ private boolSerializer: null | Serializer = null;
+ private dateSerializer: null | Serializer = null;
+ private stringSerializer: null | Serializer = null;
+ private setSerializer: null | Serializer = null;
+ private arraySerializer: null | Serializer = null;
+ private mapSerializer: null | Serializer = null;
+
init(fury: Fury) {
this.initInternalSerializer(fury);
}
@@ -213,42 +232,37 @@ export default class SerializerResolver {
}
getSerializerByData(v: any) {
- if (v === null || v === undefined) {
- return null;
+ if (typeof v === "number") {
+ return this.numberSerializer;
}
- if (typeof v === "number") {
- return this.getSerializerByType(InternalSerializerType.FLOAT64);
+ if (typeof v === "string") {
+ return this.stringSerializer;
}
- if (typeof v === "bigint") {
- return this.getSerializerByType(InternalSerializerType.INT64);
+ if (Array.isArray(v)) {
+ return this.arraySerializer;
}
if (typeof v === "boolean") {
- return this.getSerializerByType(InternalSerializerType.BOOL);
+ return this.boolSerializer;
}
- if (v instanceof Date) {
- return this.getSerializerByType(InternalSerializerType.TIMESTAMP);
+ if (typeof v === "bigint") {
+ return this.int64Serializer;
}
- if (typeof v === "string") {
- return this.getSerializerByType(InternalSerializerType.STRING);
+ if (v instanceof Date) {
+ return this.dateSerializer;
}
if (v instanceof Map) {
- return this.getSerializerByType(InternalSerializerType.MAP);
+ return this.mapSerializer;
}
if (v instanceof Set) {
- return this.getSerializerByType(InternalSerializerType.SET);
+ return this.setSerializer;
}
-
- if (Array.isArray(v)) {
- return this.getSerializerByType(InternalSerializerType.ARRAY);
- }
-
throw new Error(`Failed to detect the Fury type from JavaScript type:
${typeof v}`);
}
diff --git a/javascript/packages/fury/lib/gen/collection.ts
b/javascript/packages/fury/lib/gen/collection.ts
index 0b53edb0..5620e499 100644
--- a/javascript/packages/fury/lib/gen/collection.ts
+++ b/javascript/packages/fury/lib/gen/collection.ts
@@ -56,10 +56,9 @@ class CollectionAnySerializer {
}
if (isSame) {
const current = this.fury.classResolver.getSerializerByData(item);
- if (serializer !== null && current !== null && current !== serializer)
{
+ if (serializer !== null && current !== serializer) {
isSame = false;
- }
- if (current !== null) {
+ } else {
serializer = current;
}
}
@@ -71,16 +70,12 @@ class CollectionAnySerializer {
if (includeNone) {
flag |= CollectionFlags.HAS_NULL;
}
- if (serializer !== null && serializer.meta.needToWriteRef) {
+ if (serializer!.meta.needToWriteRef) {
flag |= CollectionFlags.TRACKING_REF;
}
this.fury.binaryWriter.uint8(flag);
if (isSame) {
- if (serializer) {
- this.fury.binaryWriter.int16(serializer.meta.type);
- } else {
- this.fury.binaryWriter.skip(2);
- }
+ this.fury.binaryWriter.int16(serializer!.meta.type);
}
return {
serializer,
diff --git a/javascript/packages/fury/lib/gen/map.ts
b/javascript/packages/fury/lib/gen/map.ts
index 7976491d..dc6eda05 100644
--- a/javascript/packages/fury/lib/gen/map.ts
+++ b/javascript/packages/fury/lib/gen/map.ts
@@ -21,77 +21,249 @@ import { MapTypeDescription, TypeDescription } from
"../description";
import { CodecBuilder } from "./builder";
import { BaseSerializerGenerator, RefState } from "./serializer";
import { CodegenRegistry } from "./router";
-import { InternalSerializerType } from "../type";
+import { InternalSerializerType, RefFlags, Serializer } from "../type";
import { Scope } from "./scope";
+import Fury from "../fury";
-class MapSerializerGenerator extends BaseSerializerGenerator {
- description: MapTypeDescription;
+const MapFlags = {
+ /** Whether track elements ref. */
+ TRACKING_REF: 0b1,
- constructor(description: TypeDescription, builder: CodecBuilder, scope:
Scope) {
- super(description, builder, scope);
- this.description = <MapTypeDescription>description;
+ /** Whether collection has null. */
+ HAS_NULL: 0b10,
+
+ /** Whether collection elements type is not declare type. */
+ NOT_DECL_ELEMENT_TYPE: 0b100,
+
+ /** Whether collection elements type different. */
+ NOT_SAME_TYPE: 0b1000,
+};
+
+class TypeInfo {
+ private static IS_NULL = 0b10;
+ private static TRACKING_REF = 0b01;
+ static elementInfo(typeId: number, isNull: 0 | 1, trackRef: 0 | 1) {
+ return typeId << 16 | isNull << 1 | trackRef;
}
- private innerMeta() {
- const key = this.description.options.key;
- const value = this.description.options.value;
- return [this.builder.meta(key), this.builder.meta(value)];
+ static isNull(info: number) {
+ return info & this.IS_NULL;
+ }
+
+ static trackingRef(info: number) {
+ return info & this.TRACKING_REF;
+ }
+}
+
+class MapChunkWriter {
+ private preKeyInfo = 0;
+ private preValueInfo = 0;
+
+ private chunkSize = 0;
+ private chunkOffset = 0;
+ private header = 0;
+
+ constructor(private fury: Fury) {
+
+ }
+
+ private getHead(keyInfo: number, valueInfo: number) {
+ let flag = 0;
+ if (TypeInfo.isNull(keyInfo)) {
+ flag |= MapFlags.HAS_NULL;
+ }
+ if (TypeInfo.trackingRef(keyInfo)) {
+ flag |= MapFlags.TRACKING_REF;
+ }
+ flag <<= 4;
+ if (TypeInfo.isNull(valueInfo)) {
+ flag |= MapFlags.HAS_NULL;
+ }
+ if (TypeInfo.trackingRef(valueInfo)) {
+ flag |= MapFlags.TRACKING_REF;
+ }
+ return flag;
}
- private innerGenerator() {
- const key = this.description.options.key;
- const value = this.description.options.value;
+ private writeHead(keyInfo: number, valueInfo: number) {
+ // KV header
+ const header = this.getHead(keyInfo, valueInfo);
+ this.fury.binaryWriter.uint8(header);
+ // chunkSize, max 255
+ this.chunkOffset = this.fury.binaryWriter.getCursor();
+ this.fury.binaryWriter.uint8(0);
+ this.fury.binaryWriter.uint32((keyInfo >> 16) | (valueInfo & 0xFFFF0000));
+ return header;
+ }
- const KeyGeneratorClass = CodegenRegistry.get(key.type);
- const ValueGeneratorClass = CodegenRegistry.get(value.type);
- if (!KeyGeneratorClass) {
- throw new Error(`${key.type} generator not exists`);
+ next(keyInfo: number, valueInfo: number) {
+ // max size of chunk is 255
+ if (this.chunkSize == 255
+ || this.chunkOffset == 0
+ || this.preKeyInfo !== keyInfo
+ || this.preValueInfo !== valueInfo
+ ) {
+ // new chunk
+ this.endChunk();
+ this.chunkSize++;
+ this.preKeyInfo = keyInfo;
+ this.preValueInfo = valueInfo;
+ return this.header = this.writeHead(keyInfo, valueInfo);
}
- if (!ValueGeneratorClass) {
- throw new Error(`${value.type} generator not exists`);
+ this.chunkSize++;
+ return this.header;
+ }
+
+ endChunk() {
+ if (this.chunkOffset > 0) {
+ this.fury.binaryWriter.setUint8Position(this.chunkOffset,
this.chunkSize);
+ this.chunkSize = 0;
}
- return [new KeyGeneratorClass(key, this.builder, this.scope), new
ValueGeneratorClass(value, this.builder, this.scope)];
}
+}
- writeStmt(accessor: string): string {
- const [keyMeta, valueMeta] = this.innerMeta();
- const [keyGenerator, valueGenerator] = this.innerGenerator();
- const key = this.scope.uniqueName("key");
- const value = this.scope.uniqueName("value");
+class MapAnySerializer {
+ private keySerializer: Serializer | null = null;
+ private valueSerializer: Serializer | null = null;
- return `
- ${this.builder.writer.varUInt32(`${accessor}.size`)}
- ${this.builder.writer.reserve(`${keyMeta.fixedSize +
valueMeta.fixedSize} * ${accessor}.size`)};
- for (const [${key}, ${value}] of ${accessor}.entries()) {
- ${keyGenerator.toWriteEmbed(key)}
- ${valueGenerator.toWriteEmbed(value)}
- }
- `;
+ constructor(private fury: Fury, keySerializerId: null | number,
valueSerializerId: null | number) {
+ if (keySerializerId !== null) {
+ fury.classResolver.getSerializerById(keySerializerId);
+ }
+ if (valueSerializerId !== null) {
+ fury.classResolver.getSerializerById(valueSerializerId);
+ }
}
- readStmt(accessor: (expr: string) => string, refState: RefState): string {
- const [keyGenerator, valueGenerator] = this.innerGenerator();
- const key = this.scope.uniqueName("key");
- const value = this.scope.uniqueName("value");
+ private writeHead(header: number, v: any) {
+ if (header !== 0) {
+ if (header & MapFlags.HAS_NULL) {
+ if (v === null || v === undefined) {
+ this.fury.binaryWriter.uint8(RefFlags.NullFlag);
+ }
+ }
+ if (header & MapFlags.TRACKING_REF) {
+ const keyRef = this.fury.referenceResolver.existsWriteObject(v);
+ if (keyRef !== undefined) {
+ this.fury.binaryWriter.uint8(RefFlags.RefFlag);
+ this.fury.binaryWriter.uint16(keyRef);
+ } else {
+ this.fury.binaryWriter.uint8(RefFlags.RefValueFlag);
+ }
+ } else {
+ this.fury.binaryWriter.uint8(RefFlags.NotNullValueFlag);
+ }
+ }
+ }
- const result = this.scope.uniqueName("result");
- const idx = this.scope.uniqueName("idx");
- const len = this.scope.uniqueName("len");
+ write(value: Map<any, any>) {
+ const mapChunkWriter = new MapChunkWriter(this.fury);
+ this.fury.binaryWriter.varInt32(value.size);
+ for (const [k, v] of value.entries()) {
+ const keySerializer = this.keySerializer !== null ? this.keySerializer :
this.fury.classResolver.getSerializerByData(k);
+ const valueSerializer = this.valueSerializer !== null ?
this.valueSerializer : this.fury.classResolver.getSerializerByData(v);
+ const header = mapChunkWriter.next(
+ TypeInfo.elementInfo(keySerializer!.meta.typeId!, k == null ? 1 : 0,
keySerializer!.meta.needToWriteRef ? 1 : 0),
+ TypeInfo.elementInfo(valueSerializer!.meta.typeId!, v == null ? 1 : 0,
valueSerializer!.meta.needToWriteRef ? 1 : 0)
+ );
+
+ this.writeHead(header >> 4, k);
+ keySerializer!.writeInner(k);
+ this.writeHead(header & 0b00001111, v);
+ valueSerializer!.writeInner(v);
+ }
+ mapChunkWriter.endChunk();
+ }
+
+ private readElement(header: number, serializer: Serializer | null) {
+ if (header === 0) {
+ return serializer!.readInner(false);
+ }
+ const isSame = !(header & MapFlags.NOT_SAME_TYPE);
+ const includeNone = header & MapFlags.HAS_NULL;
+ const trackingRef = header & MapFlags.TRACKING_REF;
+
+ let flag = 0;
+ if (trackingRef || includeNone) {
+ flag = this.fury.binaryReader.uint8();
+ }
+ if (!isSame) {
+ serializer =
this.fury.classResolver.getSerializerByType(this.fury.binaryReader.int16());
+ }
+ switch (flag) {
+ case RefFlags.RefValueFlag:
+ return serializer!.readInner(true);
+ case RefFlags.RefFlag:
+ return
this.fury.referenceResolver.getReadObject(this.fury.binaryReader.varUInt32());
+ case RefFlags.NullFlag:
+ return null;
+ case RefFlags.NotNullValueFlag:
+ return serializer!.readInner(false);
+ }
+ }
+
+ read(fromRef: boolean): any {
+ let count = this.fury.binaryReader.varInt32();
+ const result = new Map();
+ if (fromRef) {
+ this.fury.referenceResolver.reference(result);
+ }
+ while (count > 0) {
+ const header = this.fury.binaryReader.uint16();
+ const chunkSize = header >> 8;
+ const keyHeader = header >> 12;
+ const valueHeader = header & 0b00001111;
+
+ let keySerializer = null;
+ let valueSerializer = null;
+
+ if (!(keyHeader & MapFlags.NOT_SAME_TYPE)) {
+ keySerializer =
this.fury.classResolver.getSerializerById(this.fury.binaryReader.uint16());
+ }
+ if (!(valueHeader & MapFlags.NOT_SAME_TYPE)) {
+ valueSerializer =
this.fury.classResolver.getSerializerById(this.fury.binaryReader.uint16());
+ }
+ for (let index = 0; index < chunkSize; index++) {
+ result.set(
+ this.readElement(keyHeader, keySerializer),
+ this.readElement(valueHeader, valueSerializer)
+ );
+ count--;
+ }
+ }
+ return result;
+ }
+}
+
+export class MapSerializerGenerator extends BaseSerializerGenerator {
+ description: MapTypeDescription;
+
+ constructor(description: TypeDescription, builder: CodecBuilder, scope:
Scope) {
+ super(description, builder, scope);
+ this.description = <MapTypeDescription>description;
+ }
+
+ private innerMeta() {
+ const inner = this.description;
+ return [this.builder.meta(inner.options.key),
this.builder.meta(inner.options.value)];
+ }
+
+ writeStmt(accessor: string): string {
+ const [keyMeta, valueMeta] = this.innerMeta();
+ const anySerializer = this.builder.getExternal(MapAnySerializer.name);
return `
- const ${result} = new Map();
- ${this.maybeReference(result, refState)};
- const ${len} = ${this.builder.reader.varUInt32()};
- for (let ${idx} = 0; ${idx} < ${len}; ${idx}++) {
- let ${key};
- let ${value};
- ${keyGenerator.toReadEmbed(x => `${key} = ${x};`)}
- ${valueGenerator.toReadEmbed(x => `${value} = ${x};`)}
- ${result}.set(${key}, ${value});
- }
- ${accessor(result)}
- `;
+ new (${anySerializer})(${this.builder.furyName()}, ${keyMeta.typeId},
${valueMeta.typeId}).write(${accessor})
+ `;
+ }
+
+ readStmt(accessor: (expr: string) => string, refState: RefState): string {
+ const anySerializer = this.builder.getExternal(MapAnySerializer.name);
+ const [keyMeta, valueMeta] = this.innerMeta();
+ return accessor(`new (${anySerializer})(${this.builder.furyName()},
${keyMeta.typeId}, ${valueMeta.typeId}).read(${refState.toConditionExpr()})
+ `);
}
}
+CodegenRegistry.registerExternal(MapAnySerializer);
CodegenRegistry.register(InternalSerializerType.MAP, MapSerializerGenerator);
diff --git a/javascript/packages/fury/lib/meta.ts
b/javascript/packages/fury/lib/meta.ts
index 2e8978f9..2872b5c4 100644
--- a/javascript/packages/fury/lib/meta.ts
+++ b/javascript/packages/fury/lib/meta.ts
@@ -26,6 +26,7 @@ export type Meta = {
fixedSize: number;
needToWriteRef: boolean;
type: InternalSerializerType;
+ typeId: number | null;
};
export const getMeta = (description: TypeDescription, fury: Fury): Meta => {
@@ -36,24 +37,28 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 8,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.ARRAY:
return {
fixedSize: 7,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.TUPLE:
return {
fixedSize: 7,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.MAP:
return {
fixedSize: 7,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.BOOL:
case InternalSerializerType.INT8:
@@ -61,6 +66,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 4,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.INT16:
case InternalSerializerType.FLOAT16:
@@ -68,6 +74,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 5,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.VAR_INT32:
case InternalSerializerType.INT32:
@@ -76,6 +83,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 7,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.SLI_INT64:
case InternalSerializerType.INT64:
@@ -84,24 +92,28 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 11,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.BINARY:
return {
fixedSize: 8,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.DURATION:
return {
fixedSize: 7,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.TIMESTAMP:
return {
fixedSize: 11,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.OBJECT:
{
@@ -116,6 +128,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
}
@@ -124,6 +137,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 7,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.BOOL_ARRAY:
case InternalSerializerType.INT8_ARRAY:
@@ -137,6 +151,7 @@ export const getMeta = (description: TypeDescription, fury:
Fury): Meta => {
fixedSize: 7,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
case InternalSerializerType.ONEOF:
case InternalSerializerType.ANY:
@@ -144,12 +159,14 @@ export const getMeta = (description: TypeDescription,
fury: Fury): Meta => {
fixedSize: 11,
needToWriteRef: Boolean(fury.config.refTracking),
type,
+ typeId: null,
};
case InternalSerializerType.ENUM:
return {
fixedSize: 7,
needToWriteRef: false,
type,
+ typeId: ClassResolver.getTypeIdByInternalSerializerType(type),
};
default:
throw new Error(`Meta of ${description.type} not exists`);
diff --git a/javascript/packages/fury/lib/writer/index.ts
b/javascript/packages/fury/lib/writer/index.ts
index 5f21afd9..69ef3090 100644
--- a/javascript/packages/fury/lib/writer/index.ts
+++ b/javascript/packages/fury/lib/writer/index.ts
@@ -318,6 +318,14 @@ export class BinaryWriter {
this.dataView.setUint32(offset, v, true);
}
+ setUint8Position(offset: number, v: number) {
+ this.dataView.setUint8(offset, v);
+ }
+
+ setUint16Position(offset: number, v: number) {
+ this.dataView.setUint16(offset, v, true);
+ }
+
getByteLen() {
return this.byteLength;
}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]