Strange behaviour of assign of context var with init bool value


Does anyone see what i am doing wrong? After defining the variables with a context get it goes wel for all except for the bool one. SetTempCFirst is not set in the program and stays alwas true. If i put in the extra line SetTempCFirstOn = context.get('SetTempCFirstOn') everything works as expected.

SetTempC = context.get('SetTempC') || 0
SetTempCOld = context.get('SetTempCOld') || 0
SetTempCFirstOn = context.get('SetTempCFirstOn') || true

// Line below changes result. Otherwise SetTempCFirstOn is not set and always true
SetTempCFirstOn = context.get('SetTempCFirstOn')
if (msg.topic == 'SetTempC') {
msg1 = null
msg2 = null

if (msg.topic == 'Tick') {
if (msg.payload == 'on') {
msg1 = {payload:SetTempC}
msg1.topic = 'SetTempC'
// Check if it's turned on
if (SetTempCFirstOn === true) {
msg2 = {payload:'ON'}
msg2.topic = 'SetTempCTimer'
} else {
// Check status changed
if (SetTempCOld != SetTempC) {
msg2 = {payload:'CHANGED'}
msg2.topic = 'SetTempCTimer'
} else {
msg2 = null
if (msg.payload == 'stopped') {
msg1 = null
msg2 = {payload:'OFF'}
msg2.topic = 'SetTempCTimer'
return [msg1, msg2];

[{"id":"e2ffd826.ee8d18","type":"tab","label":"Flow 2","disabled":false,"info":""},{"id":"34f9d7cb.0fe788","type":"looptimer","z":"e2ffd826.ee8d18","duration":"2","units":"Second","maxloops":"1000","maxtimeout":"1","maxtimeoutunits":"Hour","name":"","x":301,"y":144,"wires":[["9777f42a.08c978"],["9777f42a.08c978"]]},{"id":"9e31a61f.d361f8","type":"inject","z":"e2ffd826.ee8d18","name":"","topic":"Tick","payload":"on","payloadType":"str","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":89,"y":132,"wires":[["34f9d7cb.0fe788"]]},{"id":"a2c38919.dc6358","type":"inject","z":"e2ffd826.ee8d18","name":"","topic":"Tick","payload":"STOP","payloadType":"str","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":97,"y":172,"wires":[["34f9d7cb.0fe788"]]},{"id":"dcbb2173.3158c","type":"inject","z":"e2ffd826.ee8d18","name":"","topic":"SetTempC","payload":"100","payloadType":"num","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":117,"y":220,"wires":[["9777f42a.08c978"]]},{"id":"83237633.5e8d08","type":"inject","z":"e2ffd826.ee8d18","name":"","topic":"SetTempC","payload":"150","payloadType":"num","repeat":"","crontab":"","once":false,"onceDelay":0.1,"x":118,"y":268,"wires":[["9777f42a.08c978"]]},{"id":"9777f42a.08c978","type":"function","z":"e2ffd826.ee8d18","name":"TimeControl2","func":"SetTempC = context.get('SetTempC') || 0\nSetTempCOld = context.get('SetTempCOld') || 0\nSetTempCFirstOn = context.get('SetTempCFirstOn') || true\n\n// Line below changes result. Otherwise SetTempCFirstOn is not set and always true\nSetTempCFirstOn = context.get('SetTempCFirstOn')\nif (msg.topic == 'SetTempC') {\n context.set('SetTempC',msg.payload)\n msg1 = null\n msg2 = null\n}\n\nif (msg.topic == 'Tick') { \n if (msg.payload == 'on') {\n msg1 = {payload:SetTempC}\n msg1.topic = 'SetTempC'\n // Check if it's turned on\n if (SetTempCFirstOn === true) {\n msg2 = {payload:'ON'}\n msg2.topic = 'SetTempCTimer'\n context.set('SetTempCFirstOn',false)\n } else {\n // Check status changed\n if (SetTempCOld != SetTempC) {\n msg2 = {payload:'CHANGED'}\n msg2.topic = 'SetTempCTimer'\n context.set('SetTempCOld',SetTempC)\n } else {\n msg2 = null\n } \n } \n } \n if (msg.payload == 'stopped') {\n msg1 = null\n msg2 = {payload:'OFF'}\n msg2.topic = 'SetTempCTimer'\n context.set('SetTempCFirstOn',true)\n }\n}\nreturn [msg1, msg2];","outputs":2,"noerr":0,"x":537,"y":178,"wires":[["db71092d.2edfd8"],["1b251a56.40ad86"]]},{"id":"1b251a56.40ad86","type":"debug","z":"e2ffd826.ee8d18","name":"output 2","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","x":555,"y":314,"wires":},{"id":"db71092d.2edfd8","type":"debug","z":"e2ffd826.ee8d18","name":"output 1","active":true,"tosidebar":true,"console":false,"tostatus":false,"complete":"payload","x":609,"y":74,"wires":}]


Solved: it's not assigning but a trick :wink: Use assign to be sure. Works only with non bool values.


The problem is the way you are trying to set the default value using the || operator.

If you set SetTempCFirstOn to false then the above code will return true because the left-hand side of the || is false.

If false is a valid value, then you cannot use the || trick - you have to be explicit:

var SetTempCFirstOn = context.get('SetTempCFirstOn');
if (SetTempCFirstOn === undefined) {
    SetTempCFirstOn = true

Please also read this post about how to share code/flows in the forum - How to share code or flow json


Pfff that was a pain to find out. Thought I was gone crazy. I was presuming it was a valid stament to assign values but it is a trick when there is a false on the left side the right side is chosen. A pipe statement. That I have to find out by try and error.

Thanks without this explanation I scratched my head even longer.