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
@@ -177,7 +177,7 @@ const GLOBAL_RSP_FRAME_BUFFER = Buffer.concat([
177
177
  GLOBAL_RSP_HEADER_BUFFER,
178
178
  Buffer.from([...uint16To8Array(256), Zcl.Status.SUCCESS, Zcl.DataType.ENUM8, 127]),
179
179
  ]);
180
- const GLOBAL_RSP_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":0,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":78,"commandIdentifier":1},"payload":[{"attrId":256,"status":0,"dataType":48,"attrData":127}],"command":{"ID":1,"name":"readRsp","parameters":[{"name":"attrId","type":33},{"name":"status","type":32},{"name":"dataType","type":32,"conditions":[{"type":"statusEquals","value":0}]},{"name":"attrData","type":1000,"conditions":[{"type":"statusEquals","value":0}]}]}}`;
180
+ const GLOBAL_RSP_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":0,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":78,"commandIdentifier":1},"payload":[{"attrId":256,"status":0,"dataType":48,"attrData":127}],"command":{"ID":1,"name":"readRsp","parameters":[{"name":"attrId","type":33},{"name":"status","type":32},{"name":"dataType","type":32,"conditions":[{"type":"fieldEquals","field":"status","value":0}]},{"name":"attrData","type":1000,"conditions":[{"type":"fieldEquals","field":"status","value":0}]}]}}`;
181
181
 
182
182
  /** Frame of Global type with no payload */
183
183
  const GLOBAL_FRAME_NO_PAYLOAD = Zcl.Frame.create(
@@ -212,7 +212,7 @@ const GLOBAL_CONDITION_FRAME_BUFFER = Buffer.concat([
212
212
  GLOBAL_CONDITION_HEADER_BUFFER,
213
213
  Buffer.from([Zcl.Direction.SERVER_TO_CLIENT, ...uint16To8Array(256), ...uint16To8Array(10000)]),
214
214
  ]);
215
- const GLOBAL_CONDITION_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":0,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":78,"commandIdentifier":6},"payload":[{"direction":1,"attrId":256,"timeout":10000}],"command":{"ID":6,"name":"configReport","parameters":[{"name":"direction","type":32},{"name":"attrId","type":33},{"name":"dataType","type":32,"conditions":[{"type":"directionEquals","value":0}]},{"name":"minRepIntval","type":33,"conditions":[{"type":"directionEquals","value":0}]},{"name":"maxRepIntval","type":33,"conditions":[{"type":"directionEquals","value":0}]},{"name":"repChange","type":1000,"conditions":[{"type":"directionEquals","value":0},{"type":"dataTypeValueTypeEquals","value":"ANALOG"}]},{"name":"timeout","type":33,"conditions":[{"type":"directionEquals","value":1}]}],"response":7}}`;
215
+ const GLOBAL_CONDITION_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":0,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":78,"commandIdentifier":6},"payload":[{"direction":1,"attrId":256,"timeout":10000}],"command":{"ID":6,"name":"configReport","parameters":[{"name":"direction","type":32},{"name":"attrId","type":33},{"name":"dataType","type":32,"conditions":[{"type":"fieldEquals","field":"direction","value":0}]},{"name":"minRepIntval","type":33,"conditions":[{"type":"fieldEquals","field":"direction","value":0}]},{"name":"maxRepIntval","type":33,"conditions":[{"type":"fieldEquals","field":"direction","value":0}]},{"name":"repChange","type":1000,"conditions":[{"type":"fieldEquals","field":"direction","value":0},{"type":"dataTypeValueTypeEquals","value":"ANALOG"}]},{"name":"timeout","type":33,"conditions":[{"type":"fieldEquals","field":"direction","value":1}]}],"response":7}}`;
216
216
 
217
217
  /** Frame of Specific type */
218
218
  const SPECIFIC_FRAME = Zcl.Frame.create(
@@ -260,7 +260,7 @@ const SPECIFIC_CONDITION_FRAME = Zcl.Frame.create(
260
260
  SPECIFIC_CONDITION_HEADER.frameControl.reservedBits,
261
261
  );
262
262
  const SPECIFIC_CONDITION_FRAME_BUFFER = Buffer.concat([SPECIFIC_CONDITION_HEADER_BUFFER, Buffer.from([149])]);
263
- const SPECIFIC_CONDITION_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":1,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":45,"commandIdentifier":2},"payload":{"status":149},"command":{"ID":2,"parameters":[{"name":"status","type":32},{"name":"manufacturerCode","type":33,"conditions":[{"type":"statusEquals","value":0}]},{"name":"imageType","type":33,"conditions":[{"type":"statusEquals","value":0}]},{"name":"fileVersion","type":35,"conditions":[{"type":"statusEquals","value":0}]},{"name":"imageSize","type":35,"conditions":[{"type":"statusEquals","value":0}]}],"name":"queryNextImageResponse"}}`;
263
+ const SPECIFIC_CONDITION_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"frameType":1,"direction":1,"disableDefaultResponse":false,"manufacturerSpecific":false},"transactionSequenceNumber":45,"commandIdentifier":2},"payload":{"status":149},"command":{"ID":2,"parameters":[{"name":"status","type":32},{"name":"manufacturerCode","type":33,"conditions":[{"type":"fieldEquals","field":"status","value":0}]},{"name":"imageType","type":33,"conditions":[{"type":"fieldEquals","field":"status","value":0}]},{"name":"fileVersion","type":35,"conditions":[{"type":"fieldEquals","field":"status","value":0}]},{"name":"imageSize","type":35,"conditions":[{"type":"fieldEquals","field":"status","value":0}]}],"name":"queryNextImageResponse"}}`;
264
264
 
