ESPhome and deep sleep

Okay, brilliant. I’ll look into that also. Many thanks

Did you have this working? If so, would you please share your code? thanks

Hi, I did. I’ll post it up later once I’m finished with work.

1 Like

@laca75tn hey. I’m so sorry but I completely forgot about your request! Newish job and hectic couple of weeks.

Here it is. This is the test script which I got working and then I apply this to other applications when I want MQTT. Notice that ‘api’ is commented out, as it clashes with deep sleep as it can take a minute or two to connect to the HA api. Just adjust the sleep time accordingly.

I also set up a static ip, just to save hassle of that getting changed. Hope this helps, if not too late


captive_portal:

# Enable logging
logger:

# Enable Home Assistant API
#api:

ota:

# Example configuration entry
sensor:
  - platform: dht
    pin: D3
    model: DHT22
    temperature:
      name: "Green House Temperature"
    humidity:
      name: "Green House Humidity"
    update_interval: 6s
    
deep_sleep:
  run_duration: 30s
  sleep_duration: 1min

mqtt:
  broker: 192.....
  username:
  password: 
  topic_prefix: /chris
  log_topic: /home/outside/greenhousetemperature
  birth_message:
   topic: /home/outside/greenhousetemperature
   payload: ""
  will_message:
   topic: /home/outside/greenhousetemperature
   payload: ""

5 Likes

Hi guys,

Is there a way that we can control deep sleep duration from home assistant?
I would like to set in home assistant duration for a deep sleep on a slider, don’t want to be hardcoded.

@moci and @tom_l You could actually use this method…

Set up a ESP like this (code below) and it will subscribe to the message on the MQTT server, se it when it wakes up and take that value and set it to be the deep sleep duration value. Make sure the value you are sending as the topic however is in milliseconds.

I believe this call:

    on_value:
      then:
       - lambda: |-
          id(deep_sleep_1).set_sleep_duration(id(custom_sleep_time).state);

is not is not documented but it works fine for me :).

substitutions:
  devicename: wemos_weather_station
  friendly_devicename: weather station

esphome:
  name: $devicename
  platform: ESP8266
  board: d1_mini_pro

wifi:
  fast_connect: true
  ssid: !secret wifi_ssid
  password: !secret wifi_password
  manual_ip:
    static_ip: 192.168.1.201
    gateway: 192.168.1.1
    subnet: 255.255.255.0

# Enable fallback hotspot (captive portal) in case wifi connection fails
  ap:
    ssid: "Wemos WS Fallback Hotspot"
    password: !secret ota_password

# NO API when using battery device
# api:
#   password: !secret api_password

mqtt:
  broker: '192.168.1.7'
  username: !secret mqtt_username
  password: !secret mqtt_password
  discovery: false
  discovery_retain: false
  birth_message:
  will_message:
  on_message:
    - topic: esp/ota_mode
      payload: 'ON'
      then:
        - deep_sleep.prevent: deep_sleep_1

# Enable logging
logger:
  level: INFO

ota:
  password: !secret ota_password

sensor:
  - platform: wifi_signal
    name: $friendly_devicename signal strength

  - platform: mqtt_subscribe
    name: "Sleep time topic"
    id: custom_sleep_time
    unit_of_measurement: ms
    accuracy_decimals: 0
    topic: esp/sleep_mode_time
    on_value:
      then:
       - lambda: |-
          id(deep_sleep_1).set_sleep_duration(id(custom_sleep_time).state);

switch:
  - platform: restart
    id: reboot_esp
    name: $friendly_devicename restart switch

deep_sleep:
  id: deep_sleep_1
  sleep_duration: 300s
  run_duration: 1s
6 Likes

I moved to different projects and didn’t pay attention. I wrote my code for this… But this is great :+1:. @runevad Thank you very much for sharing. Appreciate. I’ll try it.

I experiment with @runevad solution. It works for me. However I found some things that I don’t like.
First, here is mine code, it’s basically copy paste:

deep_sleep:
  id: deep_sleep_mode
  sleep_duration: 600s
  run_duration: 1s
  
switch:
  - platform: restart
    id: living_room_temperature_restart
    name: restart

mqtt:
  broker: '192.168.0.27'
  username: !secret mqtt_username
  password: !secret mqtt_password
  discovery: false
  discovery_retain: false
  birth_message:
  will_message:
  on_message:
    - topic: living-room-temperature/sensor/ota_update
      payload: 'ON'
      then:
        - deep_sleep.prevent: deep_sleep_mode
    
