@latticexyz/protocol-parser 2.0.12-main-d7526607 → 2.0.12-main-96e7bf43
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/package.json +7 -14
- package/src/abiTypesToSchema.test.ts +0 -39
- package/src/abiTypesToSchema.ts +0 -12
- package/src/common.ts +0 -52
- package/src/decodeDynamicField.test-d.ts +0 -48
- package/src/decodeDynamicField.test.ts +0 -175
- package/src/decodeDynamicField.ts +0 -145
- package/src/decodeField.ts +0 -13
- package/src/decodeKey.ts +0 -15
- package/src/decodeKeyTuple.test.ts +0 -37
- package/src/decodeKeyTuple.ts +0 -17
- package/src/decodeRecord.test.ts +0 -36
- package/src/decodeRecord.ts +0 -72
- package/src/decodeStaticField.test-d.ts +0 -40
- package/src/decodeStaticField.test.ts +0 -94
- package/src/decodeStaticField.ts +0 -145
- package/src/decodeValue.ts +0 -16
- package/src/decodeValueArgs.ts +0 -20
- package/src/encodeField.ts +0 -20
- package/src/encodeKey.ts +0 -13
- package/src/encodeKeyTuple.test.ts +0 -39
- package/src/encodeKeyTuple.ts +0 -8
- package/src/encodeLengths.test.ts +0 -16
- package/src/encodeLengths.ts +0 -12
- package/src/encodeRecord.test.ts +0 -24
- package/src/encodeRecord.ts +0 -34
- package/src/encodeValue.ts +0 -11
- package/src/encodeValueArgs.test.ts +0 -53
- package/src/encodeValueArgs.ts +0 -36
- package/src/errors.ts +0 -65
- package/src/exports/index.ts +0 -5
- package/src/exports/internal.ts +0 -31
- package/src/fieldLayoutToHex.ts +0 -15
- package/src/getKeySchema.ts +0 -9
- package/src/getSchemaTypes.ts +0 -10
- package/src/getValueSchema.ts +0 -11
- package/src/hexToEncodedLengths.test.ts +0 -35
- package/src/hexToEncodedLengths.ts +0 -34
- package/src/hexToSchema.test.ts +0 -68
- package/src/hexToSchema.ts +0 -42
- package/src/hexToTableSchema.ts +0 -12
- package/src/keySchemaToHex.ts +0 -8
- package/src/schemaIndexToAbiType.ts +0 -9
- package/src/schemaToHex.test.ts +0 -16
- package/src/schemaToHex.ts +0 -19
- package/src/staticDataLength.ts +0 -5
- package/src/valueSchemaToFieldLayoutHex.ts +0 -21
- package/src/valueSchemaToHex.ts +0 -11
package/src/decodeRecord.ts
DELETED
|
@@ -1,72 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
StaticPrimitiveType,
|
|
3
|
-
DynamicPrimitiveType,
|
|
4
|
-
staticAbiTypeToByteLength,
|
|
5
|
-
dynamicAbiTypeToDefaultValue,
|
|
6
|
-
} from "@latticexyz/schema-type/internal";
|
|
7
|
-
import { Hex } from "viem";
|
|
8
|
-
import { Schema } from "./common";
|
|
9
|
-
import { decodeDynamicField } from "./decodeDynamicField";
|
|
10
|
-
import { decodeStaticField } from "./decodeStaticField";
|
|
11
|
-
import { hexToEncodedLengths } from "./hexToEncodedLengths";
|
|
12
|
-
import { staticDataLength } from "./staticDataLength";
|
|
13
|
-
import { readHex } from "@latticexyz/common";
|
|
14
|
-
|
|
15
|
-
/** @deprecated use `decodeValue` instead */
|
|
16
|
-
export function decodeRecord(valueSchema: Schema, data: Hex): readonly (StaticPrimitiveType | DynamicPrimitiveType)[] {
|
|
17
|
-
const values: (StaticPrimitiveType | DynamicPrimitiveType)[] = [];
|
|
18
|
-
|
|
19
|
-
let bytesOffset = 0;
|
|
20
|
-
valueSchema.staticFields.forEach((fieldType) => {
|
|
21
|
-
const fieldByteLength = staticAbiTypeToByteLength[fieldType];
|
|
22
|
-
const value = decodeStaticField(fieldType, readHex(data, bytesOffset, bytesOffset + fieldByteLength));
|
|
23
|
-
bytesOffset += fieldByteLength;
|
|
24
|
-
values.push(value);
|
|
25
|
-
});
|
|
26
|
-
|
|
27
|
-
// Warn user if static data length doesn't match the value schema, because data corruption might be possible.
|
|
28
|
-
const schemaStaticDataLength = staticDataLength(valueSchema.staticFields);
|
|
29
|
-
const actualStaticDataLength = bytesOffset;
|
|
30
|
-
if (actualStaticDataLength !== schemaStaticDataLength) {
|
|
31
|
-
console.warn(
|
|
32
|
-
"Decoded static data length does not match value schema's expected static data length. Data may get corrupted. Is `getStaticByteLength` outdated?",
|
|
33
|
-
{
|
|
34
|
-
expectedLength: schemaStaticDataLength,
|
|
35
|
-
actualLength: actualStaticDataLength,
|
|
36
|
-
bytesOffset,
|
|
37
|
-
},
|
|
38
|
-
);
|
|
39
|
-
}
|
|
40
|
-
|
|
41
|
-
if (valueSchema.dynamicFields.length > 0) {
|
|
42
|
-
const dataLayout = hexToEncodedLengths(readHex(data, bytesOffset, bytesOffset + 32));
|
|
43
|
-
bytesOffset += 32;
|
|
44
|
-
|
|
45
|
-
valueSchema.dynamicFields.forEach((fieldType, i) => {
|
|
46
|
-
const dataLength = dataLayout.fieldByteLengths[i];
|
|
47
|
-
if (dataLength > 0) {
|
|
48
|
-
const value = decodeDynamicField(fieldType, readHex(data, bytesOffset, bytesOffset + dataLength));
|
|
49
|
-
bytesOffset += dataLength;
|
|
50
|
-
values.push(value);
|
|
51
|
-
} else {
|
|
52
|
-
values.push(dynamicAbiTypeToDefaultValue[fieldType]);
|
|
53
|
-
}
|
|
54
|
-
});
|
|
55
|
-
|
|
56
|
-
// Warn user if dynamic data length doesn't match the dynamic data length, because data corruption might be possible.
|
|
57
|
-
const actualDynamicDataLength = bytesOffset - 32 - actualStaticDataLength;
|
|
58
|
-
// TODO: refactor this so we don't break for bytes offsets >UINT40
|
|
59
|
-
if (BigInt(actualDynamicDataLength) !== dataLayout.totalByteLength) {
|
|
60
|
-
console.warn(
|
|
61
|
-
"Decoded dynamic data length does not match data layout's expected data length. Data may get corrupted. Did the data layout change?",
|
|
62
|
-
{
|
|
63
|
-
expectedLength: dataLayout.totalByteLength,
|
|
64
|
-
actualLength: actualDynamicDataLength,
|
|
65
|
-
bytesOffset,
|
|
66
|
-
},
|
|
67
|
-
);
|
|
68
|
-
}
|
|
69
|
-
}
|
|
70
|
-
|
|
71
|
-
return values;
|
|
72
|
-
}
|
|
@@ -1,40 +0,0 @@
|
|
|
1
|
-
import { assertType, describe, it } from "vitest";
|
|
2
|
-
import { Hex } from "viem";
|
|
3
|
-
import { decodeStaticField } from "./decodeStaticField";
|
|
4
|
-
|
|
5
|
-
describe("decodeStaticField", () => {
|
|
6
|
-
it("returns a boolean for bool ABI type", () => {
|
|
7
|
-
assertType<boolean>(decodeStaticField("bool", "0x"));
|
|
8
|
-
});
|
|
9
|
-
|
|
10
|
-
it("returns a number or bigint for uint ABI types", () => {
|
|
11
|
-
assertType<number>(decodeStaticField("uint8", "0x"));
|
|
12
|
-
assertType<number>(decodeStaticField("uint16", "0x"));
|
|
13
|
-
assertType<number>(decodeStaticField("uint32", "0x"));
|
|
14
|
-
assertType<number>(decodeStaticField("uint48", "0x"));
|
|
15
|
-
assertType<bigint>(decodeStaticField("uint56", "0x"));
|
|
16
|
-
assertType<bigint>(decodeStaticField("uint128", "0x"));
|
|
17
|
-
assertType<bigint>(decodeStaticField("uint256", "0x"));
|
|
18
|
-
});
|
|
19
|
-
|
|
20
|
-
it("returns a number or bigint for int ABI types", () => {
|
|
21
|
-
assertType<number>(decodeStaticField("int8", "0x"));
|
|
22
|
-
assertType<number>(decodeStaticField("int16", "0x"));
|
|
23
|
-
assertType<number>(decodeStaticField("int32", "0x"));
|
|
24
|
-
assertType<number>(decodeStaticField("int48", "0x"));
|
|
25
|
-
assertType<bigint>(decodeStaticField("int56", "0x"));
|
|
26
|
-
assertType<bigint>(decodeStaticField("int128", "0x"));
|
|
27
|
-
assertType<bigint>(decodeStaticField("int256", "0x"));
|
|
28
|
-
});
|
|
29
|
-
|
|
30
|
-
it("returns a hex for bytes ABI types", () => {
|
|
31
|
-
assertType<Hex>(decodeStaticField("bytes1", "0x"));
|
|
32
|
-
assertType<Hex>(decodeStaticField("bytes2", "0x"));
|
|
33
|
-
assertType<Hex>(decodeStaticField("bytes8", "0x"));
|
|
34
|
-
assertType<Hex>(decodeStaticField("bytes32", "0x"));
|
|
35
|
-
});
|
|
36
|
-
|
|
37
|
-
it("returns a hex for address ABI type", () => {
|
|
38
|
-
assertType<Hex>(decodeStaticField("address", "0x"));
|
|
39
|
-
});
|
|
40
|
-
});
|
|
@@ -1,94 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from "vitest";
|
|
2
|
-
import { decodeStaticField } from "./decodeStaticField";
|
|
3
|
-
|
|
4
|
-
describe("decodeStaticField", () => {
|
|
5
|
-
it("can decode bool", () => {
|
|
6
|
-
expect(decodeStaticField("bool", "0x00")).toBe(false);
|
|
7
|
-
expect(decodeStaticField("bool", "0x01")).toBe(true);
|
|
8
|
-
|
|
9
|
-
expect(() => decodeStaticField("bool", "0x0")).toThrow(
|
|
10
|
-
'Hex value "0x0" has length of 1, but expected length of 2 for bool type.',
|
|
11
|
-
);
|
|
12
|
-
expect(() => decodeStaticField("bool", "0x1")).toThrow(
|
|
13
|
-
'Hex value "0x1" has length of 1, but expected length of 2 for bool type.',
|
|
14
|
-
);
|
|
15
|
-
expect(() => decodeStaticField("bool", "0x000")).toThrow(
|
|
16
|
-
'Hex value "0x000" is an odd length (3). It must be an even length.',
|
|
17
|
-
);
|
|
18
|
-
expect(() => decodeStaticField("bool", "0x001")).toThrow(
|
|
19
|
-
'Hex value "0x001" is an odd length (3). It must be an even length.',
|
|
20
|
-
);
|
|
21
|
-
expect(() => decodeStaticField("bool", "0x0000")).toThrow(
|
|
22
|
-
'Hex value "0x0000" has length of 4, but expected length of 2 for bool type.',
|
|
23
|
-
);
|
|
24
|
-
expect(() => decodeStaticField("bool", "0x0001")).toThrow(
|
|
25
|
-
'Hex value "0x0001" has length of 4, but expected length of 2 for bool type.',
|
|
26
|
-
);
|
|
27
|
-
});
|
|
28
|
-
|
|
29
|
-
it("can decode uint8", () => {
|
|
30
|
-
expect(decodeStaticField("uint8", "0x00")).toBe(0);
|
|
31
|
-
expect(decodeStaticField("uint8", "0x01")).toBe(1);
|
|
32
|
-
expect(decodeStaticField("uint8", "0xff")).toBe(255);
|
|
33
|
-
});
|
|
34
|
-
|
|
35
|
-
it("can decode uint256", () => {
|
|
36
|
-
expect(decodeStaticField("uint256", "0x0000000000000000000000000000000000000000000000000000000000000000")).toBe(0n);
|
|
37
|
-
expect(decodeStaticField("uint256", "0x0000000000000000000000000000000000000000000000000000000000000001")).toBe(1n);
|
|
38
|
-
expect(decodeStaticField("uint256", "0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff")).toBe(
|
|
39
|
-
115792089237316195423570985008687907853269984665640564039457584007913129639935n,
|
|
40
|
-
);
|
|
41
|
-
expect(decodeStaticField("uint256", "0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffe")).toBe(
|
|
42
|
-
115792089237316195423570985008687907853269984665640564039457584007913129639934n,
|
|
43
|
-
);
|
|
44
|
-
});
|
|
45
|
-
|
|
46
|
-
it("can decode int8", () => {
|
|
47
|
-
expect(decodeStaticField("int8", "0x00")).toBe(0);
|
|
48
|
-
expect(decodeStaticField("int8", "0x01")).toBe(1);
|
|
49
|
-
expect(decodeStaticField("int8", "0x7f")).toBe(127);
|
|
50
|
-
expect(decodeStaticField("int8", "0x80")).toBe(-128);
|
|
51
|
-
expect(decodeStaticField("int8", "0x81")).toBe(-127);
|
|
52
|
-
expect(decodeStaticField("int8", "0xff")).toBe(-1);
|
|
53
|
-
});
|
|
54
|
-
|
|
55
|
-
it("can decode int256", () => {
|
|
56
|
-
expect(decodeStaticField("int256", "0x0000000000000000000000000000000000000000000000000000000000000000")).toBe(0n);
|
|
57
|
-
expect(decodeStaticField("int256", "0x0000000000000000000000000000000000000000000000000000000000000001")).toBe(1n);
|
|
58
|
-
expect(decodeStaticField("int256", "0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff")).toBe(
|
|
59
|
-
57896044618658097711785492504343953926634992332820282019728792003956564819967n,
|
|
60
|
-
);
|
|
61
|
-
expect(decodeStaticField("int256", "0x8000000000000000000000000000000000000000000000000000000000000000")).toBe(
|
|
62
|
-
-57896044618658097711785492504343953926634992332820282019728792003956564819968n,
|
|
63
|
-
);
|
|
64
|
-
expect(decodeStaticField("int256", "0x8000000000000000000000000000000000000000000000000000000000000001")).toBe(
|
|
65
|
-
-57896044618658097711785492504343953926634992332820282019728792003956564819967n,
|
|
66
|
-
);
|
|
67
|
-
expect(decodeStaticField("int256", "0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffff")).toBe(-1n);
|
|
68
|
-
});
|
|
69
|
-
|
|
70
|
-
it("can decode bytes", () => {
|
|
71
|
-
expect(decodeStaticField("bytes1", "0x01")).toBe("0x01");
|
|
72
|
-
expect(decodeStaticField("bytes2", "0x0001")).toBe("0x0001");
|
|
73
|
-
expect(decodeStaticField("bytes8", "0xff00ff00ff00ff00")).toBe("0xff00ff00ff00ff00");
|
|
74
|
-
expect(decodeStaticField("bytes32", "0x0000000000000000000000000000000000000000000000000000000000000001")).toBe(
|
|
75
|
-
"0x0000000000000000000000000000000000000000000000000000000000000001",
|
|
76
|
-
);
|
|
77
|
-
});
|
|
78
|
-
|
|
79
|
-
it("can decode address", () => {
|
|
80
|
-
expect(decodeStaticField("address", "0xf39fd6e51aad88f6f4ce6ab8827279cfffb92266")).toBe(
|
|
81
|
-
"0xf39Fd6e51aad88F6F4ce6aB8827279cffFb92266",
|
|
82
|
-
);
|
|
83
|
-
expect(decodeStaticField("address", "0xffffffffffffffffffffffffffffffffffffffff")).toBe(
|
|
84
|
-
"0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF",
|
|
85
|
-
);
|
|
86
|
-
|
|
87
|
-
expect(() => decodeStaticField("address", "0x00")).toThrow(
|
|
88
|
-
'Hex value "0x00" has length of 2, but expected length of 40 for address type.',
|
|
89
|
-
);
|
|
90
|
-
expect(() => decodeStaticField("address", "0xffffffffffffffffffffffffffffffffffffffffff")).toThrow(
|
|
91
|
-
'Hex value "0xffffffffffffffffffffffffffffffffffffffffff" has length of 42, but expected length of 40 for address type.',
|
|
92
|
-
);
|
|
93
|
-
});
|
|
94
|
-
});
|
package/src/decodeStaticField.ts
DELETED
|
@@ -1,145 +0,0 @@
|
|
|
1
|
-
import { Hex, getAddress, hexToBigInt, hexToBool } from "viem";
|
|
2
|
-
import { assertExhaustive } from "@latticexyz/common/utils";
|
|
3
|
-
import {
|
|
4
|
-
StaticAbiType,
|
|
5
|
-
StaticAbiTypeToPrimitiveType,
|
|
6
|
-
staticAbiTypeToByteLength,
|
|
7
|
-
staticAbiTypeToDefaultValue,
|
|
8
|
-
} from "@latticexyz/schema-type/internal";
|
|
9
|
-
import { InvalidHexLengthError, InvalidHexLengthForStaticFieldError } from "./errors";
|
|
10
|
-
|
|
11
|
-
export function decodeStaticField<
|
|
12
|
-
TAbiType extends StaticAbiType,
|
|
13
|
-
TPrimitiveType extends StaticAbiTypeToPrimitiveType<TAbiType>,
|
|
14
|
-
>(abiType: TAbiType, data: Hex): TPrimitiveType {
|
|
15
|
-
if (data.length > 3 && data.length % 2 !== 0) {
|
|
16
|
-
throw new InvalidHexLengthError(data);
|
|
17
|
-
}
|
|
18
|
-
|
|
19
|
-
const dataSize = (data.length - 2) / 2;
|
|
20
|
-
if (dataSize !== staticAbiTypeToByteLength[abiType]) {
|
|
21
|
-
throw new InvalidHexLengthForStaticFieldError(abiType, data);
|
|
22
|
-
}
|
|
23
|
-
|
|
24
|
-
switch (abiType) {
|
|
25
|
-
case "uint8":
|
|
26
|
-
case "uint16":
|
|
27
|
-
case "uint24":
|
|
28
|
-
case "uint32":
|
|
29
|
-
case "uint40":
|
|
30
|
-
case "uint48":
|
|
31
|
-
case "uint56":
|
|
32
|
-
case "uint64":
|
|
33
|
-
case "uint72":
|
|
34
|
-
case "uint80":
|
|
35
|
-
case "uint88":
|
|
36
|
-
case "uint96":
|
|
37
|
-
case "uint104":
|
|
38
|
-
case "uint112":
|
|
39
|
-
case "uint120":
|
|
40
|
-
case "uint128":
|
|
41
|
-
case "uint136":
|
|
42
|
-
case "uint144":
|
|
43
|
-
case "uint152":
|
|
44
|
-
case "uint160":
|
|
45
|
-
case "uint168":
|
|
46
|
-
case "uint176":
|
|
47
|
-
case "uint184":
|
|
48
|
-
case "uint192":
|
|
49
|
-
case "uint200":
|
|
50
|
-
case "uint208":
|
|
51
|
-
case "uint216":
|
|
52
|
-
case "uint224":
|
|
53
|
-
case "uint232":
|
|
54
|
-
case "uint240":
|
|
55
|
-
case "uint248":
|
|
56
|
-
case "uint256":
|
|
57
|
-
case "int8":
|
|
58
|
-
case "int16":
|
|
59
|
-
case "int24":
|
|
60
|
-
case "int32":
|
|
61
|
-
case "int40":
|
|
62
|
-
case "int48":
|
|
63
|
-
case "int56":
|
|
64
|
-
case "int64":
|
|
65
|
-
case "int72":
|
|
66
|
-
case "int80":
|
|
67
|
-
case "int88":
|
|
68
|
-
case "int96":
|
|
69
|
-
case "int104":
|
|
70
|
-
case "int112":
|
|
71
|
-
case "int120":
|
|
72
|
-
case "int128":
|
|
73
|
-
case "int136":
|
|
74
|
-
case "int144":
|
|
75
|
-
case "int152":
|
|
76
|
-
case "int160":
|
|
77
|
-
case "int168":
|
|
78
|
-
case "int176":
|
|
79
|
-
case "int184":
|
|
80
|
-
case "int192":
|
|
81
|
-
case "int200":
|
|
82
|
-
case "int208":
|
|
83
|
-
case "int216":
|
|
84
|
-
case "int224":
|
|
85
|
-
case "int232":
|
|
86
|
-
case "int240":
|
|
87
|
-
case "int248":
|
|
88
|
-
case "int256": {
|
|
89
|
-
const value = hexToBigInt(data, { signed: abiType.startsWith("int") });
|
|
90
|
-
const defaultValueType = typeof staticAbiTypeToDefaultValue[abiType];
|
|
91
|
-
if (defaultValueType === "number") {
|
|
92
|
-
return Number(value) as TPrimitiveType;
|
|
93
|
-
}
|
|
94
|
-
if (defaultValueType === "bigint") {
|
|
95
|
-
return value as TPrimitiveType;
|
|
96
|
-
}
|
|
97
|
-
throw new Error(`Unexpected default value type (${defaultValueType}) for ABI type (${abiType})`);
|
|
98
|
-
}
|
|
99
|
-
|
|
100
|
-
case "bytes1":
|
|
101
|
-
case "bytes2":
|
|
102
|
-
case "bytes3":
|
|
103
|
-
case "bytes4":
|
|
104
|
-
case "bytes5":
|
|
105
|
-
case "bytes6":
|
|
106
|
-
case "bytes7":
|
|
107
|
-
case "bytes8":
|
|
108
|
-
case "bytes9":
|
|
109
|
-
case "bytes10":
|
|
110
|
-
case "bytes11":
|
|
111
|
-
case "bytes12":
|
|
112
|
-
case "bytes13":
|
|
113
|
-
case "bytes14":
|
|
114
|
-
case "bytes15":
|
|
115
|
-
case "bytes16":
|
|
116
|
-
case "bytes17":
|
|
117
|
-
case "bytes18":
|
|
118
|
-
case "bytes19":
|
|
119
|
-
case "bytes20":
|
|
120
|
-
case "bytes21":
|
|
121
|
-
case "bytes22":
|
|
122
|
-
case "bytes23":
|
|
123
|
-
case "bytes24":
|
|
124
|
-
case "bytes25":
|
|
125
|
-
case "bytes26":
|
|
126
|
-
case "bytes27":
|
|
127
|
-
case "bytes28":
|
|
128
|
-
case "bytes29":
|
|
129
|
-
case "bytes30":
|
|
130
|
-
case "bytes31":
|
|
131
|
-
case "bytes32": {
|
|
132
|
-
return data as TPrimitiveType;
|
|
133
|
-
}
|
|
134
|
-
|
|
135
|
-
case "bool": {
|
|
136
|
-
return hexToBool(data) as TPrimitiveType;
|
|
137
|
-
}
|
|
138
|
-
|
|
139
|
-
case "address": {
|
|
140
|
-
return getAddress(data) as TPrimitiveType;
|
|
141
|
-
}
|
|
142
|
-
}
|
|
143
|
-
|
|
144
|
-
return assertExhaustive(abiType, `Unsupported static ABI type: ${abiType}`);
|
|
145
|
-
}
|
package/src/decodeValue.ts
DELETED
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import { isStaticAbiType, isDynamicAbiType } from "@latticexyz/schema-type/internal";
|
|
2
|
-
import { Hex } from "viem";
|
|
3
|
-
import { SchemaToPrimitives, ValueSchema } from "./common";
|
|
4
|
-
import { decodeRecord } from "./decodeRecord";
|
|
5
|
-
|
|
6
|
-
export function decodeValue<TSchema extends ValueSchema>(valueSchema: TSchema, data: Hex): SchemaToPrimitives<TSchema> {
|
|
7
|
-
const staticFields = Object.values(valueSchema).filter(isStaticAbiType);
|
|
8
|
-
const dynamicFields = Object.values(valueSchema).filter(isDynamicAbiType);
|
|
9
|
-
|
|
10
|
-
// TODO: refactor and move all decodeRecord logic into this method so we can delete decodeRecord
|
|
11
|
-
const valueTuple = decodeRecord({ staticFields, dynamicFields }, data);
|
|
12
|
-
|
|
13
|
-
return Object.fromEntries(
|
|
14
|
-
Object.keys(valueSchema).map((name, i) => [name, valueTuple[i]]),
|
|
15
|
-
) as SchemaToPrimitives<TSchema>;
|
|
16
|
-
}
|
package/src/decodeValueArgs.ts
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
import { concatHex } from "viem";
|
|
2
|
-
import { isStaticAbiType } from "@latticexyz/schema-type/internal";
|
|
3
|
-
import { SchemaToPrimitives, ValueArgs, ValueSchema } from "./common";
|
|
4
|
-
import { decodeValue } from "./decodeValue";
|
|
5
|
-
import { staticDataLength } from "./staticDataLength";
|
|
6
|
-
import { readHex } from "@latticexyz/common";
|
|
7
|
-
|
|
8
|
-
export function decodeValueArgs<TSchema extends ValueSchema>(
|
|
9
|
-
valueSchema: TSchema,
|
|
10
|
-
{ staticData, encodedLengths, dynamicData }: ValueArgs,
|
|
11
|
-
): SchemaToPrimitives<TSchema> {
|
|
12
|
-
return decodeValue(
|
|
13
|
-
valueSchema,
|
|
14
|
-
concatHex([
|
|
15
|
-
readHex(staticData, 0, staticDataLength(Object.values(valueSchema).filter(isStaticAbiType))),
|
|
16
|
-
encodedLengths,
|
|
17
|
-
dynamicData,
|
|
18
|
-
]),
|
|
19
|
-
);
|
|
20
|
-
}
|
package/src/encodeField.ts
DELETED
|
@@ -1,20 +0,0 @@
|
|
|
1
|
-
import { SchemaAbiType, arrayToStaticAbiType, isArrayAbiType } from "@latticexyz/schema-type/internal";
|
|
2
|
-
import { AbiParameterToPrimitiveType } from "abitype";
|
|
3
|
-
import { Hex, encodePacked } from "viem";
|
|
4
|
-
|
|
5
|
-
export function encodeField<TSchemaAbiType extends SchemaAbiType>(
|
|
6
|
-
fieldType: TSchemaAbiType,
|
|
7
|
-
value: AbiParameterToPrimitiveType<{ type: TSchemaAbiType }>,
|
|
8
|
-
): Hex {
|
|
9
|
-
if (isArrayAbiType(fieldType) && Array.isArray(value)) {
|
|
10
|
-
const staticFieldType = arrayToStaticAbiType(fieldType);
|
|
11
|
-
// TODO: we can remove conditional once this is fixed: https://github.com/wagmi-dev/viem/pull/1147
|
|
12
|
-
return value.length === 0
|
|
13
|
-
? "0x"
|
|
14
|
-
: encodePacked(
|
|
15
|
-
value.map(() => staticFieldType),
|
|
16
|
-
value,
|
|
17
|
-
);
|
|
18
|
-
}
|
|
19
|
-
return encodePacked([fieldType], [value]);
|
|
20
|
-
}
|
package/src/encodeKey.ts
DELETED
|
@@ -1,13 +0,0 @@
|
|
|
1
|
-
import { isStaticAbiType } from "@latticexyz/schema-type/internal";
|
|
2
|
-
import { Hex } from "viem";
|
|
3
|
-
import { SchemaToPrimitives, KeySchema } from "./common";
|
|
4
|
-
import { encodeKeyTuple } from "./encodeKeyTuple";
|
|
5
|
-
|
|
6
|
-
export function encodeKey<TSchema extends KeySchema>(
|
|
7
|
-
keySchema: TSchema,
|
|
8
|
-
key: SchemaToPrimitives<TSchema>,
|
|
9
|
-
): readonly Hex[] {
|
|
10
|
-
const staticFields = Object.values(keySchema).filter(isStaticAbiType);
|
|
11
|
-
// TODO: refactor and move all encodeKeyTuple logic into this method so we can delete encodeKeyTuple
|
|
12
|
-
return encodeKeyTuple({ staticFields, dynamicFields: [] }, Object.values(key));
|
|
13
|
-
}
|
|
@@ -1,39 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from "vitest";
|
|
2
|
-
import { encodeKeyTuple } from "./encodeKeyTuple";
|
|
3
|
-
|
|
4
|
-
describe("encodeKeyTuple", () => {
|
|
5
|
-
it("can encode bool key tuple", () => {
|
|
6
|
-
expect(encodeKeyTuple({ staticFields: ["bool"], dynamicFields: [] }, [false])).toStrictEqual([
|
|
7
|
-
"0x0000000000000000000000000000000000000000000000000000000000000000",
|
|
8
|
-
]);
|
|
9
|
-
expect(
|
|
10
|
-
encodeKeyTuple(
|
|
11
|
-
{
|
|
12
|
-
staticFields: ["bool"],
|
|
13
|
-
dynamicFields: [],
|
|
14
|
-
},
|
|
15
|
-
[true],
|
|
16
|
-
),
|
|
17
|
-
).toStrictEqual(["0x0000000000000000000000000000000000000000000000000000000000000001"]);
|
|
18
|
-
});
|
|
19
|
-
|
|
20
|
-
it("can encode complex key tuple", () => {
|
|
21
|
-
expect(
|
|
22
|
-
encodeKeyTuple({ staticFields: ["uint256", "int32", "bytes16", "address", "bool", "int8"], dynamicFields: [] }, [
|
|
23
|
-
42n,
|
|
24
|
-
-42,
|
|
25
|
-
"0x12340000000000000000000000000000",
|
|
26
|
-
"0xFFfFfFffFFfffFFfFFfFFFFFffFFFffffFfFFFfF",
|
|
27
|
-
true,
|
|
28
|
-
3,
|
|
29
|
-
]),
|
|
30
|
-
).toStrictEqual([
|
|
31
|
-
"0x000000000000000000000000000000000000000000000000000000000000002a",
|
|
32
|
-
"0xffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffd6",
|
|
33
|
-
"0x1234000000000000000000000000000000000000000000000000000000000000",
|
|
34
|
-
"0x000000000000000000000000ffffffffffffffffffffffffffffffffffffffff",
|
|
35
|
-
"0x0000000000000000000000000000000000000000000000000000000000000001",
|
|
36
|
-
"0x0000000000000000000000000000000000000000000000000000000000000003",
|
|
37
|
-
]);
|
|
38
|
-
});
|
|
39
|
-
});
|
package/src/encodeKeyTuple.ts
DELETED
|
@@ -1,8 +0,0 @@
|
|
|
1
|
-
import { StaticPrimitiveType } from "@latticexyz/schema-type/internal";
|
|
2
|
-
import { Hex, encodeAbiParameters } from "viem";
|
|
3
|
-
import { Schema } from "./common";
|
|
4
|
-
|
|
5
|
-
/** @deprecated use `encodeKey` instead */
|
|
6
|
-
export function encodeKeyTuple(keySchema: Schema, keyTuple: StaticPrimitiveType[]): Hex[] {
|
|
7
|
-
return keyTuple.map((key, index) => encodeAbiParameters([{ type: keySchema.staticFields[index] }], [key]));
|
|
8
|
-
}
|
|
@@ -1,16 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from "vitest";
|
|
2
|
-
import { encodeLengths } from "./encodeLengths";
|
|
3
|
-
|
|
4
|
-
describe("encodeLengths", () => {
|
|
5
|
-
it("can encode empty tuple", () => {
|
|
6
|
-
expect(encodeLengths([])).toMatchInlineSnapshot(
|
|
7
|
-
'"0x0000000000000000000000000000000000000000000000000000000000000000"',
|
|
8
|
-
);
|
|
9
|
-
});
|
|
10
|
-
|
|
11
|
-
it("can encode bool key tuple", () => {
|
|
12
|
-
expect(encodeLengths(["0x1234", "0x12345678"])).toMatchInlineSnapshot(
|
|
13
|
-
'"0x0000000000000000000000000000000000000004000000000200000000000006"',
|
|
14
|
-
);
|
|
15
|
-
});
|
|
16
|
-
});
|
package/src/encodeLengths.ts
DELETED
|
@@ -1,12 +0,0 @@
|
|
|
1
|
-
import { Hex, concatHex, padHex, size } from "viem";
|
|
2
|
-
import { encodeField } from "./encodeField";
|
|
3
|
-
|
|
4
|
-
export function encodeLengths(values: Hex[]): Hex {
|
|
5
|
-
const byteLengths = values.map(size).reverse();
|
|
6
|
-
const totalByteLength = byteLengths.reduce((total, length) => total + BigInt(length), 0n);
|
|
7
|
-
|
|
8
|
-
return padHex(
|
|
9
|
-
concatHex([...byteLengths.map((length) => encodeField("uint40", length)), encodeField("uint56", totalByteLength)]),
|
|
10
|
-
{ size: 32, dir: "left" },
|
|
11
|
-
);
|
|
12
|
-
}
|
package/src/encodeRecord.test.ts
DELETED
|
@@ -1,24 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from "vitest";
|
|
2
|
-
import { encodeRecord } from "./encodeRecord";
|
|
3
|
-
|
|
4
|
-
describe("encodeRecord", () => {
|
|
5
|
-
it("can encode a value schema and record values to hex", () => {
|
|
6
|
-
const valueSchema = { staticFields: ["uint32", "uint128"], dynamicFields: ["uint32[]", "string"] } as const;
|
|
7
|
-
const hex = encodeRecord(valueSchema, [1, 2n, [3, 4], "some string"]);
|
|
8
|
-
expect(hex).toBe(
|
|
9
|
-
"0x0000000100000000000000000000000000000002000000000000000000000000000000000000000b0000000008000000000000130000000300000004736f6d6520737472696e67",
|
|
10
|
-
);
|
|
11
|
-
});
|
|
12
|
-
|
|
13
|
-
it("should not include the packed dynamic lengths if there are no dynamic fields", () => {
|
|
14
|
-
const valueSchema = { staticFields: ["uint32", "uint128"], dynamicFields: [] } as const;
|
|
15
|
-
const hex = encodeRecord(valueSchema, [1, 2n]);
|
|
16
|
-
expect(hex).toBe("0x0000000100000000000000000000000000000002");
|
|
17
|
-
});
|
|
18
|
-
|
|
19
|
-
it("can encode an array to hex", () => {
|
|
20
|
-
const valueSchema = { staticFields: [], dynamicFields: ["uint32[]"] } as const;
|
|
21
|
-
const hex = encodeRecord(valueSchema, [[42]]);
|
|
22
|
-
expect(hex).toBe("0x00000000000000000000000000000000000000000000000004000000000000040000002a");
|
|
23
|
-
});
|
|
24
|
-
});
|
package/src/encodeRecord.ts
DELETED
|
@@ -1,34 +0,0 @@
|
|
|
1
|
-
import { StaticPrimitiveType, DynamicPrimitiveType } from "@latticexyz/schema-type/internal";
|
|
2
|
-
import { Hex } from "viem";
|
|
3
|
-
import { encodeField } from "./encodeField";
|
|
4
|
-
import { Schema } from "./common";
|
|
5
|
-
|
|
6
|
-
/** @deprecated use `encodeValue` instead */
|
|
7
|
-
export function encodeRecord(
|
|
8
|
-
valueSchema: Schema,
|
|
9
|
-
values: readonly (StaticPrimitiveType | DynamicPrimitiveType)[],
|
|
10
|
-
): Hex {
|
|
11
|
-
const staticValues = values.slice(0, valueSchema.staticFields.length) as readonly StaticPrimitiveType[];
|
|
12
|
-
const dynamicValues = values.slice(valueSchema.staticFields.length) as readonly DynamicPrimitiveType[];
|
|
13
|
-
|
|
14
|
-
const staticData = staticValues
|
|
15
|
-
.map((value, i) => encodeField(valueSchema.staticFields[i], value).replace(/^0x/, ""))
|
|
16
|
-
.join("");
|
|
17
|
-
|
|
18
|
-
if (valueSchema.dynamicFields.length === 0) return `0x${staticData}`;
|
|
19
|
-
|
|
20
|
-
const dynamicDataItems = dynamicValues.map((value, i) =>
|
|
21
|
-
encodeField(valueSchema.dynamicFields[i], value).replace(/^0x/, ""),
|
|
22
|
-
);
|
|
23
|
-
|
|
24
|
-
const dynamicFieldByteLengths = dynamicDataItems.map((value) => value.length / 2).reverse();
|
|
25
|
-
const dynamicTotalByteLength = dynamicFieldByteLengths.reduce((total, length) => total + BigInt(length), 0n);
|
|
26
|
-
|
|
27
|
-
const dynamicData = dynamicDataItems.join("");
|
|
28
|
-
|
|
29
|
-
const encodedLengths = `${dynamicFieldByteLengths
|
|
30
|
-
.map((length) => encodeField("uint40", length).replace(/^0x/, ""))
|
|
31
|
-
.join("")}${encodeField("uint56", dynamicTotalByteLength).replace(/^0x/, "")}`.padStart(64, "0");
|
|
32
|
-
|
|
33
|
-
return `0x${staticData}${encodedLengths}${dynamicData}`;
|
|
34
|
-
}
|
package/src/encodeValue.ts
DELETED
|
@@ -1,11 +0,0 @@
|
|
|
1
|
-
import { Hex, concatHex } from "viem";
|
|
2
|
-
import { SchemaToPrimitives, ValueSchema } from "./common";
|
|
3
|
-
import { encodeValueArgs } from "./encodeValueArgs";
|
|
4
|
-
|
|
5
|
-
export function encodeValue<TSchema extends ValueSchema>(
|
|
6
|
-
valueSchema: TSchema,
|
|
7
|
-
value: SchemaToPrimitives<TSchema>,
|
|
8
|
-
): Hex {
|
|
9
|
-
const { staticData, encodedLengths, dynamicData } = encodeValueArgs(valueSchema, value);
|
|
10
|
-
return concatHex([staticData, encodedLengths, dynamicData]);
|
|
11
|
-
}
|
|
@@ -1,53 +0,0 @@
|
|
|
1
|
-
import { describe, expect, it } from "vitest";
|
|
2
|
-
import { encodeValueArgs } from "./encodeValueArgs";
|
|
3
|
-
import { stringToHex } from "viem";
|
|
4
|
-
|
|
5
|
-
describe("encodeValueArgs", () => {
|
|
6
|
-
it("can encode record value to hex", () => {
|
|
7
|
-
const valueSchema = {
|
|
8
|
-
entityId: "bytes32",
|
|
9
|
-
exists: "bool",
|
|
10
|
-
playerName: "string",
|
|
11
|
-
badges: "uint256[]",
|
|
12
|
-
} as const;
|
|
13
|
-
|
|
14
|
-
const result = encodeValueArgs(valueSchema, {
|
|
15
|
-
entityId: stringToHex("hello", { size: 32 }),
|
|
16
|
-
exists: true,
|
|
17
|
-
playerName: "henry",
|
|
18
|
-
badges: [42n],
|
|
19
|
-
});
|
|
20
|
-
|
|
21
|
-
expect(result).toMatchInlineSnapshot(`
|
|
22
|
-
{
|
|
23
|
-
"dynamicData": "0x68656e7279000000000000000000000000000000000000000000000000000000000000002a",
|
|
24
|
-
"encodedLengths": "0x0000000000000000000000000000000000000020000000000500000000000025",
|
|
25
|
-
"staticData": "0x68656c6c6f00000000000000000000000000000000000000000000000000000001",
|
|
26
|
-
}
|
|
27
|
-
`);
|
|
28
|
-
});
|
|
29
|
-
|
|
30
|
-
it("encodes record when key order of value and valueSchema do not match", () => {
|
|
31
|
-
const valueSchema = {
|
|
32
|
-
entityId: "bytes32",
|
|
33
|
-
playerName: "string",
|
|
34
|
-
exists: "bool",
|
|
35
|
-
badges: "uint256[]",
|
|
36
|
-
} as const;
|
|
37
|
-
|
|
38
|
-
const result = encodeValueArgs(valueSchema, {
|
|
39
|
-
exists: true,
|
|
40
|
-
playerName: "henry",
|
|
41
|
-
entityId: stringToHex("hello", { size: 32 }),
|
|
42
|
-
badges: [42n],
|
|
43
|
-
});
|
|
44
|
-
|
|
45
|
-
expect(result).toMatchInlineSnapshot(`
|
|
46
|
-
{
|
|
47
|
-
"dynamicData": "0x68656e7279000000000000000000000000000000000000000000000000000000000000002a",
|
|
48
|
-
"encodedLengths": "0x0000000000000000000000000000000000000020000000000500000000000025",
|
|
49
|
-
"staticData": "0x68656c6c6f00000000000000000000000000000000000000000000000000000001",
|
|
50
|
-
}
|
|
51
|
-
`);
|
|
52
|
-
});
|
|
53
|
-
});
|
package/src/encodeValueArgs.ts
DELETED
|
@@ -1,36 +0,0 @@
|
|
|
1
|
-
import {
|
|
2
|
-
StaticPrimitiveType,
|
|
3
|
-
DynamicPrimitiveType,
|
|
4
|
-
isStaticAbiType,
|
|
5
|
-
isDynamicAbiType,
|
|
6
|
-
StaticAbiType,
|
|
7
|
-
DynamicAbiType,
|
|
8
|
-
} from "@latticexyz/schema-type/internal";
|
|
9
|
-
import { concatHex } from "viem";
|
|
10
|
-
import { encodeField } from "./encodeField";
|
|
11
|
-
import { SchemaToPrimitives, ValueArgs, ValueSchema } from "./common";
|
|
12
|
-
import { encodeLengths } from "./encodeLengths";
|
|
13
|
-
|
|
14
|
-
export function encodeValueArgs<TSchema extends ValueSchema>(
|
|
15
|
-
valueSchema: TSchema,
|
|
16
|
-
value: SchemaToPrimitives<TSchema>,
|
|
17
|
-
): ValueArgs {
|
|
18
|
-
const valueSchemaEntries = Object.entries(valueSchema);
|
|
19
|
-
const staticFields = valueSchemaEntries.filter(([, type]) => isStaticAbiType(type)) as [string, StaticAbiType][];
|
|
20
|
-
const dynamicFields = valueSchemaEntries.filter(([, type]) => isDynamicAbiType(type)) as [string, DynamicAbiType][];
|
|
21
|
-
// TODO: validate <=5 dynamic fields
|
|
22
|
-
// TODO: validate <=28 total fields
|
|
23
|
-
|
|
24
|
-
const encodedStaticValues = staticFields.map(([name, type]) => encodeField(type, value[name] as StaticPrimitiveType));
|
|
25
|
-
const encodedDynamicValues = dynamicFields.map(([name, type]) =>
|
|
26
|
-
encodeField(type, value[name] as DynamicPrimitiveType),
|
|
27
|
-
);
|
|
28
|
-
|
|
29
|
-
const encodedLengths = encodeLengths(encodedDynamicValues);
|
|
30
|
-
|
|
31
|
-
return {
|
|
32
|
-
staticData: concatHex(encodedStaticValues),
|
|
33
|
-
encodedLengths,
|
|
34
|
-
dynamicData: concatHex(encodedDynamicValues),
|
|
35
|
-
};
|
|
36
|
-
}
|