265
265
  /** Frame manufacturer-specific */
266
266
  const MANUF_SPE_FRAME = Zcl.Frame.create(
@@ -280,36 +280,11 @@ const MANUF_SPE_FRAME_STRING = `{"header":{"frameControl":{"reservedBits":0,"fra
280
280
 
281
281
  describe("ZCL Frame", () => {
282
282
  describe("Validates Parameter Condition", () => {
283
- it("STATUS_EQUAL", () => {
284
- expect(Zcl.Frame.conditionsValid(Zcl.Foundation.readRsp.parameters[2], {status: 0}, undefined)).toBeTruthy();
285
- expect(Zcl.Frame.conditionsValid(Zcl.Foundation.readRsp.parameters[2], {status: 1}, undefined)).toBeFalsy();
286
- });
287
-
288
- it("STATUS_NOT_EQUAL", () => {
289
- expect(Zcl.Frame.conditionsValid(Zcl.Foundation.writeRsp.parameters[1], {status: 1}, undefined)).toBeTruthy();
290
- expect(Zcl.Frame.conditionsValid(Zcl.Foundation.writeRsp.parameters[1], {status: 0}, undefined)).toBeFalsy();
291
- });
292
-
293
283
  it("MINIMUM_REMAINING_BUFFER_BYTES", () => {
294
284
  expect(Zcl.Frame.conditionsValid(Zcl.Foundation.configReportRsp.parameters[1], {status: 1}, 3)).toBeTruthy();
295
285
  expect(Zcl.Frame.conditionsValid(Zcl.Foundation.configReportRsp.parameters[1], {status: 1}, 2)).toBeFalsy();
296
286
  });
297
287
 
298
- it("DIRECTION_EQUAL", () => {
299
- expect(
300
- Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[2], {direction: Zcl.Direction.CLIENT_TO_SERVER}, undefined),
301
- ).toBeTruthy();
302
- expect(
303
- Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[2], {direction: Zcl.Direction.SERVER_TO_CLIENT}, undefined),
304
- ).toBeFalsy();
305
- expect(
306
- Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[6], {direction: Zcl.Direction.SERVER_TO_CLIENT}, undefined),
307
- ).toBeTruthy();
308
- expect(
309
- Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[6], {direction: Zcl.Direction.CLIENT_TO_SERVER}, undefined),
310
- ).toBeFalsy();
311
- });
312
-
313
288
  it("BITMASK_SET", () => {
314
289
  expect(Zcl.Frame.conditionsValid(Zcl.Clusters.greenPower.commands.notification.parameters[8], {options: 0x4000}, undefined)).toBeTruthy();
315
290
  expect(Zcl.Frame.conditionsValid(Zcl.Clusters.greenPower.commands.notification.parameters[8], {options: 0x4150}, undefined)).toBeTruthy();
@@ -359,6 +334,22 @@ describe("ZCL Frame", () => {
359
334
  });
360
335
 
361
336
  it("FIELD_EQUAL", () => {
337
+ expect(Zcl.Frame.conditionsValid(Zcl.Foundation.readRsp.parameters[2], {status: 0}, undefined)).toBeTruthy();
338
+ expect(Zcl.Frame.conditionsValid(Zcl.Foundation.readRsp.parameters[2], {status: 1}, undefined)).toBeFalsy();
339
+ expect(Zcl.Frame.conditionsValid(Zcl.Foundation.writeRsp.parameters[1], {status: 1}, undefined)).toBeTruthy();
340
+ expect(Zcl.Frame.conditionsValid(Zcl.Foundation.writeRsp.parameters[1], {status: 0}, undefined)).toBeFalsy();
341
+ expect(
342
+ Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[2], {direction: Zcl.Direction.CLIENT_TO_SERVER}, undefined),
343
+ ).toBeTruthy();
344
+ expect(
345
+ Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[2], {direction: Zcl.Direction.SERVER_TO_CLIENT}, undefined),
346
+ ).toBeFalsy();
347
+ expect(
348
+ Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[6], {direction: Zcl.Direction.SERVER_TO_CLIENT}, undefined),
349
+ ).toBeTruthy();
350
+ expect(
351
+ Zcl.Frame.conditionsValid(Zcl.Foundation.configReport.parameters[6], {direction: Zcl.Direction.CLIENT_TO_SERVER}, undefined),
352
+ ).toBeFalsy();
362
353
  expect(
363
354
  Zcl.Frame.conditionsValid(Zcl.Clusters.touchlink.commandsResponse.scanResponse.parameters[13], {numberOfSubDevices: 1}, undefined),
364
355
  ).toBeTruthy();
@@ -368,6 +359,24 @@ describe("ZCL Frame", () => {
368
359
  expect(
369
360
  Zcl.Frame.conditionsValid(Zcl.Clusters.touchlink.commandsResponse.scanResponse.parameters[13], {numberOfSubDevices: 3}, undefined),
370
361
  ).toBeFalsy();
362
+ expect(
363
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[2], {payloadType: 0}, undefined),
364
+ ).toBeFalsy();
365
+ expect(
366
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[2], {payloadType: 1}, undefined),
367
+ ).toBeTruthy();
368
+ expect(
369
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[3], {payloadType: 1}, undefined),
370
+ ).toBeFalsy();
371
+ expect(
372
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[3], {payloadType: 2}, undefined),
373
+ ).toBeTruthy();
374
+ expect(
375
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[4], {payloadType: 2}, undefined),
376
+ ).toBeFalsy();
377
+ expect(
378
+ Zcl.Frame.conditionsValid(Zcl.Clusters.genOta.commandsResponse.imageNotify.parameters[4], {payloadType: 3}, undefined),
379
+ ).toBeTruthy();
371
380
  });
372
381
  });
373
382
 
@@ -923,4 +932,29 @@ describe("ZCL Frame", () => {
923
932
  const short2New = short2Zcl.toBuffer();
924
933
  expect(short2New).toStrictEqual(short2);
925
934
  });
935
+
936
+ it("throws when payload too short to continue reading", () => {
937
+ const b = Buffer.from([1, 3, 3, 0, 33, 16, 18, 0, 255, 69, 81, 0, 62, 0, 0, 0]);
938
+
939
+ expect(() => {
940
+ Zcl.Frame.fromBuffer(Zcl.Clusters.genOta.ID, Zcl.Header.fromBuffer(b), b, {});
941
+ }).toThrow(
942
+ `Cannot parse 'imageBlockRequest:maximumDataSize' (The value of "offset" is out of range. It must be >= 0 and <= 15. Received 16)`,
943
+ );
944
+ });
945
+
946
+ // https://github.com/Koenkk/zigbee2mqtt/issues/28217
947
+ it("[workaround] Reads genOta imageBlockRequest even if minimumBlockPeriod is missing", () => {
948
+ const b = Buffer.from([1, 3, 3, 2, 33, 16, 18, 0, 255, 69, 81, 0, 62, 0, 0, 0, 8]);
949
+ const frame = Zcl.Frame.fromBuffer(Zcl.Clusters.genOta.ID, Zcl.Header.fromBuffer(b), b, {});
950
+
951
+ expect(frame.payload).toStrictEqual({
952
+ fieldControl: 2,
953
+ manufacturerCode: 4129,
954
+ imageType: 18,
955
+ fileVersion: 5326335,
956
+ fileOffset: 62,
957
+ maximumDataSize: 8,
958
+ });
959
+ });
926
960
  });
@@ -51,13 +51,13 @@ describe("ZCL Utils", () => {
51
51
  ],
52
52
  [
53
53
  "by ID with non-matching manufacturer code",
54
- {key: Zcl.Clusters.sprutDevice.ID, manufacturerCode: 123, customClusters: {}},
55
- {cluster: Zcl.Clusters.sprutDevice, name: "sprutDevice"},
54
+ {key: Zcl.Clusters.manuSpecificSinope.ID, manufacturerCode: 123, customClusters: {}},
55
+ {cluster: Zcl.Clusters.manuSpecificSinope, name: "manuSpecificSinope"},
56
56
  ],
57
57
  [
58
58
  "by ID with matching manufacturer code",
59
- {key: Zcl.Clusters.sprutDevice.ID, manufacturerCode: Zcl.Clusters.sprutDevice.manufacturerCode!, customClusters: {}},
60
- {cluster: Zcl.Clusters.sprutDevice, name: "sprutDevice"},
59
+ {key: Zcl.Clusters.manuSpecificSinope.ID, manufacturerCode: Zcl.Clusters.manuSpecificSinope.manufacturerCode!, customClusters: {}},
60
+ {cluster: Zcl.Clusters.manuSpecificSinope, name: "manuSpecificSinope"},
61
61
  ],
62
62
  [
63
63
  "custom by ID",