zigbee-herdsman 5.0.4 → 6.0.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.
Files changed (122) hide show
  1. package/.github/dependabot.yml +3 -0
  2. package/.github/workflows/ci.yml +1 -1
  3. package/.github/workflows/typedoc.yaml +1 -1
  4. package/.release-please-manifest.json +1 -1
  5. package/CHANGELOG.md +29 -0
  6. package/biome.json +1 -1
  7. package/dist/adapter/ember/ezsp/buffalo.d.ts +0 -2
  8. package/dist/adapter/ember/ezsp/buffalo.d.ts.map +1 -1
  9. package/dist/adapter/ember/ezsp/buffalo.js +0 -4
  10. package/dist/adapter/ember/ezsp/buffalo.js.map +1 -1
  11. package/dist/adapter/ember/uart/ash.d.ts.map +1 -1
  12. package/dist/adapter/ember/uart/ash.js +0 -2
  13. package/dist/adapter/ember/uart/ash.js.map +1 -1
  14. package/dist/buffalo/buffalo.d.ts +5 -0
  15. package/dist/buffalo/buffalo.d.ts.map +1 -1
  16. package/dist/buffalo/buffalo.js +7 -0
  17. package/dist/buffalo/buffalo.js.map +1 -1
  18. package/dist/controller/controller.d.ts.map +1 -1
  19. package/dist/controller/controller.js +8 -11
  20. package/dist/controller/controller.js.map +1 -1
  21. package/dist/controller/events.d.ts +2 -1
  22. package/dist/controller/events.d.ts.map +1 -1
  23. package/dist/controller/helpers/request.d.ts.map +1 -1
  24. package/dist/controller/helpers/request.js +2 -1
  25. package/dist/controller/helpers/request.js.map +1 -1
  26. package/dist/controller/helpers/zclFrameConverter.d.ts +2 -4
  27. package/dist/controller/helpers/zclFrameConverter.d.ts.map +1 -1
  28. package/dist/controller/helpers/zclFrameConverter.js +2 -0
  29. package/dist/controller/helpers/zclFrameConverter.js.map +1 -1
  30. package/dist/controller/model/device.d.ts +13 -24
  31. package/dist/controller/model/device.d.ts.map +1 -1
  32. package/dist/controller/model/device.js +88 -129
  33. package/dist/controller/model/device.js.map +1 -1
  34. package/dist/controller/model/endpoint.d.ts +17 -16
  35. package/dist/controller/model/endpoint.d.ts.map +1 -1
  36. package/dist/controller/model/endpoint.js +31 -16
  37. package/dist/controller/model/endpoint.js.map +1 -1
  38. package/dist/controller/model/group.d.ts +6 -6
  39. package/dist/controller/model/group.d.ts.map +1 -1
  40. package/dist/controller/model/group.js +5 -3
  41. package/dist/controller/model/group.js.map +1 -1
  42. package/dist/controller/model/index.d.ts +1 -0
  43. package/dist/controller/model/index.d.ts.map +1 -1
  44. package/dist/controller/model/index.js +3 -1
  45. package/dist/controller/model/index.js.map +1 -1
  46. package/dist/controller/model/zigbeeEntity.d.ts +8 -0
  47. package/dist/controller/model/zigbeeEntity.d.ts.map +1 -0
  48. package/dist/controller/model/zigbeeEntity.js +11 -0
  49. package/dist/controller/model/zigbeeEntity.js.map +1 -0
  50. package/dist/controller/tstype.d.ts +39 -0
  51. package/dist/controller/tstype.d.ts.map +1 -1
  52. package/dist/zspec/zcl/buffaloZcl.d.ts +32 -17
  53. package/dist/zspec/zcl/buffaloZcl.d.ts.map +1 -1
  54. package/dist/zspec/zcl/buffaloZcl.js +257 -121
  55. package/dist/zspec/zcl/buffaloZcl.js.map +1 -1
  56. package/dist/zspec/zcl/definition/cluster.d.ts.map +1 -1
  57. package/dist/zspec/zcl/definition/cluster.js +156 -33
  58. package/dist/zspec/zcl/definition/cluster.js.map +1 -1
  59. package/dist/zspec/zcl/definition/clusters-typegen.d.ts +2 -0
  60. package/dist/zspec/zcl/definition/clusters-typegen.d.ts.map +1 -0
  61. package/dist/zspec/zcl/definition/clusters-typegen.js +348 -0
  62. package/dist/zspec/zcl/definition/clusters-typegen.js.map +1 -0
  63. package/dist/zspec/zcl/definition/clusters-types.d.ts +7238 -0
  64. package/dist/zspec/zcl/definition/clusters-types.d.ts.map +1 -0
  65. package/dist/zspec/zcl/definition/clusters-types.js +3 -0
  66. package/dist/zspec/zcl/definition/clusters-types.js.map +1 -0
  67. package/dist/zspec/zcl/definition/enums.d.ts +14 -6
  68. package/dist/zspec/zcl/definition/enums.d.ts.map +1 -1
  69. package/dist/zspec/zcl/definition/enums.js +15 -6
  70. package/dist/zspec/zcl/definition/enums.js.map +1 -1
  71. package/dist/zspec/zcl/definition/foundation.d.ts.map +1 -1
  72. package/dist/zspec/zcl/definition/foundation.js +43 -15
  73. package/dist/zspec/zcl/definition/foundation.js.map +1 -1
  74. package/dist/zspec/zcl/definition/tstype.d.ts +105 -11
  75. package/dist/zspec/zcl/definition/tstype.d.ts.map +1 -1
  76. package/dist/zspec/zcl/index.d.ts +1 -0
  77. package/dist/zspec/zcl/index.d.ts.map +1 -1
  78. package/dist/zspec/zcl/index.js.map +1 -1
  79. package/dist/zspec/zcl/utils.d.ts +1 -1
  80. package/dist/zspec/zcl/utils.d.ts.map +1 -1
  81. package/dist/zspec/zcl/utils.js +1 -1
  82. package/dist/zspec/zcl/utils.js.map +1 -1
  83. package/dist/zspec/zcl/zclFrame.d.ts.map +1 -1
  84. package/dist/zspec/zcl/zclFrame.js +32 -20
  85. package/dist/zspec/zcl/zclFrame.js.map +1 -1
  86. package/dist/zspec/zdo/buffaloZdo.d.ts +0 -6
  87. package/dist/zspec/zdo/buffaloZdo.d.ts.map +1 -1
  88. package/dist/zspec/zdo/buffaloZdo.js +0 -8
  89. package/dist/zspec/zdo/buffaloZdo.js.map +1 -1
  90. package/package.json +3 -3
  91. package/src/adapter/ember/ezsp/buffalo.ts +0 -5
  92. package/src/adapter/ember/uart/ash.ts +0 -2
  93. package/src/adapter/ezsp/driver/driver.ts +1 -1
  94. package/src/buffalo/buffalo.ts +8 -0
  95. package/src/controller/controller.ts +13 -16
  96. package/src/controller/events.ts +2 -1
  97. package/src/controller/greenPower.ts +4 -4
  98. package/src/controller/helpers/request.ts +3 -1
  99. package/src/controller/helpers/zclFrameConverter.ts +13 -17
  100. package/src/controller/model/device.ts +103 -148
  101. package/src/controller/model/endpoint.ts +112 -64
  102. package/src/controller/model/group.ts +33 -9
  103. package/src/controller/model/index.ts +1 -0
  104. package/src/controller/model/zigbeeEntity.ts +30 -0
  105. package/src/controller/tstype.ts +251 -16
  106. package/src/zspec/zcl/buffaloZcl.ts +323 -238
  107. package/src/zspec/zcl/definition/cluster.ts +156 -33
  108. package/src/zspec/zcl/definition/clusters-typegen.ts +588 -0
  109. package/src/zspec/zcl/definition/clusters-types.ts +7331 -0
  110. package/src/zspec/zcl/definition/enums.ts +14 -5
  111. package/src/zspec/zcl/definition/foundation.ts +43 -15
  112. package/src/zspec/zcl/definition/tstype.ts +118 -8
  113. package/src/zspec/zcl/index.ts +1 -0
  114. package/src/zspec/zcl/utils.ts +1 -1
  115. package/src/zspec/zcl/zclFrame.ts +37 -19
  116. package/src/zspec/zdo/buffaloZdo.ts +0 -9
  117. package/test/controller.test.ts +356 -896
  118. package/test/greenpower.test.ts +0 -12
  119. package/test/zcl.test.ts +13 -11
  120. package/test/zspec/zcl/buffalo.test.ts +216 -74
  121. package/test/zspec/zcl/frame.test.ts +62 -28
  122. package/test/zspec/zcl/utils.test.ts +4 -4
