diff --git a/README.md b/README.md
index b59f89d..89c8379 100644
--- a/README.md
+++ b/README.md
@@ -217,7 +217,13 @@ otherwise it is more complex and individually to be parametrized.
* blind alert state -> decode bit array
## Changelog
-### 2.5.2
+### 2.5.3 (npm)
+* correction for updating komfort, absenk
+* corrections for the statistics polling when device is not plugged in
+* correction for year to date energy value (not recognizing two digit month)
+* new possibility in admin page to exclude templates/routines/statistics for compatibility with older FB
+
+### 2.5.2 (npm)
* correction for komfort, absenk if receiving 253/254 for OFF/ON it will be NaN see issue #164
### 2.5.1
diff --git a/admin/index_m.html b/admin/index_m.html
index 26875ee..e4f80b3 100644
--- a/admin/index_m.html
+++ b/admin/index_m.html
@@ -304,6 +304,20 @@
options for the
diff --git a/io-package.json b/io-package.json
index 4deb8fa..13e1533 100644
--- a/io-package.json
+++ b/io-package.json
@@ -148,7 +148,10 @@
"fritz_hysteresis": 1,
"fritz_boosttime": 5,
"fritz_windowtime": 5,
- "fritz_tsolldefault": 23
+ "fritz_tsolldefault": 23,
+ "fritz_exclude_templates": false,
+ "fritz_exclude_routines": false,
+ "fritz_exclude_stats": false
},
"objects": [],
"instanceObjects": []
diff --git a/main.js b/main.js
index 509a9bd..5d80232 100644
--- a/main.js
+++ b/main.js
@@ -154,6 +154,9 @@ class Fritzdect extends utils.Adapter {
settings.windowtime = this.windowtime = this.config.fritz_windowtime;
settings.tsolldefault = this.tsolldefault = this.config.fritz_tsolldefault;
settings.fritz_writeonhyst = this.fritz_writeonhyst = this.config.fritz_writeonhyst;
+ settings.exclude_templates = this.exclude_templates = this.config.fritz_exclude_templates;
+ settings.exclude_routines = this.exclude_routines = this.config.fritz_exclude_routines;
+ settings.exclude_stats = this.exclude_stats = this.config.fritz_exclude_stats;
// The adapters config (in the instance object everything under the attribute "native") is accessible via
// this.config:
@@ -212,12 +215,16 @@ class Fritzdect extends utils.Adapter {
this.log.info('start creating devices/groups');
await this.createDevices(this.fritz).catch((e) => this.errorHandlerAdapter(e));
this.log.info('finished creating devices/groups (if any)');
- this.log.info('start creating templates ');
- await this.createTemplates(this.fritz).catch((e) => this.errorHandlerAdapter(e));
- this.log.info('finished creating templates (if any) ');
- this.log.info('start creating routines ');
- await this.createRoutines(this.fritz).catch((e) => this.errorHandlerAdapter(e));
- this.log.info('finished creating routines (if any) ');
+ if (!settings.exclude_templates) {
+ this.log.info('start creating templates ');
+ await this.createTemplates(this.fritz).catch((e) => this.errorHandlerAdapter(e));
+ this.log.info('finished creating templates (if any) ');
+ }
+ if (!settings.exclude_routines) {
+ this.log.info('start creating routines ');
+ await this.createRoutines(this.fritz).catch((e) => this.errorHandlerAdapter(e));
+ this.log.info('finished creating routines (if any) ');
+ }
this.log.info('start initial updating devices/groups');
await this.updateDevices(this.fritz).catch((e) => this.errorHandlerAdapter(e));
this.log.info('finished initial updating devices/groups');
@@ -228,21 +235,26 @@ class Fritzdect extends utils.Adapter {
polling = setInterval(async () => {
// poll fritzbox
try {
- this.log.debug('polling! fritzdect is alive');
+ this.log.debug('polling! fritzdect is alive with ' + settings.intervall + ' s');
await this.updateDevices(this.fritz).catch((e) => this.errorHandlerAdapter(e));
- await this.updateRoutines(this.fritz).catch((e) => this.errorHandlerAdapter(e));
- const deviceswithstat = await this.getStateAsync(
- 'global.statdevices'
- ).catch((e) => {
- this.log.warn('problem getting statdevices ' + e);
- });
-
- if (deviceswithstat && deviceswithstat.val) {
- this.log.debug('glob state ' + deviceswithstat.val);
- let devstat = [].concat([], JSON.parse(String(deviceswithstat.val)));
- for (let i = 0; i < devstat.length; i++) {
- this.log.debug('updating Stats of device ' + devstat[i]);
- await this.updateStats(devstat[i], this.fritz);
+ if (settings.exclude_routines) {
+ await this.updateRoutines(this.fritz).catch((e) =>
+ this.errorHandlerAdapter(e)
+ );
+ }
+ if (!settings.exclude_stats) {
+ const deviceswithstat = await this.getStateAsync(
+ 'global.statdevices'
+ ).catch((e) => {
+ this.log.warn('problem getting statdevices ' + e);
+ });
+ if (deviceswithstat && deviceswithstat.val) {
+ this.log.debug('glob state ' + deviceswithstat.val);
+ let devstat = [].concat([], JSON.parse(String(deviceswithstat.val)));
+ for (let i = 0; i < devstat.length; i++) {
+ this.log.debug('updating Stats of device ' + devstat[i]);
+ await this.updateStats(devstat[i], this.fritz);
+ }
}
}
} catch (e) {
@@ -1522,18 +1534,25 @@ class Fritzdect extends utils.Adapter {
await Promise.all(
Object.entries(statsobj.devicestats).map(async ([ key, obj ]) => {
if (key !== 'temperature') {
+ let old;
if (key == 'energy') {
//months
if (obj['stats']) {
if (obj['stats'][0]) {
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.countm', {
- val: parseInt(obj['stats'][0]['count']),
- ack: true
- });
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.gridm', {
- val: parseInt(obj['stats'][0]['grid']),
- ack: true
- });
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.countm');
+ if (old.val !== parseInt(obj['stats'][0]['count'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.countm', {
+ val: parseInt(obj['stats'][0]['count']),
+ ack: true
+ });
+ }
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.gridm');
+ if (old.val !== parseInt(obj['stats'][0]['grid'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.gridm', {
+ val: parseInt(obj['stats'][0]['grid']),
+ ack: true
+ });
+ }
let datatimem = parseInt(obj['stats'][0]['datatime']);
await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.datatimem', {
val: datatimem,
@@ -1549,7 +1568,7 @@ class Fritzdect extends utils.Adapter {
val: last12m,
ack: true
});
- let monthnum = parseInt(new Date(datatimem * 1000).toISOString().slice(6, 8));
+ let monthnum = parseInt(new Date(datatimem * 1000).toISOString().slice(5, 7));
let ytd = montharr.splice(0, monthnum).reduce((pv, cv) => pv + cv, 0);
await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.energy_ytd', {
val: ytd,
@@ -1558,14 +1577,20 @@ class Fritzdect extends utils.Adapter {
}
// days
if (obj['stats'][1]) {
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.countd', {
- val: parseInt(obj['stats'][1]['count']),
- ack: true
- });
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.gridd', {
- val: parseInt(obj['stats'][1]['grid']),
- ack: true
- });
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.countd');
+ if (old.val !== parseInt(obj['stats'][1]['count'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.countd', {
+ val: parseInt(obj['stats'][1]['count']),
+ ack: true
+ });
+ }
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.gridd');
+ if (old.val !== parseInt(obj['stats'][1]['grid'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.gridd', {
+ val: parseInt(obj['stats'][1]['grid']),
+ ack: true
+ });
+ }
let datatimed = parseInt(obj['stats'][1]['datatime']);
await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.datatimed', {
val: datatimed,
@@ -1596,14 +1621,20 @@ class Fritzdect extends utils.Adapter {
}
} else {
if (obj['stats']) {
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.count', {
- val: parseInt(obj['stats']['count']),
- ack: true
- });
- await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.grid', {
- val: parseInt(obj['stats']['grid']),
- ack: true
- });
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.count');
+ if (old.val !== parseInt(obj['stats']['count'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.count', {
+ val: parseInt(obj['stats']['count']),
+ ack: true
+ });
+ }
+ old = await this.getStateAsync('DECT_' + identifier + '.' + key + '_stats.grid');
+ if (old.val !== parseInt(obj['stats']['grid'])) {
+ await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.grid', {
+ val: parseInt(obj['stats']['grid']),
+ ack: true
+ });
+ }
await this.setStateAsync('DECT_' + identifier + '.' + key + '_stats.datatime', {
val: parseInt(obj['stats']['datatime']),
ack: true
@@ -1749,20 +1780,63 @@ class Fritzdect extends utils.Adapter {
}
*/
let newtemp = 0;
- if (old.val !== parseFloat(value) / 2 || !this.config.fritz_writeonhyst) {
+ // ohne old.val !== parseFloat(value) / 2 ||
+ // individual check
+ if (!this.config.fritz_writeonhyst) {
+ // read value is a temperatur
if (value < 57) {
newtemp = parseFloat(value) / 2;
+ if (old.val !== newtemp) {
+ this.log.debug(
+ 'updating data DECT_' +
+ ain +
+ ' : ' +
+ key +
+ ' new: ' +
+ newtemp +
+ ' old: ' +
+ old.val
+ );
+ await this.setStateAsync('DECT_' + ain + '.' + key, {
+ val: newtemp,
+ ack: true
+ });
+ }
} else {
+ // read value is 253 or 254 and therfore set to NaN
newtemp = NaN;
+ // previous was a temp
+ if (!isNaN(old.val)) {
+ this.log.debug(
+ 'updating data DECT_' +
+ ain +
+ ' : ' +
+ key +
+ ' new: ' +
+ newtemp +
+ ' old: ' +
+ old.val
+ );
+ await this.setStateAsync('DECT_' + ain + '.' + key, {
+ val: newtemp,
+ ack: true
+ });
+ } else {
+ //previous was already no temperature
+ // skip new setting
+ this.log.debug(
+ 'no update data DECT_' +
+ ain +
+ ' : ' +
+ key +
+ ' new: ' +
+ newtemp +
+ ' old: ' +
+ old.val
+ );
+ }
}
}
- this.log.debug(
- 'updating data DECT_' + ain + ' : ' + key + ' new: ' + newtemp + ' old: ' + old.val
- );
- await this.setStateAsync('DECT_' + ain + '.' + key, {
- val: newtemp,
- ack: true
- });
} else if (key == 'humidity') {
//e.g humidity
if (old.val !== parseFloat(value) || !this.config.fritz_writeonhyst) {
@@ -1783,15 +1857,19 @@ class Fritzdect extends utils.Adapter {
}
} else if (key == 'tsoll') {
//neu 2.3.0c
- if (old.val !== parseFloat(value) / 2 || !this.config.fritz_writeonhyst) {
+ if (!this.config.fritz_writeonhyst) {
let targettemp;
let tsoll;
+ let oldval;
if (value < 57) {
// die Abfrage auf <57 brauchen wir wahrscheinlich nicht
- await this.setStateAsync('DECT_' + ain + '.tsoll', {
- val: parseFloat(value) / 2,
- ack: true
- });
+ if (old.val !== parseFloat(value) / 2 || !this.config.fritz_writeonhyst) {
+ await this.setStateAsync('DECT_' + ain + '.tsoll', {
+ val: parseFloat(value) / 2,
+ ack: true
+ });
+ }
+
await this.setStateAsync('DECT_' + ain + '.lasttarget', {
val: parseFloat(value) / 2,
ack: true
@@ -1820,23 +1898,40 @@ class Fritzdect extends utils.Adapter {
tsoll = settings.tsolldefault || this.tsolldefault;
this.log.debug('DECT_' + ain + ' tsoll will be set to default value');
}
- await this.setStateAsync('DECT_' + ain + '.tsoll', {
- val: tsoll,
- ack: true
- });
- await this.setStateAsync('DECT_' + ain + '.lasttarget', {
- val: tsoll,
- ack: true
+ if (old.val !== tsoll) {
+ await this.setStateAsync('DECT_' + ain + '.tsoll', {
+ val: tsoll,
+ ack: true
+ });
+ }
+ oldval = await this.getStateAsync('DECT_' + ain + '.lasttarget').catch((e) => {
+ this.log.warn('problem getting the lasttarget status ' + e);
});
- await this.setStateAsync('DECT_' + ain + '.hkrmode', {
- val: 1,
- ack: true
+ if (oldval.val !== tsoll) {
+ await this.setStateAsync('DECT_' + ain + '.lasttarget', {
+ val: tsoll,
+ ack: true
+ });
+ }
+ oldval = await this.getStateAsync('DECT_' + ain + '.hkrmode').catch((e) => {
+ this.log.warn('problem getting the hkrmode status ' + e);
});
+ if (oldval.val !== 1) {
+ await this.setStateAsync('DECT_' + ain + '.hkrmode', {
+ val: 1,
+ ack: true
+ });
+ }
const currentMode = 'Off';
- await this.setStateAsync('DECT_' + ain + '.operationmode', {
- val: currentMode,
- ack: true
+ oldval = await this.getStateAsync('DECT_' + ain + '.operationmode').catch((e) => {
+ this.log.warn('problem getting the operationmode status ' + e);
});
+ if (oldval.val !== currentMode) {
+ await this.setStateAsync('DECT_' + ain + '.operationmode', {
+ val: currentMode,
+ ack: true
+ });
+ }
} else if (value == 254) {
this.log.debug('DECT_' + ain + ' (tsoll) : ' + 'mode : Opened');
// this.setStateAsync('DECT_'+ ain +'.tsoll', {val: 29, ack: true}); // zum setzen der Temperatur außerhalb der Anzeige?
@@ -1849,23 +1944,40 @@ class Fritzdect extends utils.Adapter {
tsoll = settings.tsolldefault || this.tsolldefault;
this.log.debug('DECT_' + ain + ' tsoll will be set to default value');
}
- await this.setStateAsync('DECT_' + ain + '.tsoll', {
- val: tsoll,
- ack: true
- });
- await this.setStateAsync('DECT_' + ain + '.lasttarget', {
- val: tsoll,
- ack: true
+ if (old.val !== tsoll) {
+ await this.setStateAsync('DECT_' + ain + '.tsoll', {
+ val: tsoll,
+ ack: true
+ });
+ }
+ oldval = await this.getStateAsync('DECT_' + ain + '.lasttarget').catch((e) => {
+ this.log.warn('problem getting the lasttarget status ' + e);
});
- await this.setStateAsync('DECT_' + ain + '.hkrmode', {
- val: 2,
- ack: true
+ if (oldval.val !== tsoll) {
+ await this.setStateAsync('DECT_' + ain + '.lasttarget', {
+ val: tsoll,
+ ack: true
+ });
+ }
+ oldval = await this.getStateAsync('DECT_' + ain + '.hkrmode').catch((e) => {
+ this.log.warn('problem getting the hkrmode status ' + e);
});
+ if (oldval.val !== 2) {
+ await this.setStateAsync('DECT_' + ain + '.hkrmode', {
+ val: 2,
+ ack: true
+ });
+ }
const currentMode = 'On';
- await this.setStateAsync('DECT_' + ain + '.operationmode', {
- val: currentMode,
- ack: true
+ oldval = await this.getStateAsync('DECT_' + ain + '.operationmode').catch((e) => {
+ this.log.warn('problem getting the operationmode status ' + e);
});
+ if (oldval.val !== currentMode) {
+ await this.setStateAsync('DECT_' + ain + '.operationmode', {
+ val: currentMode,
+ ack: true
+ });
+ }
} else {
this.log.warn('undefined tsoll submitted from fritzbox !');
}