I'm running an ESP32 to fire an ultrasonic distance sensor to check the fill level on my coffee machine. If it gets below a float-switch level, it just turns the mains power off...and always midway through a shot. The LED shows green/yellow/red for level and flashes red if there's an error. Worked perfectly with 2026.1.0. The problem I have is that with the latest versions (2026.6.3) the LED gets stuck on flashing red the moment there's a single error. Sometimes it seems it will change if the status changes - so if it's in the green level and there's an error reading the ultrasonic it will flash red and not go back to green if there's a good reading. If the level drops to yellow, that change seems to make it change the LED to yellow until the next error. Also, my logger.log attempts to diagnose this, don't seem to be working.
I don't know if there were many errors reading the ultrasonic before but I didn't notice it being a problem before; it just worked.
This might be a minor irritation...but right now it's the straw that broke the camels back!
Any pointers appreciated.
Many thanks,
Gareth
esphome:
name: espresso
friendly_name: ESPresso
on_boot:
then:
- light.turn_on:
id: led
effect: Booting
- component.update: fill_level
esp32:
board: m5stack-atom
framework:
type: esp-idf
substitutions:
#model Atom (grey)
rgb_pin: "GPIO27"
button_pin: "GPIO39"
ir_pin: "GPIO12"
grove1_pin: "GPIO26"
grove2_pin: "GPIO32"
#bottom pins: 33,23,19,22 25,21
# Enable logging
logger:
# Enable Home Assistant API
api:
encryption:
key: ""
ota:
- platform: esphome
password: ""
wifi:
ssid: !secret IoT_ssid
password: !secret IoT_password
min_auth_mode: WPA2
# Enable fallback hotspot (captive portal) in case wifi connection fails
ap:
ssid: "Espresso Fallback Hotspot"
password: ""
captive_portal:
web_server:
port: 80
version: 2
auth:
username: !secret web_server_username
password: !secret web_server_password
light:
- platform: esp32_rmt_led_strip
rgb_order: GRB
pin: ${rgb_pin}
num_leds: 1
chipset: ws2811
name: "LED"
id: led
effects:
- strobe:
name: Booting
colors:
- state: true
brightness: 100%
red: 0%
green: 100%
blue: 0%
duration: 1s
transition_length: 500ms
- state: false
duration: 1s
transition_length: 500ms
- strobe:
name: Overfill
colors:
- state: true
brightness: 100%
red: 100%
green: 0%
blue: 0%
duration: 250ms
- state: false
duration: 250ms
- strobe:
name: Error
colors:
- state: true
brightness: 100%
red: 100%
green: 0%
blue: 0%
duration: 1s
- state: false
duration: 1s
- automation:
name: Good
sequence:
- light.addressable_set:
id: led
color_brightness: 40%
red: 0%
green: 100%
blue: 0%
- automation:
name: Warning
sequence:
- light.addressable_set:
id: led
red: 100%
green: 100%
blue: 0%
- automation:
name: Empty
sequence:
- light.addressable_set:
id: led
red: 100%
green: 0%
blue: 0%
binary_sensor:
- platform: homeassistant
id: coffee_machine_power
entity_id: switch.coffee_machine
- platform: gpio
id: button
name: "button"
internal: true
pin:
number: ${button_pin}
inverted: true
mode:
input: true
on_multi_click:
- timing: # Double-click
- ON for at most 1s
- OFF for at most 1s
- ON for at most 1s
- OFF for at least 0.2s
then:
- switch.turn_on: button_double
- timing: # Long-click
- ON for 1s to 3s
- OFF for at least 0.5s
then:
- switch.turn_on: button_long
- timing:
- ON for at most 1s
- OFF for at least 0.5s
then: # Single-click
- switch.turn_on: button_single
switch:
- platform: template
name: Single Click
id: button_single
optimistic: True
on_turn_on:
- delay: 500ms
- switch.turn_off: button_single
- platform: template
name: Double Click
id: button_double
optimistic: True
on_turn_on:
- delay: 500ms
- switch.turn_off: button_double
- platform: template
name: Long Click
id: button_long
optimistic: True
on_turn_on:
- delay: 500ms
- switch.turn_off: button_long
interval:
- interval: 10s
then:
if:
condition:
binary_sensor.is_on: coffee_machine_power
then:
- component.update: fill_level
- interval: 5min
then:
if:
condition:
binary_sensor.is_off: coffee_machine_power
then:
- component.update: fill_level
sensor:
- platform: ultrasonic
trigger_pin: ${grove1_pin}
echo_pin: ${grove2_pin}
name: "Coffee Machine Fill Level"
id: fill_level
update_interval: never
#timeout: 8m #8m minimum
unit_of_measurement: "cm"
filters:
- lambda: return 24.5-((x+0.005)*100);
on_raw_value:
then:
if:
condition:
lambda: 'return (isnan(x));'
then:
- logger.log: "Ultrasonic failed"
- light.turn_on:
id: led
effect: Error
on_value_range:
- below: 0
then:
#state Error
- logger.log: "Ultrasonic below 0"
- light.turn_on:
id: led
effect: Error
- above: 0
below: 6
then:
#state Empty (Red) - switches off about 4cm
- logger.log: "Ultrasonic 0-6"
- light.turn_on:
id: led
effect: Empty
- above: 5
below: 8
#state Warning (Yellow)
then:
- logger.log: "Ultrasonic 5-8"
- light.turn_on:
id: led
effect: Warning
- above: 8
below: 22
then:
#state OK (Green)
- logger.log: "Ultrasonic 8-22"
- light.turn_on:
id: led
effect: Good
- above: 22
then:
#state Overfull (Pulse Red)
- logger.log: "Ultrasonic 22+"
- light.turn_on:
id: led
effect: Overfill