@@ -394,18 +394,6 @@ describe("GreenPower", () => {
394
394
  gpdCommandPayload.length,
395
395
  );
396
396
 
397
- {
398
- // mock bad frame, allows to bypass options check and validate that this errors out (trying to parse as CHANNEL_REQUEST)
399
- const alteredSecurityGpdHeader = Buffer.from(gpdHeader);
400
- alteredSecurityGpdHeader[3] = 0;
401
- alteredSecurityGpdHeader[4] = 0;
402
- const payload = makePayload(addr.sourceId, Buffer.concat([alteredSecurityGpdHeader, gpdCommandPayload]), gpdLink);
403
-
404
- expect(() => {
405
- Zcl.Frame.fromBuffer(payload.clusterID, payload.header, payload.data, {});
406
- }).toThrow('The value of "offset" is out of range. It must be >= 0 and <= 14. Received 15');
407
- }
408
-
409
397
  const payload = makePayload(addr.sourceId, Buffer.concat([gpdHeader, gpdCommandPayload]), gpdLink);
410
398
  const frame = Zcl.Frame.fromBuffer(payload.clusterID, payload.header, payload.data, {});
411
399
 
package/test/zcl.test.ts CHANGED
@@ -499,8 +499,8 @@ describe("Zcl", () => {
499
499
  "12": 0,
500
500
  "100": 1,
501
501
  "101": 0,
502
- "110": 255,
503
- "111": 255,
502
+ "110": Number.NaN,
503
+ "111": Number.NaN,
504
504
  "148": 4,
505
505
  "149": 0.14562499523162842,
506
506
  "150": 2335.614013671875,
@@ -742,7 +742,7 @@ describe("Zcl", () => {
742
742
  commandID: 16,
743
743
  frameCounter: 1253,
744
744
  options: 5280,
745
- payloadSize: 255,
745
+ payloadSize: Number.NaN,
746
746
  };
747
747
 
748
748
  expect(frame.header).toStrictEqual(header);
@@ -750,7 +750,7 @@ describe("Zcl", () => {
750
750
  });
751
751
 
752
752
  it("ZclFrame from buffer GPD with extra data", () => {
753
- const buffer = Buffer.from([0x11, 0x00, 0x00, 0xa0, 0x14, 0xfe, 0xf4, 0x46, 0x00, 0xe5, 0x04, 0x00, 0x00, 0x10, 0xff, 0x01]);
753
+ const buffer = Buffer.from([0x11, 0x00, 0x00, 0xa0, 0x14, 0xfe, 0xf4, 0x46, 0x00, 0xe5, 0x04, 0x00, 0x00, 0x10, 0x01, 0x01]);
754
754
  const frame = Zcl.Frame.fromBuffer(Zcl.Clusters.greenPower.ID, Zcl.Header.fromBuffer(buffer)!, buffer, {});
755
755
  const header = new Zcl.Header(
756
756
  {
@@ -771,7 +771,7 @@ describe("Zcl", () => {
771
771
  commandID: 16,
772
772
  frameCounter: 1253,
773
773
  options: 5280,
774
- payloadSize: 255,
774
+ payloadSize: 1,
775
775
  };
776
776
 
777
777
  expect(frame.header).toStrictEqual(header);
@@ -1951,6 +1951,7 @@ describe("Zcl", () => {
1951
1951
  expect(
1952
1952
  frame.read(BuffaloZclDataType.GPD_FRAME, {
1953
1953
  payload: {
1954
+ payloadSize: buffer.length,
1954
1955
  commandID: 0xe0,
1955
1956
  },
1956
1957
  }),
@@ -2020,6 +2021,7 @@ describe("Zcl", () => {
2020
2021
  expect(
2021
2022
  frame.read(BuffaloZclDataType.GPD_FRAME, {
2022
2023
  payload: {
2024
+ payloadSize: buffer.length,
2023
2025
  commandID: 0xe0,
2024
2026
  },
2025
2027
  }),
@@ -2051,6 +2053,7 @@ describe("Zcl", () => {
2051
2053
  expect(
2052
2054
  frame.read(BuffaloZclDataType.GPD_FRAME, {
2053
2055
  payload: {
2056
+ payloadSize: buffer.length,
2054
2057
  commandID: 0xe3,
2055
2058
  },
2056
2059
  }),
@@ -2404,7 +2407,7 @@ describe("Zcl", () => {
2404
2407
  const buffer = Buffer.alloc(4);
2405
2408
  const expected = Buffer.from([0xff, 0xff, 0xff, 0xff]);
2406
2409
  const buffalo = new BuffaloZcl(buffer);
2407
- const payload = {hours: undefined, minutes: undefined, seconds: undefined, hundredths: undefined};
2410
+ const payload = {hours: Number.NaN, minutes: Number.NaN, seconds: Number.NaN, hundredths: Number.NaN};
2408
2411
  buffalo.write(DataType.TOD, payload, {});
2409
2412
  expect(buffalo.getBuffer()).toStrictEqual(expected);
2410
2413
  });
@@ -2413,7 +2416,7 @@ describe("Zcl", () => {
2413
2416
  const buffer = Buffer.alloc(4);
2414
2417
  const expected = Buffer.from([0xff, 0xff, 0xff, 0xff]);
2415
2418
  const buffalo = new BuffaloZcl(buffer);
2416
- const payload = {year: undefined, month: undefined, dayOfMonth: undefined, dayOfWeek: undefined};
2419
+ const payload = {year: Number.NaN, month: Number.NaN, dayOfMonth: Number.NaN, dayOfWeek: Number.NaN};
2417
2420
  buffalo.write(DataType.DATE, payload, {});
2418
2421
  expect(buffalo.getBuffer()).toStrictEqual(expected);
2419
2422
  });
@@ -2779,8 +2782,7 @@ describe("Zcl", () => {
2779
2782
  const buffalo = new BuffaloZcl(Buffer.from([12, 34]));
2780
2783
  const value = buffalo.read(BuffaloZclDataType.USE_DATA_TYPE, {});
2781
2784
  expect(value).toStrictEqual(Buffer.from([12, 34]));
2782
- // @ts-expect-error protected
2783
- buffalo.position = 1;
2785
+ buffalo.setPosition(1);
2784
2786
  const value2 = buffalo.read(BuffaloZclDataType.USE_DATA_TYPE, {length: 1});
2785
2787
  expect(value2).toStrictEqual(Buffer.from([34]));
2786
2788
  });
@@ -2801,11 +2803,11 @@ describe("Zcl", () => {
2801
2803
  }).toThrow("Cannot write USE_DATA_TYPE without dataType option specified");
2802
2804
  });
2803
2805
 
2804
- it("Throws when read GPD_FRAME is missing payload.payloadSize option when payload.commandID is 0xA1", () => {
2806
+ it("Throws when read GPD_FRAME is missing payload.payloadSize option", () => {
2805
2807
  expect(() => {
2806
2808
  const buffalo = new BuffaloZcl(Buffer.alloc(1));
2807
2809
  buffalo.read(BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0xa1}});
2808
- }).toThrow("Cannot read GPD_FRAME with commandID=0xA1 without payloadSize options specified");
2810
+ }).toThrow("Cannot read GPD_FRAME without required payload options specified");
2809
2811
  });
2810
2812
 
2811
2813
  it("Throws when read LIST_THERMO_TRANSITIONS is missing required payload options", () => {
@@ -14,8 +14,7 @@ describe("ZCL Buffalo", () => {
14
14
  expect(writeSpy).toHaveBeenCalledWith(value, value.length);
15
15
  expect(writeSpy).toHaveBeenCalledTimes(1);
16
16
 
17
- // @ts-expect-error private
18
- buffalo.position = 0;
17
+ buffalo.setPosition(0);
19
18
 
20
19
  // @ts-expect-error invalid on purpose
21
20
  buffalo.write(99999, Buffer.from(value), {});
@@ -68,9 +67,11 @@ describe("ZCL Buffalo", () => {
68
67
  });
69
68
 
70
69
  it.each([
70
+ ["boolean", {value: 1, types: [Zcl.DataType.BOOLEAN]}, {position: 1, write: "writeUInt8", read: "readUInt8"}],
71
+ ["boolean", {value: 0, types: [Zcl.DataType.BOOLEAN]}, {position: 1, write: "writeUInt8", read: "readUInt8"}],
71
72
  [
72
73
  "uint8-like",
73
- {value: 250, types: [Zcl.DataType.DATA8, Zcl.DataType.BOOLEAN, Zcl.DataType.BITMAP8, Zcl.DataType.UINT8, Zcl.DataType.ENUM8]},
74
+ {value: 250, types: [Zcl.DataType.DATA8, Zcl.DataType.BITMAP8, Zcl.DataType.UINT8, Zcl.DataType.ENUM8]},
74
75
  {position: 1, write: "writeUInt8", read: "readUInt8"},
75
76
  ],
76
77
  [
@@ -150,17 +151,14 @@ describe("ZCL Buffalo", () => {
150
151
  for (const type of payload.types) {
151
152
  const buffer = Buffer.alloc(255);
152
153
  const buffalo = new BuffaloZcl(buffer);
153
- // @ts-expect-error dynamic
154
- const writeSpy = vi.spyOn(buffalo, expected.write);
155
- // @ts-expect-error dynamic
156
- const readSpy = vi.spyOn(buffalo, expected.read);
154
+ const writeSpy = vi.spyOn(buffalo, expected.write as keyof BuffaloZcl);
155
+ const readSpy = vi.spyOn(buffalo, expected.read as keyof BuffaloZcl);
157
156
 
158
157
  buffalo.write(type, payload.value, {});
159
158
  expect(writeSpy).toHaveBeenCalledTimes(1);
160
159
  expect(buffalo.getPosition()).toStrictEqual(expected.position);
161
160
 
162
- // @ts-expect-error private
163
- buffalo.position = 0;
161
+ buffalo.setPosition(0);
164
162
 
165
163
  expect(buffalo.read(type, readOptions)).toStrictEqual(payload.value);
166
164
  expect(readSpy).toHaveBeenCalledTimes(1);
@@ -168,6 +166,175 @@ describe("ZCL Buffalo", () => {
168
166
  }
169
167
  });
170
168
 
169
+ it.each([
170
+ ["boolean", {value: Number.NaN, types: [Zcl.DataType.BOOLEAN]}, {written: 0xff, position: 1, write: "writeUInt8", read: "readUInt8"}],
171
+ [
172
+ "uint8-like",
173
+ {value: Number.NaN, types: [Zcl.DataType.DATA8, Zcl.DataType.BITMAP8, Zcl.DataType.UINT8, Zcl.DataType.ENUM8]},
174
+ {written: 0xff, position: 1, write: "writeUInt8", read: "readUInt8"},
175
+ ],
176
+ [
177
+ "uint16-like",
178
+ {
179
+ value: Number.NaN,
180
+ types: [
181
+ Zcl.DataType.DATA16,
182
+ Zcl.DataType.BITMAP16,
183
+ Zcl.DataType.UINT16,
184
+ Zcl.DataType.ENUM16,
185
+ Zcl.DataType.CLUSTER_ID,
186
+ Zcl.DataType.ATTR_ID,
187
+ ],
188
+ },
189
+ {written: 0xffff, position: 2, write: "writeUInt16", read: "readUInt16"},
190
+ ],
191
+ [
192
+ "uint24-like",
193
+ {value: Number.NaN, types: [Zcl.DataType.DATA24, Zcl.DataType.BITMAP24, Zcl.DataType.UINT24]},
194
+ {written: 0xffffff, position: 3, write: "writeUInt24", read: "readUInt24"},
195
+ ],
196
+ [
197
+ "uint32-like",
198
+ {value: Number.NaN, types: [Zcl.DataType.DATA32, Zcl.DataType.BITMAP32, Zcl.DataType.UINT32, Zcl.DataType.UTC, Zcl.DataType.BAC_OID]},
199
+ {written: 0xffffffff, position: 4, write: "writeUInt32", read: "readUInt32"},
200
+ ],
201
+ [
202
+ "uint40-like",
203
+ {value: Number.NaN, types: [Zcl.DataType.DATA40, Zcl.DataType.BITMAP40, Zcl.DataType.UINT40]},
204
+ {written: 0xffffffffff, position: 5, write: "writeUInt40", read: "readUInt40"},
205
+ ],
206
+ [
207
+ "uint48-like",
208
+ {value: Number.NaN, types: [Zcl.DataType.DATA48, Zcl.DataType.BITMAP48, Zcl.DataType.UINT48]},
209
+ {written: 0xffffffffffff, position: 6, write: "writeUInt48", read: "readUInt48"},
210
+ ],
211
+ [
212
+ "uint56-like",
213
+ {value: undefined, types: [Zcl.DataType.DATA56, Zcl.DataType.BITMAP56, Zcl.DataType.UINT56]},
214
+ {written: 0xffffffffffffffn, position: 7, write: "writeUInt56", read: "readUInt56"},
215
+ ],
216
+ [
217
+ "uint64-like",
218
+ {value: undefined, types: [Zcl.DataType.DATA64, Zcl.DataType.BITMAP64, Zcl.DataType.UINT64]},
219
+ {written: 0xffffffffffffffffn, position: 8, write: "writeUInt64", read: "readUInt64"},
220
+ ],
221
+ [
222
+ "octectStr",
223
+ {value: undefined, types: [Zcl.DataType.OCTET_STR]},
224
+ {written: 0xff, valueRead: Buffer.from([]), position: 1, write: "writeUInt8", read: "readUInt8"},
225
+ ],
226
+ [
227
+ "longOctectStr",
228
+ {value: undefined, types: [Zcl.DataType.LONG_OCTET_STR]},
229
+ {written: 0xffff, valueRead: Buffer.from([]), position: 2, write: "writeUInt16", read: "readUInt16"},
230
+ ],
231
+ [
232
+ "charStr",
233
+ {value: undefined, types: [Zcl.DataType.CHAR_STR]},
234
+ {written: 0xff, valueRead: "", position: 1, write: "writeUInt8", read: "readUInt8"},
235
+ ],
236
+ [
237
+ "longCharStr",
238
+ {value: undefined, types: [Zcl.DataType.LONG_CHAR_STR]},
239
+ {written: 0xffff, valueRead: "", position: 2, write: "writeUInt16", read: "readUInt16"},
240
+ ],
241
+ [
242
+ "array",
243
+ {value: undefined, types: [Zcl.DataType.ARRAY]},
244
+ {written: 0xffff00, valueRead: [], position: 3, write: "writeUInt16", read: "readUInt16"},
245
+ ],
246
+ [
247
+ "struct",
248
+ {value: undefined, types: [Zcl.DataType.STRUCT]},
249
+ {written: 0xffff, valueRead: [], position: 2, write: "writeUInt16", read: "readUInt16"},
250
+ ],
251
+ ])("Writes & Reads non-value for %s", (_name, payload, expected) => {
252
+ for (const type of payload.types) {
253
+ const buffer = Buffer.alloc(255);
254
+ const buffalo = new BuffaloZcl(buffer);
255
+ const writeSpy = vi.spyOn(buffalo, expected.write as keyof BuffaloZcl);
256
+ const readSpy = vi.spyOn(buffalo, expected.read as keyof BuffaloZcl);
257
+
258
+ buffalo.write(type, payload.value, {});
259
+ expect(writeSpy).toHaveBeenCalledTimes(1);
260
+ expect(buffalo.getPosition()).toStrictEqual(expected.position);
261
+ const expectedWrittenBuf = Buffer.alloc(expected.position);
262
+
263
+ if (typeof expected.written === "bigint") {
264
+ if (expected.position === 7) {
265
+ const unsignedValue = expected.written < 0n ? (1n << 56n) + expected.written : expected.written;
266
+ expectedWrittenBuf.writeUIntLE(Number(unsignedValue & 0xffffffffffffn), 0, 6);
267
+ expectedWrittenBuf.writeUInt8(Number(unsignedValue >> 48n), 0 + 6);
268
+ } else {
269
+ expectedWrittenBuf.writeBigUInt64LE(expected.written, 0);
270
+ }
271
+ } else {
272
+ expectedWrittenBuf.writeUIntLE(expected.written, 0, expected.position);
273
+ }
274
+
275
+ expect(buffalo.getWritten()).toStrictEqual(expectedWrittenBuf);
276
+
277
+ buffalo.setPosition(0);
278
+
279
+ expect(buffalo.read(type, {})).toStrictEqual("valueRead" in expected ? expected.valueRead : payload.value);
280
+ expect(readSpy).toHaveBeenCalledTimes(1);
281
+ expect(buffalo.getPosition()).toStrictEqual(expected.position);
282
+ }
283
+ });
284
+
285
+ it.each([
286
+ ["int8-like", {value: Number.NaN, type: Zcl.DataType.INT8}, {written: -0x80, position: 1, write: "writeInt8", read: "readInt8"}],
287
+ ["int16-like", {value: Number.NaN, type: Zcl.DataType.INT16}, {written: -0x8000, position: 2, write: "writeInt16", read: "readInt16"}],
288
+ ["int24-like", {value: Number.NaN, type: Zcl.DataType.INT24}, {written: -0x800000, position: 3, write: "writeInt24", read: "readInt24"}],
289
+ ["int32-like", {value: Number.NaN, type: Zcl.DataType.INT32}, {written: -0x80000000, position: 4, write: "writeInt32", read: "readInt32"}],
290
+ ["int40-like", {value: Number.NaN, type: Zcl.DataType.INT40}, {written: -0x8000000000, position: 5, write: "writeInt40", read: "readInt40"}],
291
+ [
292
+ "int48-like",
293
+ {value: Number.NaN, type: Zcl.DataType.INT48},
294
+ {written: -0x800000000000, position: 6, write: "writeInt48", read: "readInt48"},
295
+ ],
296
+ [
297
+ "int56-like",
298
+ {value: undefined, type: Zcl.DataType.INT56},
299
+ {written: -0x80000000000000n, position: 7, write: "writeInt56", read: "readInt56"},
300
+ ],
301
+ [
302
+ "int64-like",
303
+ {value: undefined, type: Zcl.DataType.INT64},
304
+ {written: -0x8000000000000000n, position: 8, write: "writeInt64", read: "readInt64"},
305
+ ],
306
+ ])("Writes & Reads signed non-value for %s", (_name, payload, expected) => {
307
+ const buffer = Buffer.alloc(255);
308
+ const buffalo = new BuffaloZcl(buffer);
309
+ const writeSpy = vi.spyOn(buffalo, expected.write as keyof BuffaloZcl);
310
+ const readSpy = vi.spyOn(buffalo, expected.read as keyof BuffaloZcl);
311
+
312
+ buffalo.write(payload.type, payload.value, {});
313
+ expect(writeSpy).toHaveBeenCalledTimes(1);
314
+ expect(buffalo.getPosition()).toStrictEqual(expected.position);
315
+ const expectedWrittenBuf = Buffer.alloc(expected.position);
316
+
317
+ if (typeof expected.written === "bigint") {
318
+ if (expected.position === 7) {
319
+ const unsignedValue = expected.written < 0n ? (1n << 56n) + expected.written : expected.written;
320
+ expectedWrittenBuf.writeUIntLE(Number(unsignedValue & 0xffffffffffffn), 0, 6);
321
+ expectedWrittenBuf.writeUInt8(Number(unsignedValue >> 48n), 0 + 6);
322
+ } else {
323
+ expectedWrittenBuf.writeBigInt64LE(expected.written, 0);
324
+ }
325
+ } else {
326
+ expectedWrittenBuf.writeIntLE(expected.written, 0, expected.position);
327
+ }
328
+
329
+ expect(buffalo.getWritten()).toStrictEqual(expectedWrittenBuf);
330
+
331
+ buffalo.setPosition(0);
332
+
333
+ expect(buffalo.read(payload.type, {})).toStrictEqual("valueRead" in expected ? expected.valueRead : payload.value);
334
+ expect(readSpy).toHaveBeenCalledTimes(1);
335
+ expect(buffalo.getPosition()).toStrictEqual(expected.position);
336
+ });
337
+
171
338
  it("Reads whole buffer without length option", () => {
172
339
  const value = [1, 2, 3, 4];
173
340
  const buffer = Buffer.alloc(4);
@@ -181,8 +348,7 @@ describe("ZCL Buffalo", () => {
181
348
  expect(writeSpy).toHaveBeenCalledWith(Buffer.from(value), value.length);
182
349
  expect(buffalo.getPosition()).toStrictEqual(value.length);
183
350
 
184
- // @ts-expect-error private
185
- buffalo.position = 0;
351
+ buffalo.setPosition(0);
186
352
 
187
353
  expect(buffalo.read(Zcl.BuffaloZclDataType.BUFFER, {})).toStrictEqual(Buffer.from(value));
188
354
  expect(readSpy).toHaveBeenCalledTimes(1);
@@ -204,8 +370,7 @@ describe("ZCL Buffalo", () => {
204
370
  expect(writeSpy).toHaveBeenCalledWith(Buffer.from(value), value.length);
205
371
  expect(buffalo.getPosition()).toStrictEqual(value.length);
206
372
 
207
- // @ts-expect-error private
208
- buffalo.position = 0;
373
+ buffalo.setPosition(0);
209
374
 
210
375
  expect(buffalo.read(Zcl.BuffaloZclDataType.BUFFER, {length})).toStrictEqual(Buffer.from([value[0], value[1]]));
211
376
  expect(readSpy).toHaveBeenCalledTimes(1);
@@ -222,8 +387,7 @@ describe("ZCL Buffalo", () => {
222
387
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
223
388
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from([value.length, ...value]));
224
389
 
225
- // @ts-expect-error private
226
- buffalo.position = 0;
390
+ buffalo.setPosition(0);
227
391
 
228
392
  expect(buffalo.read(Zcl.DataType.OCTET_STR, {})).toStrictEqual(Buffer.from(value));
229
393
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
@@ -238,8 +402,7 @@ describe("ZCL Buffalo", () => {
238
402
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
239
403
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from([value.length, 0 /*length uint16*/, ...value]));
240
404
 
241
- // @ts-expect-error private
242
- buffalo.position = 0;
405
+ buffalo.setPosition(0);
243
406
 
244
407
  expect(buffalo.read(Zcl.DataType.LONG_OCTET_STR, {})).toStrictEqual(Buffer.from(value));
245
408
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
@@ -265,8 +428,7 @@ describe("ZCL Buffalo", () => {
265
428
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
266
429
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedValue));
267
430
 
268
- // @ts-expect-error private
269
- buffalo.position = 0;
431
+ buffalo.setPosition(0);
270
432
 
271
433
  expect(buffalo.read(Zcl.DataType.CHAR_STR, {})).toStrictEqual(value);
272
434
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
@@ -318,8 +480,7 @@ describe("ZCL Buffalo", () => {
318
480
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
319
481
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedValue));
320
482
 
321
- // @ts-expect-error private
322
- buffalo.position = 0;
483
+ buffalo.setPosition(0);
323
484
 
324
485
  expect(buffalo.read(Zcl.DataType.LONG_CHAR_STR, {})).toStrictEqual(value);
325
486
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
@@ -368,8 +529,7 @@ describe("ZCL Buffalo", () => {
368
529
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
369
530
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
370
531
 
371
- // @ts-expect-error private
372
- buffalo.position = 0;
532
+ buffalo.setPosition(0);
373
533
 
374
534
  expect(buffalo.read(Zcl.DataType.ARRAY, {})).toStrictEqual(payload.value.elements);
375
535
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -463,8 +623,7 @@ describe("ZCL Buffalo", () => {
463
623
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
464
624
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
465
625
 
466
- // @ts-expect-error private
467
- buffalo.position = 0;
626
+ buffalo.setPosition(0);
468
627
 
469
628
  expect(buffalo.read(Zcl.DataType.STRUCT, {})).toStrictEqual(payload.value);
470
629
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -479,8 +638,7 @@ describe("ZCL Buffalo", () => {
479
638
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
480
639
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedWritten));
481
640
 
482
- // @ts-expect-error private
483
- buffalo.position = 0;
641
+ buffalo.setPosition(0);
484
642
 
485
643
  expect(buffalo.read(Zcl.DataType.TOD, {})).toStrictEqual(value);
486
644
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
@@ -495,25 +653,21 @@ describe("ZCL Buffalo", () => {
495
653
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
496
654
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedWritten));
497
655
 
498
- // @ts-expect-error private
499
- buffalo.position = 0;
656
+ buffalo.setPosition(0);
500
657
 
501
658
  expect(buffalo.read(Zcl.DataType.DATE, {})).toStrictEqual(value);
502
659
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
503
660
  });
504
661
 
505
662
  it.each([
506
- ["octet str", {type: Zcl.DataType.OCTET_STR, position: 1, returned: Buffer.from([])}],
507
- ["char str", {type: Zcl.DataType.CHAR_STR, position: 1, returned: ""}],
508
- ["long octet str", {type: Zcl.DataType.LONG_OCTET_STR, position: 2, returned: Buffer.from([])}],
509
- ["long char str", {type: Zcl.DataType.LONG_CHAR_STR, position: 2, returned: ""}],
510
- ["array", {type: Zcl.DataType.ARRAY, position: 3, returned: []}],
511
- ["struct", {type: Zcl.DataType.STRUCT, position: 2, returned: []}],
512
663
  [
513
664
  "time of day",
514
- {type: Zcl.DataType.TOD, position: 4, returned: {hours: undefined, minutes: undefined, seconds: undefined, hundredths: undefined}},
665
+ {type: Zcl.DataType.TOD, position: 4, returned: {hours: Number.NaN, minutes: Number.NaN, seconds: Number.NaN, hundredths: Number.NaN}},
666
+ ],
667
+ [
668
+ "date",
669
+ {type: Zcl.DataType.DATE, position: 4, returned: {year: Number.NaN, month: Number.NaN, dayOfMonth: Number.NaN, dayOfWeek: Number.NaN}},
515
670
  ],
516
- ["date", {type: Zcl.DataType.DATE, position: 4, returned: {year: undefined, month: undefined, dayOfMonth: undefined, dayOfWeek: undefined}}],
517
671
  ["mi struct", {type: Zcl.BuffaloZclDataType.MI_STRUCT, position: 1, returned: {}}],
518
672
  ])("Reads Non-Value for %s", (_name, payload) => {
519
673
  const buffalo = new BuffaloZcl(Buffer.alloc(50, 0xff));
@@ -522,13 +676,12 @@ describe("ZCL Buffalo", () => {
522
676
  });
523
677
 
524
678
  it.each([
525
- // TODO: others not yet supported
526
679
  [
527
680
  "time of day",
528
681
  {
529
682
  type: Zcl.DataType.TOD,
530
683
  position: 4,
531
- value: {hours: undefined, minutes: undefined, seconds: undefined, hundredths: undefined},
684
+ value: {hours: Number.NaN, minutes: Number.NaN, seconds: Number.NaN, hundredths: Number.NaN},
532
685
  written: [0xff, 0xff, 0xff, 0xff],
533
686
  },
534
687
  ],
@@ -537,7 +690,7 @@ describe("ZCL Buffalo", () => {
537
690
  {
538
691
  type: Zcl.DataType.DATE,
539
692
  position: 4,
540
- value: {year: undefined, month: undefined, dayOfMonth: undefined, dayOfWeek: undefined},
693
+ value: {year: Number.NaN, month: Number.NaN, dayOfMonth: Number.NaN, dayOfWeek: Number.NaN},
541
694
  written: [0xff, 0xff, 0xff, 0xff],
542
695
  },
543
696
  ],
@@ -550,8 +703,8 @@ describe("ZCL Buffalo", () => {
550
703
  });
551
704
 
552
705
  it.each([
553
- ["time of day", {type: Zcl.DataType.TOD, value: {hours: 1, minutes: 2, seconds: undefined, hundredths: 3}, written: [1, 2, 0xff, 3]}],
554
- ["date", {type: Zcl.DataType.DATE, value: {year: 1901, month: 2, dayOfMonth: undefined, dayOfWeek: 3}, written: [1, 2, 0xff, 3]}],
706
+ ["time of day", {type: Zcl.DataType.TOD, value: {hours: 1, minutes: 2, seconds: Number.NaN, hundredths: 3}, written: [1, 2, 0xff, 3]}],
707
+ ["date", {type: Zcl.DataType.DATE, value: {year: 1901, month: 2, dayOfMonth: Number.NaN, dayOfWeek: 3}, written: [1, 2, 0xff, 3]}],
555
708
  ])("Writes & Reads partial Non-Value for %s", (_name, payload) => {
556
709
  const buffer = Buffer.alloc(10);
557
710
  const buffalo = new BuffaloZcl(buffer);
@@ -559,8 +712,7 @@ describe("ZCL Buffalo", () => {
559
712
  expect(buffalo.getPosition()).toStrictEqual(payload.written.length);
560
713
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(payload.written));
561
714
 
562
- // @ts-expect-error private
563
- buffalo.position = 0;
715
+ buffalo.setPosition(0);
564
716
 
565
717
  expect(buffalo.read(payload.type, {})).toStrictEqual(payload.value);
566
718
  expect(buffalo.getPosition()).toStrictEqual(payload.written.length);
@@ -573,17 +725,14 @@ describe("ZCL Buffalo", () => {
573
725
  ])("Writes & Reads Use Data Type for %s", (_name, payload, expected) => {
574
726
  const buffer = Buffer.alloc(255);
575
727
  const buffalo = new BuffaloZcl(buffer);
576
- // @ts-expect-error dynamic
577
- const writeSpy = vi.spyOn(buffalo, expected.write);
578
- // @ts-expect-error dynamic
579
- const readSpy = vi.spyOn(buffalo, expected.read);
728
+ const writeSpy = vi.spyOn(buffalo, expected.write as keyof BuffaloZcl);
729
+ const readSpy = vi.spyOn(buffalo, expected.read as keyof BuffaloZcl);
580
730
 
581
731
  buffalo.write(Zcl.BuffaloZclDataType.USE_DATA_TYPE, payload.value, {dataType: payload.type});
582
732
  expect(writeSpy).toHaveBeenCalledTimes(1);
583
733
  expect(buffalo.getPosition()).toStrictEqual(expected.position);
584
734
 
585
- // @ts-expect-error private
586
- buffalo.position = 0;
735
+ buffalo.setPosition(0);
587
736
 
588
737
  expect(buffalo.read(Zcl.BuffaloZclDataType.USE_DATA_TYPE, {dataType: payload.type})).toStrictEqual(payload.value);
589
738
  expect(readSpy).toHaveBeenCalledTimes(1);
@@ -600,15 +749,13 @@ describe("ZCL Buffalo", () => {
600
749
  expect(writeSpy).toHaveBeenCalledTimes(1);
601
750
  expect(writeSpy).toHaveBeenCalledWith(value, value.length);
602
751
 
603
- // @ts-expect-error private
604
- buffalo.position = 0;
752
+ buffalo.setPosition(0);
605
753
 
606
754
  expect(buffalo.read(Zcl.BuffaloZclDataType.USE_DATA_TYPE, {})).toStrictEqual(Buffer.from(value));
607
755
  expect(readSpy).toHaveBeenCalledTimes(1);
608
756
  expect(readSpy).toHaveBeenCalledWith(value.length);
609
757
 
610
- // @ts-expect-error private
611
- buffalo.position = 0;
758
+ buffalo.setPosition(0);
612
759
 
613
760
  expect(buffalo.read(Zcl.BuffaloZclDataType.USE_DATA_TYPE, {length: 1})).toStrictEqual(Buffer.from([value[0]]));
614
761
  expect(readSpy).toHaveBeenCalledTimes(2);
@@ -648,8 +795,7 @@ describe("ZCL Buffalo", () => {
648
795
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
649
796
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedWritten));
650
797
 
651
- // @ts-expect-error private
652
- buffalo.position = 0;
798
+ buffalo.setPosition(0);
653
799
 
654
800
  expect(buffalo.read(Zcl.BuffaloZclDataType.LIST_ZONEINFO, {length: value.length})).toStrictEqual(value);
655
801
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
@@ -684,8 +830,7 @@ describe("ZCL Buffalo", () => {
684
830
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
685
831
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
686
832
 
687
- // @ts-expect-error private
688
- buffalo.position = 0;
833
+ buffalo.setPosition(0);
689
834
 
690
835
  expect(buffalo.read(Zcl.BuffaloZclDataType.EXTENSION_FIELD_SETS, {})).toStrictEqual(payload.value);
691
836
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -760,8 +905,7 @@ describe("ZCL Buffalo", () => {
760
905
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
761
906
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
762
907
 
763
- // @ts-expect-error private
764
- buffalo.position = 0;
908
+ buffalo.setPosition(0);
765
909
 
766
910
  expect(buffalo.read(Zcl.BuffaloZclDataType.LIST_THERMO_TRANSITIONS, payload.readOptions)).toStrictEqual(payload.value);
767
911
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -817,7 +961,9 @@ describe("ZCL Buffalo", () => {
817
961
  const value = [0xff, 0x00];
818
962
  const buffalo = new BuffaloZcl(Buffer.from(value), value.length /* pos at end*/);
819
963
 
820
- expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0x1ff, payloadSize: 2}})).toStrictEqual({});
964
+ expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0x1ff, payloadSize: value.length}})).toStrictEqual({
965
+ raw: Buffer.from([]),
966
+ });
821
967
  });
822
968
 
823
969
  it("Writes commissioning", () => {
@@ -844,7 +990,7 @@ describe("ZCL Buffalo", () => {
844
990
  const value = [0xff /*device*/, 0x00 /*options*/];
845
991
  const buffalo = new BuffaloZcl(Buffer.from(value));
846
992
 
847
- expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0xe0}})).toStrictEqual({
993
+ expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {payloadSize: value.length, commandID: 0xe0}})).toStrictEqual({
848
994
  deviceID: 0xff,
849
995
  options: 0x00,
850
996
  extendedOptions: 0x00,
@@ -956,7 +1102,7 @@ describe("ZCL Buffalo", () => {
956
1102
  ];
957
1103
  const buffalo = new BuffaloZcl(Buffer.from(value));
958
1104
 
959
- expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0xe0}})).toStrictEqual({
1105
+ expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {payloadSize: value.length, commandID: 0xe0}})).toStrictEqual({
960
1106
  deviceID: 0xff,
961
1107
  options: 0x80 | 0x04,
962
1108
  extendedOptions: 0x20 | 0x40 | 0x80,
@@ -1013,7 +1159,7 @@ describe("ZCL Buffalo", () => {
1013
1159
  const value = [0xfa];
1014
1160
  const buffalo = new BuffaloZcl(Buffer.from(value));
1015
1161
 
1016
- expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0xe3}})).toStrictEqual({
1162
+ expect(buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {payloadSize: value.length, commandID: 0xe3}})).toStrictEqual({
1017
1163
  nextChannel: 0xa,
1018
1164
  nextNextChannel: 0xf,
1019
1165
  });
@@ -1080,11 +1226,11 @@ describe("ZCL Buffalo", () => {
1080
1226
  expect(buffalo.getWritten()).toStrictEqual(Buffer.alloc(0));
1081
1227
  });
1082
1228
 
1083
- it("Throws when read is missing payload.payloadSize option when payload.commandID is 0xA1", () => {
1229
+ it("Throws when read is missing payload.payloadSize option", () => {
1084
1230
  expect(() => {
1085
1231
  const buffalo = new BuffaloZcl(Buffer.alloc(1));
1086
1232
  buffalo.read(Zcl.BuffaloZclDataType.GPD_FRAME, {payload: {commandID: 0xa1}});
1087
- }).toThrow("Cannot read GPD_FRAME with commandID=0xA1 without payloadSize options specified");
1233
+ }).toThrow("Cannot read GPD_FRAME without required payload options specified");
1088
1234
  });
1089
1235
  });
1090
1236
 
@@ -1102,8 +1248,7 @@ describe("ZCL Buffalo", () => {
1102
1248
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
1103
1249
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
1104
1250
 
1105
- // @ts-expect-error private
1106
- buffalo.position = 0;
1251
+ buffalo.setPosition(0);
1107
1252
 
1108
1253
  expect(buffalo.read(Zcl.BuffaloZclDataType.STRUCTURED_SELECTOR, {})).toStrictEqual(payload.value);
1109
1254
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -1156,8 +1301,7 @@ describe("ZCL Buffalo", () => {
1156
1301
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
1157
1302
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expected.written));
1158
1303
 
1159
- // @ts-expect-error private
1160
- buffalo.position = 0;
1304
+ buffalo.setPosition(0);
1161
1305
 
1162
1306
  expect(buffalo.read(Zcl.BuffaloZclDataType.LIST_TUYA_DATAPOINT_VALUES, {})).toStrictEqual(payload.value);
1163
1307
  expect(buffalo.getPosition()).toStrictEqual(expected.written.length);
@@ -1206,8 +1350,7 @@ describe("ZCL Buffalo", () => {
1206
1350
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
1207
1351
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedWritten));
1208
1352
 
1209
- // @ts-expect-error private
1210
- buffalo.position = 0;
1353
+ buffalo.setPosition(0);
1211
1354
 
1212
1355
  expect(buffalo.read(Zcl.BuffaloZclDataType.LIST_MIBOXER_ZONES, {length: value.length})).toStrictEqual(value);
1213
1356
  expect(buffalo.getPosition()).toStrictEqual(expectedWritten.length);
@@ -1223,8 +1366,7 @@ describe("ZCL Buffalo", () => {
1223
1366
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);
1224
1367
  expect(buffalo.getWritten()).toStrictEqual(Buffer.from(expectedWritten));
1225
1368
 
1226
- // @ts-expect-error private
1227
- buffalo.position = 0;
1369
+ buffalo.setPosition(0);
1228
1370
 
1229
1371
  expect(buffalo.read(Zcl.BuffaloZclDataType.BIG_ENDIAN_UINT24, {})).toStrictEqual(value);
1230
1372
  expect(buffalo.getPosition()).toStrictEqual(expectedPosition);