sensor:
  - platform: mqtt_subscribe
    name: "Deep Sleep Timer"
    id: deep_sleep_timer
    unit_of_measurement: min
    accuracy_decimals: 0
    topic: living-room-temperature/sensor/deep_sleep_timer/state
    on_value:
      then:
       - lambda: |-
          id(deep_sleep_mode).set_sleep_duration(id(deep_sleep_timer).state * 1000 * 60); 

  - platform: dht
    pin: D3
    model: DHT11
    temperature:
      name: "Temperature"
      accuracy_decimals: 2
    humidity:
      name: "Humidity"
      accuracy_decimals: 2
    update_interval: 2s

As you can see I set unit_of_measurement to minutes, but I compensate this in lambda expression.
Problem that I noticed is burst of messages which are catch in MQTT Broker when I listen topic:

living-room-temperature/sensor/deep_sleep_timer/state

Every time board wakes up it receives not one message, but the whole burst of spamming messages.
See here:

Anyone knows why is that and how to improve it?
Along with those messages, I can see debug traces spamming log when board restarted:

I think that this is not related with home assistant part, where I set deep sleep timer just once. I even disabled some automation I have for deep sleep timer.
I would say that sensor on device (mqtt_subscribe) actually enters a loop where it sets state and generate messages over again until board enters deep sleep. Could that be the reason? If so, how could be fixed?

@exiledyorkie I’m curious, if you still have this project working… How long were you able to keep the Wemos alive and reporting on one battery cycle? Thanks for your time! Do you have any pictures as well?

@exiledyorkie I too would be interested in how long your batteries lasted. What capacity and voltage info would be useful to know too.

Why no API with deep sleep? Are there known problems with this combination?
It works sort of for me, except that all sensors are most of the time marked as “unknown”, which is a bit annoying (expire_after is only available with mqtt, which I do not use atm) :slight_smile:

I m also interested to the API / deep sleep topic

If I remember rightly, it depends on how long the node is awake, as it can take a while to connect to wifi and make the API connection

Apparently there have been enhancements along the way and as long as your mdns is working similarly then API is a solid choice these days.

That was the feedback from one of the devs I had when I asked on Discord a while back.

Hmmm nice to know… :thinking:. Before (have not tested how it behaves nowadays) the issue was that you can’t get the API to behave with “keep alive”-settings. The moment the ESP goes down to sleep the sensorns and everything gets the state “Unavaliable” in Home Assistant (wich is the correct behaviour with the API since you want to know when the ESP is down).

But… this is not the best for like a weather station or similar projects when you (probably) want the sensors to be set to the latest state until a new value is sent and only be set to the state “Unavailiable” if no new value has been sent for a set period of time, the keep alive-setting.

1 Like

I believe that’s still the API behaviour (for my projects anyways). Haven’t double checked to confirm though.

I used a template in HA to normalise data coming from a weather station. Scrub out states you don’t want

I essentially use the method described at the below link, which uses API to prevent deep sleep from reoccurring. I haven’t fully implemented my final product, but the deep sleep/prevention works fine. It’s set to delay going back into deep sleep for 10s, and that seems to be plenty of time to connect to the api.

I haven’t played around with it enough to see how low I can get the delay to be, but 10s doesn’t seem that bad to me.

:battery: ESPHome: Batteries, Deep Sleep, and Over-the-Air Updates – Tatham Oddie

Hi, I’ve just tried to use that link - I got to this thread after trying to do the setup - exactly as described and I just get errors about not being allow to map id: when the yaml is parsed. Can you please share what you have done if it is something different?
I’m working with an esp8266 by that shouldn’t matter as I’m not getting past the binary_sensor/homeassistant config for some reason.

Relevant code below (also note that my helper boolean is created within Home Assistant, not the ESPHome YAML:

substitutions:
  device_name: water-pump-01
  name_: water_pump_01
  name_pretty: Water Pump
  # sleep parameters
  sleep_time: 10min

esphome:
  name: "${device_name}"
  platform: ESP8266
  board: esp01_1m
  on_boot:
    then:
      - script.execute: consider_deep_sleep

# --- DEEP SLEEP CONFIG ---
deep_sleep:
  id: deep_sleep_control
  sleep_duration: ${sleep_time}

# pull in Helper from Home Assistant for deep sleep config
binary_sensor:
  - platform: homeassistant
    id: prevent_deep_sleep
    name: Prevent Deep Sleep
    entity_id: input_boolean.prevent_deep_sleep

# deep sleep script
script:
  - id: consider_deep_sleep
    mode: queued
    then:
      - delay: 10s
      - if:
          condition:
            binary_sensor.is_on: prevent_deep_sleep
          then:
            - logger.log: 'Skipping sleep, per prevent_deep_sleep'
          else:
            - deep_sleep.enter: deep_sleep_control
      - script.execute: consider_deep_sleep