substitutions: device_name: "battery-sensor-7f3a" friendly_name: "Battery Sensor 7F3A" esphome: name: ${device_name} friendly_name: ${friendly_name} on_boot: - priority: -100 then: - logger.log: "Device started - 10s for OTA" - delay: 10s - logger.log: "OTA window closed - proceeding to sensor reading" - script.execute: read_sensors_and_sleep esp32: board: esp32-c6-devkitc-1 framework: type: esp-idf logger: # level: INFO api: encryption: key: !secret mail_notifier_ha_api_key reboot_timeout: 0s ota: - platform: esphome password: !secret mail_notifier_ota_password wifi: ssid: !secret wifi_ssid password: !secret wifi_password power_save_mode: LIGHT fast_connect: true reboot_timeout: 0s mqtt: broker: !secret mqqt_broker username: !secret mqqt_username password: !secret mqqt_password port: 1883 discovery: false log_topic: null birth_message: topic: ${device_name}/status payload: "online" retain: true will_message: topic: ${device_name}/status payload: "offline" retain: true keepalive: 15s deep_sleep: id: deep_sleep_control sleep_duration: 24h esp32_ext1_wakeup: pins: - number: GPIO7 allow_other_uses: True mode: input: true pullup: true mode: ANY_HIGH script: - id: read_sensors_and_sleep mode: single then: - if: condition: not: mqtt.connected: then: - logger.log: "Waiting for MQTT connection..." - wait_until: condition: mqtt.connected: timeout: 10s - logger.log: "Starting sensor reading" - component.update: battery_raw - delay: 50ms - mqtt.publish: topic: ${device_name}/battery/voltage payload: !lambda |- return to_string(id(battery_voltage).state); retain: true - mqtt.publish: topic: ${device_name}/battery/percent payload: !lambda |- return to_string(id(battery_percent).state); retain: true - if: condition: lambda: 'return esp_sleep_get_wakeup_cause() == ESP_SLEEP_WAKEUP_EXT1;' then: - logger.log: "Woke up by interrupt - Sending ALARM!" - mqtt.publish: topic: ${device_name}/alarm payload: "TRIGGERED" retain: false - mqtt.publish: topic: ${device_name}/reed_switch payload: !lambda |- return id(reed_switch).state ? "OPEN" : "CLOSED"; retain: true - logger.log: "Data sent via MQTT" - delay: 1s - if: condition: binary_sensor.is_off: reed_switch then: - logger.log: "Reed switch closed - entering deep sleep" - deep_sleep.enter: deep_sleep_control else: - logger.log: "WARNING: Reed switch open - staying active!" - delay: 5s - script.execute: read_sensors_and_sleep binary_sensor: - platform: gpio id: reed_switch name: "Reed Switch" internal: true pin: number: GPIO7 mode: input: true pullup: true allow_other_uses: true filters: - delayed_on: 100ms on_release: then: - logger.log: "Reed switch closed" - mqtt.publish: topic: ${device_name}/reed_switch payload: !lambda |- return id(reed_switch).state ? "OPEN" : "CLOSED"; retain: true - delay: 1s sensor: - platform: adc pin: GPIO0 id: battery_raw name: "Battery Raw" attenuation: 12db internal: true filters: - multiply: 2.0 on_value: then: - component.update: battery_voltage - component.update: battery_percent - platform: template id: battery_voltage name: "Battery Voltage" unit_of_measurement: "V" accuracy_decimals: 2 device_class: voltage state_class: measurement update_interval: 1min internal: True lambda: |- float raw = id(battery_raw).state; if (isnan(raw)) return NAN; return raw; - platform: template id: battery_percent name: "Battery Level" unit_of_measurement: "%" accuracy_decimals: 0 device_class: battery state_class: measurement update_interval: 1min internal: True lambda: |- const float min_v = 3.0; const float max_v = 4.15; float v = id(battery_raw).state; if (isnan(v)) return NAN; float p = (v - min_v) / (max_v - min_v) * 100.0; if (p < 0) p = 0; if (p > 100) p = 100; return p;