iobroker.zigbee2mqtt 3.0.9 → 3.0.10

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/README.md CHANGED
@@ -22,6 +22,12 @@ This adapter allows to control the data points of the devices of a Zigbee2MQTT i
22
22
  [Adapter Documentation](https://github.com/arteck/ioBroker.zigbee2mqtt/blob/main/docs/wiki.md)
23
23
 
24
24
  ## Changelog
25
+ ### 3.0.10 (2025-12-07)
26
+ - (arteck) Dependencies have been updated
27
+ - (bluefox) Changed role of `color_temp_startup` state to `level` to avoid double `level.temperature` in one device
28
+ - (arteck) fix ZBMINIR2 inching DP
29
+ - (arteck) delete DP colortempstartup
30
+
25
31
  ### 3.0.9 (2025-06-19)
26
32
  - (bjoernbusch) queue up message parsing
27
33
  - (dotcom84) Support for non-default MQTT base topics
package/io-package.json CHANGED
@@ -1,8 +1,21 @@
1
1
  {
2
2
  "common": {
3
3
  "name": "zigbee2mqtt",
4
- "version": "3.0.9",
4
+ "version": "3.0.10",
5
5
  "news": {
6
+ "3.0.10": {
7
+ "en": "Dependencies have been updated\nChanged role of `color_temp_startup` state to `level` to avoid double `level.temperature` in one device\nfix ZBMINIR2 inching DP\ndelete DP colortempstartup",
8
+ "de": "Abhängigkeiten wurden aktualisiert\nÄnderung der Rolle von `color_temp_startup` Zustand auf `level`, um Doppel `level.temperature` in einem Gerät zu vermeiden\nzBMINIR2 Inch DP reparieren\nlöschen DP colortempstartup",
9
+ "ru": "Зависимости были обновлены\nИзменилась роль состояния «color_temp_startup» до «level», чтобы избежать двойной «level.temperature» в одном устройстве\nzBMINIR2 Inching DP\nудалить DP colortempstartup",
10
+ "pt": "As dependências foram atualizadas\nPapel alterado do estado de `color_temp_startup` para `level` para evitar o duplo `level.temperature` em um dispositivo\ncorrigir ZBMINIR2 nching DP\napagar DP colortempstartup",
11
+ "nl": "Afhankelijkheden zijn bijgewerkt\nVeranderde rol van Color_temp_startup\nfix ZBMINIR2 inching DP\nverwijderen DP colortempstartup",
12
+ "fr": "Les dépendances ont été actualisées\nChangement du rôle de l'état `color_temp_startup` à `level` pour éviter le double `level.temperature` dans un seul appareil\ncorrection de l'encoche ZBMINIR2 DP\nsupprimer DP colortempstartup",
13
+ "it": "Le dipendenze sono state aggiornate\nCambiato ruolo di `color_temp_startup` stato a `level` per evitare doppio `level.temperature` in un dispositivo\ncorrezione ZBMINIR2 inching DP\neliminare DP colortempstartup",
14
+ "es": "Se han actualizado las dependencias\nCambiar el papel de `color_temp_startup` estado a `nivel` para evitar el doble `nivel.temperatura` en un dispositivo\nfijar ZBMINIR2 inching DP\neliminar DP colortempstartup",
15
+ "pl": "Zaktualizowano zależności\nZmieniona rola 'color _ temp _ startup' stanu na 'poziom', aby uniknąć podwójnego 'level.temperature' w jednym urządzeniu\nfix ZBMINIR2 inching DP\nusuń odtwarzacz kolorów DP",
16
+ "uk": "Залежність було оновлено\nЗмінена роль `color_temp_startup` для `level`, щоб уникнути подвійного рівня `level. Температура` в одному пристрої\nзафіксувати ZBMINIR2 інвертор ДП\nвидалити DP Colortempstartup",
17
+ "zh-cn": "依赖关系已更新\n将“color_temp_startup”状态的作用改为“level”,以避免一个设备中的双“level.teperature”\n修补 ZBMINIR2 插入 DP\n删除 DP 调色符启动"
18
+ },
6
19
  "3.0.9": {
7
20
  "en": "queue up message parsing\nSupport for non-default MQTT base topics",
8
21
  "de": "nachrichtenparsing löschen\nUnterstützung für nicht-Standard-MQTT-Basisthemen",
@@ -80,19 +93,6 @@
80
93
  "pl": "aktualizacja admin",
81
94
  "uk": "оновлення адмін",
82
95
  "zh-cn": "更新管理员"
83
- },
84
- "3.0.3": {
85
- "en": "corr illuminance (del illuminance_raw)\nindicator.alarm.flood",
86
- "de": "korr illuminance (del illuminance_raw)\nindikator.alarm.flood",
87
- "ru": "коррозионная иллюминация (подлинный рисунок)\nindicator.alarm.flood",
88
- "pt": "illuminance de corr (del illuminance_raw)\nindicador.alarm.flood",
89
- "nl": "verlichtingssterkte (del verlichtingssterkte_raw)\nindicator.alarm.vloed",
90
- "fr": "illuminance du corr (del illuminance_raw)\nindicateur.alarme.inondation",
91
- "it": "illuminazione corr (del illuminance_raw)\nindicatore.alarm.flood",
92
- "es": "iluminancia del corr (iluminación del dedo_raw)\nindicador.alarm.flood",
93
- "pl": "krzak świetlny (del luminance _ raw)\nindicator.alarm.powódź",
94
- "uk": "апошні\nіндикатор.alarm.flood",
95
- "zh-cn": "corr 灯光( del 灯光_ raw)\n指标. alarm.flood"
96
96
  }
97
97
  },
98
98
  "messages": [
package/lib/exposes.js CHANGED
@@ -269,9 +269,7 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
269
269
  // as we have new state, responsible for set, we have to use new `isOption`
270
270
  // or remove it
271
271
  if (
272
- (!state.hasOwnProperty('isOption') || state.isOptions === false) &&
273
- states[stateExists].hasOwnProperty('isOption')
274
- ) {
272
+ (!state.hasOwnProperty('isOption') || state.isOption === false) && states[stateExists].hasOwnProperty('isOption')) {
275
273
  delete states[stateExists].isOption;
276
274
  } else {
277
275
  states[stateExists].isOption = state.isOption;
@@ -442,17 +440,17 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
442
440
  read: true,
443
441
  type: 'number',
444
442
  min:
445
- config.useKelvin == true
446
- ? utils.miredKelvinConversion(prop.value_max)
447
- : prop.value_min,
443
+ config.useKelvin == true
444
+ ? utils.miredKelvinConversion(prop.value_max)
445
+ : prop.value_min,
448
446
  max:
449
- config.useKelvin == true
450
- ? utils.miredKelvinConversion(prop.value_min)
451
- : prop.value_max,
447
+ config.useKelvin == true
448
+ ? utils.miredKelvinConversion(prop.value_min)
449
+ : prop.value_max,
452
450
  def:
453
- config.useKelvin == true
454
- ? utils.miredKelvinConversion(prop.value_min)
455
- : prop.value_max,
451
+ config.useKelvin == true
452
+ ? utils.miredKelvinConversion(prop.value_min)
453
+ : prop.value_max,
456
454
  unit: config.useKelvin == true ? 'K' : 'mired',
457
455
  setter: (value) => {
458
456
  return utils.toMired(value);
@@ -490,21 +488,21 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
490
488
  break;
491
489
  }
492
490
  case 'color_temp_startup': {
493
- const stateName = expose.endpoint
494
- ? `colortempstartup_${expose.endpoint}`
495
- : 'colortempstartup';
491
+ //const stateName = expose.endpoint
492
+ // ? `colortempstartup_${expose.endpoint}`
493
+ // : 'colortempstartup';
496
494
  const propName = expose.endpoint
497
495
  ? `color_temp_startup_${expose.endpoint}`
498
496
  : 'color_temp_startup';
499
497
  //const colorMode = expose.endpoint ? `color_mode_${expose.endpoint}` : 'color_mode';
500
498
  pushToStates(
501
499
  {
502
- id: stateName,
500
+ id: propName,
503
501
  prop: propName,
504
502
  name: `${prop.description} ${expose.endpoint ? `(${expose.endpoint})` : ''}`.trim(),
505
503
  //options: ['transition'],
506
504
  icon: undefined,
507
- role: 'level.color.temperature',
505
+ role: 'level', // Changed role to level to avoid double level.temperature in one device
508
506
  write: true,
509
507
  read: true,
510
508
  type: 'number',
@@ -560,8 +558,8 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
560
558
  }
561
559
  if (
562
560
  payload[stateName] &&
563
- payload[stateName].hasOwnProperty('x') &&
564
- payload[stateName].hasOwnProperty('y')
561
+ payload[stateName].hasOwnProperty('x') &&
562
+ payload[stateName].hasOwnProperty('y')
565
563
  ) {
566
564
  const colorval = rgb.cie_to_rgb(
567
565
  payload[stateName].x,
@@ -569,9 +567,9 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
569
567
  );
570
568
  return (
571
569
  '#' +
572
- utils.decimalToHex(colorval[0]) +
573
- utils.decimalToHex(colorval[1]) +
574
- utils.decimalToHex(colorval[2])
570
+ utils.decimalToHex(colorval[0]) +
571
+ utils.decimalToHex(colorval[1]) +
572
+ utils.decimalToHex(colorval[2])
575
573
  );
576
574
  } else {
577
575
  return undefined;
@@ -1238,48 +1236,27 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
1238
1236
  }
1239
1237
  break;
1240
1238
 
1241
- case 'composite':
1239
+ case 'composite': {
1240
+ const options = [];
1242
1241
  for (const prop of expose.features) {
1243
- // let state;
1244
- // if (prop.type == 'list' && prop.features) {
1245
- // const listName = prop.name;
1246
-
1247
- // for (const feature of prop.features) {
1248
- // genState(feature, 'state', `${listName}_${feature.name}`, prop.description);
1249
- // }
1250
- // }
1242
+ prop.type = 'text'; // to avoid problems with numbers, booleans, etc.
1251
1243
 
1252
1244
  const state = genState(prop);
1253
1245
  // Workaround for FP1 new state (region_upsert)
1254
1246
  if (!state) {
1255
1247
  break;
1256
1248
  }
1257
- state.prop = expose.property;
1258
- state.inOptions = true;
1259
- // I'm not fully sure, as it really needed, but
1260
- state.setterOpt = (value, options) => {
1261
- const result = {};
1262
- options[prop.property] = value;
1263
- result[expose.property] = options;
1264
- return result;
1265
- };
1266
- // if we have a composite expose, the value have to be an object {expose.property : {prop.property: value}}
1267
- if (prop.access & z2mAccess.SET) {
1268
- state.setter = (value, options) => {
1269
- const result = {};
1270
- options[prop.property] = value;
1271
- result[expose.property] = options;
1272
- return result;
1273
- };
1274
- state.setattr = expose.property;
1275
- }
1276
- // if we have a composite expose, the payload will be an object {expose.property : {prop.property: value}}
1277
- if (prop.access & z2mAccess.STATE) {
1249
+
1250
+ state.prop = expose.property;
1251
+ state.inOptions = true;
1252
+ state.isOption = true;
1253
+
1254
+ if (expose.access & z2mAccess.STATE) {
1278
1255
  state.getter = (payload) => {
1279
1256
  if (
1280
1257
  payload.hasOwnProperty(expose.property) &&
1281
- payload[expose.property] !== null &&
1282
- payload[expose.property].hasOwnProperty(prop.property)
1258
+ payload[expose.property] !== null &&
1259
+ payload[expose.property].hasOwnProperty(prop.property)
1283
1260
  ) {
1284
1261
  return !isNaN(payload[expose.property][prop.property])
1285
1262
  ? payload[expose.property][prop.property]
@@ -1289,13 +1266,16 @@ async function createDeviceFromExposes(devicesMessag, adapter) {
1289
1266
  }
1290
1267
  };
1291
1268
  } else {
1292
- state.getter = (_payload) => {
1293
- return undefined;
1269
+ state.getter = (payload) => {
1270
+ return payload[expose.property][prop.property];
1294
1271
  };
1295
1272
  }
1296
- pushToStates(state, prop.access);
1273
+
1274
+ pushToStates(state, z2mAccess.STATE);
1297
1275
  }
1276
+
1298
1277
  break;
1278
+ }
1299
1279
  default:
1300
1280
  console.log(`Unhandled expose type ${expose.type} for device ${deviceID}`);
1301
1281
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "iobroker.zigbee2mqtt",
3
- "version": "3.0.9",
3
+ "version": "3.0.10",
4
4
  "description": "Zigbee2MQTT adapter for ioBroker",
5
5
  "author": {
6
6
  "name": "Dennis Rathjen and Arthur Rupp",
@@ -24,43 +24,32 @@
24
24
  "node": ">= 20"
25
25
  },
26
26
  "dependencies": {
27
- "@iobroker/adapter-core": "^3.2.3",
27
+ "@iobroker/adapter-core": "^3.3.2",
28
28
  "@iobroker/dm-utils": "^1.0.10",
29
29
  "aedes": "^0.51.3",
30
30
  "aedes-persistence-nedb": "^2.0.3",
31
- "mqtt": "^5.10.4",
31
+ "mqtt": "^5.14.1",
32
32
  "net": "^1.0.2",
33
33
  "node-schedule": "^2.1.1",
34
- "sharp": "^0.33.5",
35
- "ws": "^8.18.2"
34
+ "sharp": "^0.34.5",
35
+ "ws": "^8.18.3"
36
36
  },
37
37
  "devDependencies": {
38
- "@alcalzone/release-script": "^3.8.0",
39
- "@alcalzone/release-script-plugin-iobroker": "^3.7.0",
40
- "@alcalzone/release-script-plugin-license": "^3.7.0",
41
- "@alcalzone/release-script-plugin-manual-review": "^3.7.0",
42
- "@iobroker/adapter-dev": "^1.4.0",
43
- "@iobroker/testing": "^5.0.4",
44
- "@tsconfig/node14": "^14.1.3",
45
- "@types/chai": "^5.2.2",
46
- "@types/chai-as-promised": "^8.0.2",
47
- "@types/mocha": "^10.0.10",
48
- "@types/node": "^22.15.29",
49
- "@types/node-schedule": "^2.1.7",
50
- "@types/proxyquire": "^1.3.31",
51
- "@types/sinon": "^17.0.3",
52
- "@types/sinon-chai": "^4.0.0",
53
- "chai": "^5.2.0",
54
- "chai-as-promised": "^8.0.1",
55
- "eslint": "^9.25.1",
56
- "eslint-config-prettier": "^10.1.5",
57
- "eslint-plugin-prettier": "^5.2.3",
58
- "mocha": "^11.0.1",
59
- "prettier": "^3.5.3",
60
- "proxyquire": "^2.1.3",
61
- "sinon": "^19.0.2",
62
- "sinon-chai": "^4.0.0",
63
- "typescript": "~5.8.2"
38
+ "@alcalzone/release-script": "^5.0.0",
39
+ "@alcalzone/release-script-plugin-iobroker": "^4.0.0",
40
+ "@alcalzone/release-script-plugin-license": "^4.0.0",
41
+ "@alcalzone/release-script-plugin-manual-review": "^4.0.0",
42
+ "@iobroker/adapter-dev": "^1.5.0",
43
+ "@iobroker/testing": "^5.2.2",
44
+ "@iobroker/eslint-config": "^2.1.0",
45
+ "@tsconfig/node14": "^14.1.8",
46
+ "@types/node": "^24.10.1",
47
+ "@types/node-schedule": "^2.1.8",
48
+ "eslint": "^9.39.1",
49
+ "eslint-config-prettier": "^10.1.8",
50
+ "eslint-plugin-prettier": "^5.5.4",
51
+ "prettier": "^3.6.2",
52
+ "typescript": "~5.9.2"
64
53
  },
65
54
  "main": "main.js",
66
55
  "files": [