I am trying to store time variables in flow variables. And somehow it's not working. When I test with node.warn, everything seems ok. Also when I store actual time, it's ok. So I am puzzled here. Can anybody help me out?
msg_p = {};
msg_period = {};
msg_datepick = {};
let h, m, y, val, period, d;
// Start up
if (msg.topic == "boot"){
}
flow.set('overview.actualtime', new Date());
// Button today pushed
if (msg.topic == "today"){
period = "today";
flow.set('overview.period', period);
// Set new starttime
d = new Date();
d.setHours(0);
d.setMinutes(0);
d.setSeconds(0);
node.warn("starttime = "+d);
flow.set('overview.starttime', d);
// Set new endtime
d.setHours(23);
d.setMinutes(59);
d.setSeconds(59);
node.warn("endtime = "+d);
flow.set('overview.endtime', d);
}
The result in flow variables is,
as you can see, starttime and endtime are the same here.
This is due to JS storing objects by reference. you have set endtime and starttime to refer to the same object. When you update the object starttime refers to, then when you update endtime you update the same object. Simple fix is to use different Date vars
msg_p = {};
msg_period = {};
msg_datepick = {};
let h, m, y, val, period, ds, de;
// Start up
if (msg.topic == "boot"){
}
flow.set('overview.actualtime', new Date());
// Button today pushed
if (msg.topic == "today"){
period = "today";
flow.set('overview.period', period);
// Set new starttime
ds = new Date();
ds.setHours(0);
ds.setMinutes(0);
ds.setSeconds(0);
node.warn("starttime = "+ds);
flow.set('overview.starttime', ds);
// Set new endtime
de = new Date();
de.setHours(23);
de.setMinutes(59);
de.setSeconds(59);
node.warn("endtime = "+de);
flow.set('overview.endtime', de);
}
return null;
@E1cid , yes, indeed, now I understand. I already knew for copying objects (deep copying). But did not connect the dots, this is also an object. Thanks very much, helpt me a lot.
The link was more for the OP to understand how objects are stored by reference, not for the cloning technics. If you wish to add a link for better cloning methods feel free.
@TotallyInformation, @E1cid, yes, I read the article, it was very technical, but I understand a bit.
I think copying objects in javascript is a weard thing though. I know the concept of alliasing, that's very clear.
But normal copying of objects in javascript is a mix of copying and aliassing.
I use then:
flow.set('dest', JSON.parse(JSON.stringify(source))); // Deep copy);
But now I have another mistery on my hands with the same subject I think.
Maybe you can help me out with that also, here is the code,
let test = {};
let a,b,c;
a=1;
b=2;
c=3;
// This is working
test.a = a;
test.b = b;
test.c = c;
// This is NOT working
//test.item.a = a;
//test.item.b = b;
//test.item.c = c;
flow.set('test', JSON.parse(JSON.stringify(test))); // Deep copy);
//flow.set('dest', JSON.parse(JSON.stringify(source))); // Deep copy);
//node.warn(test);
//node.warn(typeof test);
return msg;
If I use test.item.a/b/c, I get this warning,
What I am trying to do , is build a complex object, and then (deep) copy the complete object to flow.
But if I write each (complex) variable separete to flow it is working, but I don't know if that is referenced then or a real copy.
@E1cid , your solution might be working, I also read the article you pointed out, but that doesn't make live easier.
I like simple code. So I think I opt for the solution to copy each variable seperately.
Make absolutely certain that you wrap that line in a try/catch block for when it fails. JSON parsing is very fragile. It is generally better to use something like flow.set('test', Object.assign({}, test))
@TotallyInformation, I guess you speak from experience, so I will replace that construct at the places I used it. Thanks very much for the info so far.
Also thanks @E1cid and @Colin for your input.
I am still learning every day!!