Skip to content

Commit

Permalink
* (Apollon77) Allow storeState and GetHistory also to be called for "…
Browse files Browse the repository at this point in the history
…unknown ids"
  • Loading branch information
Apollon77 committed May 27, 2022
1 parent e3d837f commit 244cf02
Show file tree
Hide file tree
Showing 3 changed files with 66 additions and 32 deletions.
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,8 @@ This adapter saves state history in a two-staged process.

### __WORK IN PROGRESS__
* (Apollon77) Fix several crash cases reported by Sentry
* (Apollon77) Make sure disabling "Log changes only" also really do not log the changes anymore
* (Apollon77) Allow storeState and GetHistory also to be called for "unknown ids"

### 2.0.1 (2022-05-11)
* (Apollon77) BREAKING: Configuration is only working in the new Admin 5 UI!
Expand Down
66 changes: 34 additions & 32 deletions main.js
Original file line number Diff line number Diff line change
Expand Up @@ -851,15 +851,15 @@ function pushHelper(_id, state) {

history[_id].list.push(state);

const _settings = history[_id][adapter.namespace];
const _settings = history[_id][adapter.namespace] || {};
if (_settings && history[_id].list.length > _settings.maxLength) {
_settings.enableDebugLogs && adapter.log.debug(`moving ${history[_id].list.length} entries from ${_id} to file`);
appendFile(_id, history[_id].list);
}
}

function checkRetention(id) {
if (history[id][adapter.namespace].retention) {
if (history[id] && history[id][adapter.namespace] && history[id][adapter.namespace].retention) {
const d = new Date();
const dt = d.getTime();
// check every 6 hours
Expand Down Expand Up @@ -1801,7 +1801,19 @@ function deleteStateAll(msg) {
adapter.sendTo(msg.from, msg.command, {success: true}, msg.callback);
}

function storeState(msg) {
function storeStatePushData(id, state, applyRules) {
let pushFunc = applyRules ? pushHistory : pushHelper;
if (!history[id] || !history[id][adapter.namespace]) {
if (applyRules) {
adapter.log.warn(`storeState: history not enabled for ${id}, so can not apply the rules as requested`);
throw new Error(`history not enabled for ${id}, so can not apply the rules as requested`);
}
history[id] = {};
}
pushFunc(id, state);
}

async function storeState(msg) {
if (msg.message && (msg.message.success || msg.message.error)) { // Seems we got a callback from running converter
return;
}
Expand All @@ -1812,40 +1824,30 @@ function storeState(msg) {
}, msg.callback);
}

let pushFunc = pushHelper;
if (msg.message.rules) {
pushFunc = pushHistory;
}

let id;
if (Array.isArray(msg.message)) {
adapter.log.debug(`storeState: store ${msg.message.length} states for multiple ids`);
for (let i = 0; i < msg.message.length; i++) {
id = aliasMap[msg.message[i].id] ? aliasMap[msg.message[i].id] : msg.message[i].id;
if (history[id]) {
pushFunc(id, msg.message[i].state);
} else {
adapter.log.warn(`storeState: history not enabled for ${msg.message[i].id}. Ignoring`);
try {
if (Array.isArray(msg.message)) {
adapter.log.debug(`storeState: store ${msg.message.length} states for multiple ids`);
for (let i = 0; i < msg.message.length; i++) {
id = aliasMap[msg.message[i].id] ? aliasMap[msg.message[i].id] : msg.message[i].id;
storeStatePushData(id, msg.message[i].state, msg.message.rules);
}
}
} else if (msg.message.state && Array.isArray(msg.message.state)) {
adapter.log.debug(`storeState: store ${msg.message.state.length} states for ${msg.message.id}`);
id = aliasMap[msg.message.id] ? aliasMap[msg.message.id] : msg.message.id;
for (let j = 0; j < msg.message.state.length; j++) {
if (history[id]) {
pushFunc(id, msg.message.state[j]);
} else {
adapter.log.warn(`storeState: history not enabled for ${msg.message.id}. Ignoring`);
} else if (msg.message.state && Array.isArray(msg.message.state)) {
adapter.log.debug(`storeState: store ${msg.message.state.length} states for ${msg.message.id}`);
id = aliasMap[msg.message.id] ? aliasMap[msg.message.id] : msg.message.id;
for (let j = 0; j < msg.message.state.length; j++) {
storeStatePushData(id, msg.message.state[j], msg.message.rules);
}
}
} else {
adapter.log.debug(`storeState: store 1 state for ${msg.message.id}`);
id = aliasMap[msg.message.id] ? aliasMap[msg.message.id] : msg.message.id;
if (history[id]) {
pushFunc(id, msg.message.state);
} else {
adapter.log.warn(`storeState: history not enabled for ${msg.message.id}. Ignoring`);
adapter.log.debug(`storeState: store 1 state for ${msg.message.id}`);
id = aliasMap[msg.message.id] ? aliasMap[msg.message.id] : msg.message.id;
storeStatePushData(id, msg.message.state, msg.message.rules);
}
} catch (err) {
adapter.log.warn(`storeState: ${err.message}`);
return adapter.sendTo(msg.from, msg.command, {
error: err.message
}, msg.callback);
}

adapter.sendTo(msg.from, msg.command, {success: true}, msg.callback);
Expand Down
30 changes: 30 additions & 0 deletions test/lib/testcases.js
Original file line number Diff line number Diff line change
Expand Up @@ -1057,6 +1057,36 @@ function register(it, expect, sendTo, adapterShortName, writeNulls, assumeExisti
done();
});
});

it(`Test ${adapterShortName}: storeState and getHistory for unknown Id`, function (done) {
this.timeout(25000);

const customNow = Date.now();
sendTo(instanceName, 'storeState', {
id: `my.own.unknown.value-${customNow}`,
state: [
{val: 1, ack: true, ts: customNow - 5000},
{val: 2, ack: true, ts: customNow - 4000},
{val: 3, ack: true, ts: customNow - 3000}
]
}, function (result) {
expect(result.success).to.be.true;

sendTo(instanceName, 'getHistory', {
id: `my.own.unknown.value-${customNow}`,
options: {
count: 500,
aggregate: 'none'
}
}, function (result) {
console.log(JSON.stringify(result.result, null, 2));
expect(result.result.length).to.be.equal(3);

done();
});
});
});

}

module.exports.register = register;
Expand Down

0 comments on commit 244cf02

Please sign in to comment.