A variable that updates on change and periodically?

Afternoon all,

I've only been playing around with IoT Cloud for a few days now, it doesn't look like I can create a variable that updates on change and every (for example) 60 seconds. I was just wondering if there was a way to manipulate this behavior in code...

Example, say we have 2 variables. First (temp) a float wich reads temperature from a temperature sensor set to update every 60 seconds as it doesn't need great resolution. Second (status) an integer used as a boolean to show if something is on or off set to update on change as i want to know immediatly if its turned on or off (using an integer as i can graph them in the dashboard, can't graph a boolean).

Problem is i still want the status to update every 60 seconds even if its still reporting the same status...

OK, long and short of it, can anyone think of a way that i can get a variable to update every 60 seconds and when it changes....?

If there was any code i'd post it, its just an issue i came accross but havent needed to implment yet...

Apologies for the bad description...

Thanks

Dave

hi @quattrodave

I'm trying to understand what the need for this would be.
If your variable updates on change, it will work as it's expected, and every 60 seconds you'll have the correct value.

Assume this scenario with a temperature updating on change:

  • 11:01:00 am - temperature is 22ºC
  • 11:01:25 am - temperature is 23ºC (on change event is triggered)
  • 11:02:00 am - 1 minute elapsed since 11:01, no change between last operation has happened but we've already been notified of that chnage at 11:01:25 so we know the temperature.

hope I managed to convince you that you don't need such a feature :slight_smile:

Hi, thank for your reply. True, it wouldn't be needed for the temp variable, its the status veritable that I do want it for. Apologies probably my bad descriptions...

OK, say I have a switch, and I want to know what its status is, on or off, I can set the variable to update every 60 seconds I'll get uts status reported weather it changes or not, but I also want to know the moment it changes, then I can set it to 'on change'... problem is I can’t seem to do both...

Is there anything like an ArduinoCloud.update.now or ArduinoCloud.update.force which might force all variables to be updated regardless...?

@quattrodave

I really need to understand why onChange is not a good option.
The Arduino IoT Cloud object updates at every loop cycle, and if there is a change it notifies the proper callback.
I have honestly never used interval updates, so I'm really struggling to understand why it doesn't fit your needs :smiley:

say I have a switch, and I want to know what its status is, on or off
you always know, because you have the variable associated with the property

I can set the variable to update every 60 seconds I'll get uts status reported weather it changes or not
you can always get its status because the variable is there. In theory you can have your internal time-based code to be executed every 60 seconds

but I also want to know the moment it changes, then I can set it to 'on change'
you cannot change its behaviour, we have no "removeProperty" method.

if you want to achieve this do the following:

  • leave the property with onChange
  • in your loop track time using millis() and implement something that happens every 60 seconds
  • in the onChange callback for your property, instead of executing code, call a custom function that executes such code
  • every 60 seconds call that same function

This allows you to do what you need to without puzzling yourself too much.
Some times we approach a problem from the wrong angle, and I think this angle might help you get to a solution :slight_smile:

ubidefeo:

but I also want to know the moment it changes, then I can set it to 'on change'
you cannot change its behaviour, we have no "removeProperty" method.

