BLYNK_WRITE and deep sleep

Hi all,

I’ve used blynk for other projects before but this is the first time I’m trying to use ESP 32 deep sleep functionality (time based).

Basically, I am taking temperature reading, sending it to Blynk and then going to deep sleep for a minute. That works - all code is in setup()

However I want to have a slow-feedback function which will be triggered from BLYNK via button or slider on a virtual pin (V2). I understand that it will only be executed once the device wakes up from deep sleep - that is fine.

The problem is that when I configure the BLYNK_WRITE(V2) handler it gets executed every time my device wakes up - unlike in normal flow when the code reaches loop()

I’ve tried Blynk.syncAll() but the message is received many times. Any thoughts?

Blynk.syncAll() forces every BLYNK_WRITE callback to fire.
If you’re wanting your device to do something different when a button widget connected to V2 is in a certain position (such as not sleeping when the button widget is On) then you need to check the setting of the button widget using param.asInt()

If you do this then I’d recommend switching to Blynk.syncVirtual(V2) instead of syncAll as it will execute quicker.

Pete.

Thanks for your reply Pete.
Consider this sketch:

#include <Arduino.h>
#include <WiFi.h>
#include <BlynkSimpleEsp32.h>

const char* SSID = "****";
const char* PASSCODE = "***";
char auth[] = "***";

#define TIME_TO_SLEEP  (60 * 1000000)

void deepSleep() {
  Serial.println("Going to sleep now");
  Serial.flush(); 

  esp_deep_sleep_start();
}

BLYNK_WRITE(V2)
{
  Serial.print("Message from Blynk: ");
  Serial.println(param.asInt());
}

BLYNK_CONNECTED() {
  Serial.println("Connected to blynk");
  Blynk.syncAll();
}

void setupWifi() {
  WiFi.mode(WIFI_STA);
  WiFi.begin(SSID, PASSCODE);

  uint8_t retry = 0;
  while (WiFi.status() != WL_CONNECTED) {
    Serial.print(".");
    delay(1000);

    if ((++retry % 16) == 0) {
      deepSleep();
    }
  }

  Serial.print("Connected :");
  Serial.println(WiFi.localIP());
}

void setup() {
  Serial.begin(115200);
  esp_sleep_enable_timer_wakeup(TIME_TO_SLEEP);
    
  setupWifi();
  
  Blynk.config(auth);
  uint8_t retry = 0;
  while (Blynk.connect() == false) {
    Serial.print("x");
     
    if ((++retry % 16) == 0) {
      deepSleep();
    }
  }
  
  Blynk.run();
  
  Blynk.syncAll();
  
  deepSleep();
}

void loop() {
  // would never get here
}

My assumption was that if I use a Slider in Blynk app (connected to V2) and set it to certain value, than I will get callback BLYNK_WRITE(V2) exactly once at the moment the device is woken up. After processing and going to deep sleep, I thought at the next wake up I will not get BLYNK_WRITE(V2) triggered. That’s how it works if you do not use deep sleep, just have Blynk.run() in the loop() method.

My output was however:

Connected :192.168.2.36
Connected to blynk
Message from Blynk: 856
Going to sleep now

Connected :192.168.2.36
Connected to blynk
Message from Blynk: 856
Going to sleep now

Connected :192.168.2.36
Connected to blynk
Message from Blynk: 856
Going to sleep now

So I assume there needs to be some way of “confirming” the receive of the data on V2 which happens successfully if the Blynk callbacks happen in loop but it does not happen in my code.

Incorrect.
As I said, Blynk.syncAll or Blynk.syncVirtual(V2) forces the Blynk server to send the current value for V2 to the device, which forces the BLYNK_WRITE(V2) callback to fire.
When the device wakes from deep sleep it boots, connects to Blynk and calls Blynk.syncAll causing BLYNK_WRITE(V2) to fire.

You have two options - store the previous V2 value in SPIFFS or other NVR and compare the new result with this, or use a switch or slider where a specific value means something, as opposed to a change of value.

Pete.

Okay I can store the last value in eeprom - I understand the approach here.
But why am I not seeing the same behavior if I just have the Blynk.run() in loop() without the deep sleep?
What I’m trying to get to is a simple approach to hit a button in blynk app, read that in my sketch, handle that callback and go up deep sleep.

Because BLYNK remains connected.

Upon boot, once BLYNK connects to the server, the BLYNK_CONNECTED() function will run. If there is a Blynk.syncAll(); in that function, it will trigger all of the BLYNK_WRITE(Vpin) functions. This will happen every time you wake from DeepSleep.

Because when Blynk.run is in the in the void loop, it is being executed hundreds, if not thousands of times per second.
The moment that you move the slider the server is notified by the app, then that is picked-up by the device the next time Blynk.run is executed.
If you have one Blynk.run in your void setup then you’ll be very lucky to be moving the slider at precisely the time when that executes.

I would t use EEPROM. I’d use SPIFFS, FS or RTC NVR.

Pete.

Right! I think I get it now, thanks!
I misunderstood how blynk server sends the messages to the devices.
I thought it is a queue of messages and a message is picked up from it, removed from the queue and invisible for the next processing run.
Thanks for the explanation.