Yes, sorry, I wasn't meaning change the variables behaviour/setup mid-execution.
Ok, let me try to explain again (if i sound patronising or sarcastic i really don't mean to!).

Example 1.
I have a switch, and I want to know what its status is, on or off, 1 or 0.
I setup a 'readonly' variable 'periodicaly' & update every 60 seconds I'll get its status reported to the dashboard every 60 seconds weather it changes or not. However, if the switch is moved from 'off' to 'on' for 10 seconds inbetween the update cycle it won't be logged, therefore a bit pointless monitoring it.

Example 2.
I have a switch, and I want to know what its status is, on or off, 1 or 0.
I setup a 'readonly' variable to 'on change' and its status will be updated to the dashboard the moment it changes.
However, if it doens't change i have no idea what state its in because it hasn't updated. This makes graphing history impossable.

My initial asumption was that if i had 2 variables, first one set 'periodically' @ 60 seconds & the second one set 'on change'. Then, when 60 second update process was performed, it would send both variables data to the dashboard. However thats not the behavior i'm seeing, it would send the 'periodically' data to the dashboard but not send any data for the 'on change' variable.

ubidefeo:
if you want to achieve this do the following:

  • leave the property with onChange
  • in your loop track time using millis() and implement something that happens every 60 seconds
  • in the onChange callback for your property, instead of executing code, call a custom function that executes such code
  • every 60 seconds call that same function

OK, i'm liking the the sound of this... Not a problem creating a simple timer to fire a custom function every 60 seconds but, where would i find the 'onChange callback' code so as to modify its behaviour? Or have i mis-understood you?

ubidefeo:
This allows you to do what you need to without puzzling yourself too much.
Some times we approach a problem from the wrong angle, and I think this angle might help you get to a solution :slight_smile:

Oh i couldn't agree more, its far too easy to get blinkered and only see a probelm from one angle, I do it a lot :smiley:
Thank you!

hey @quattrodave

Really for Example 1, you don't have to use "periodically" but just make it "on change".
Your goal is to get data to the dashboard, and you will get it.
What's the point of having it run periodically?
It's not that your board will disconnect or go to sleep in the meantime.
There is no gain in using such strategy.

For Example 2 I'm gonna take a stab at this and keep you posted :slight_smile:

I think I also have an answer for Example 2:

despite the property update being "on change", at every successful connection between IoT Cloud and your board there is a "Sync" event which syncs your board's variable with the Cloud property.

If you need to know this once connected because you need to act upon it locally (at board level) you can subscribe to this event and add a callback
in the setup you can add any of these and then declare your callback functions in your sketch

// in your sketch after ArduinoCloud.begin()
ArduinoCloud.addCallback(ArduinoIoTCloudEvent::CONNECT, onIoTConnect);
ArduinoCloud.addCallback(ArduinoIoTCloudEvent::DISCONNECT, onIoTDisconnect);
ArduinoCloud.addCallback(ArduinoIoTCloudEvent::SYNC, onIoTSync);

for the functions

void onIoTConnect() {
	Serial.println(">>> connected to Arduino IoT Cloud");
}
void onIoTDisconnect() {
	Serial.println(">>> disconnected to Arduino IoT Cloud");
}

void onIoTSync() {
	Serial.println(">>> Board and Cloud SYNC OK");
}

Thank you. Replacement SIM car has just arrived, i'm planning to do some work on it tonight & tomorrow...

ubidefeo:
despite the property update being "on change", at every successful connection between IoT Cloud and your board there is a "Sync" event which syncs your board's variable with the Cloud property.

OK, i'm pretty sure I understand what the code is doing. So your idea is when this sync event is fired, to manually sync the 'switch state' regardless of if its changed or not?

@quattrodave

the onIoTSync will get triggered at every successful connection/reconnection between the board and IoT Cloud.
This makes sure that if you have your board reset for whatever reason, the last expressely set value is assigned to the one out of sync.
If you have changed your local variable it will be updated to the Cloud and viceversa.

I am 100% sure all you need to do can be done with onChange type properties

Hiya,

Yes, I can confirm the 'onIoTSync' is triggered after the board re-connects to IoTCloud, either due to power failure, reset button or a GSM glitch.

***** Arduino IoT Cloud - configuration info *****
Device ID: bbaa7dd3-***************************
Thing ID: e23ae93f-****************************
MQTT Broker: mqtts-sa.**********************
SIM card ok
Sending PING to outer space...
GPRS.ping(): 58
Connected to GPRS Network
Connected to Arduino IoT Cloud
>>> Board and Cloud SYNC OK

I'm a bit suprised but it looks that adding the call back alone makes it update the 'SwitchState' when 'onIoTSync' is called.
I would have assumed i'd need some extra code in the 'onIoTSync' function...

Hmmm looks to be working out just fine, thank you.

On a side note, where did you find out about the IoT callbacks, is there any documentation anywhere? I was wondering if there were anyothers that may come in useful :slight_smile:

@quattrodave

the Sync should happen regardless of you adding the callback.
if it doesn't then I'd like to ask you to share your sketch (and thinkgProperties.h) so I can investigate possible bugs.

where did you find out about the IoT callbacks, is there any documentation anywhere?

funny story: I did the first rewriting of this library, that's how I know.
I expressely requested the feature to my colleague Alexander because I wasn't able to write the callback at the time :smiley:

I don't think this is documented anywhere... maybe it's time to provide an example

This topic was automatically closed 120 days after the last reply. New replies are no longer allowed.