ESPhome BLE proxy stays online but loses connections to BLE devices until power cycle

The ESP devices don’t go offline, I can see their logs via the ESPHome panel in the Home Assistant UI, etc.

But the BLE devices that I use them to connect to often become unavailable (several different ones, e.g., a Xioami plant sensor, a Tuya BLE irrigation timer).

Often, they will only work a couple of hours before stopping. I don’t need to move them (they are within range), I don’t need to change anything in config or on the actual BLE device (they work fine, I don’t ever need to touch them). It’s almost as if the ESPHome just can’t function for more than a few hours without a restart.

Has anyone experienced anything like this? And more importantly, have an idea of how to fix?

I've tried both of these configs for the ESP with the same result
esphome:
  name: ble-proxy-01
  friendly_name: ble-proxy-01

esp32:
  board: esp32dev
  framework:
    type: arduino

# Enable logging
logger:

# Enable Home Assistant API
api:
  encryption:
    key: REDACTED

ota:
  password: REDACTED

wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

  # Enable fallback hotspot (captive portal) in case wifi connection fails
  ap:
    ssid: "Ble-Proxy-01 Fallback Hotspot"
    password: REDACTED

esp32_ble_tracker:
  scan_parameters:
    interval: 1100ms
    window: 1100ms
    active: true

bluetooth_proxy:
  active: true

captive_portal:
    
substitutions:
  name: ble-proxy-01
  friendly_name: ble-proxy-01
packages:
  esphome.bluetooth-proxy: github://esphome/firmware/bluetooth-proxy/esp32-generic.yaml@main
esphome:
  name: ${name}
  name_add_mac_suffix: false
  friendly_name: ${friendly_name}
api:
  encryption:
    key: REDACTED


wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

This is the log output when it stops working ...
INFO ESPHome 2024.5.1
INFO Reading configuration /config/esphome/ble-proxy-01.yaml...
INFO Starting log output from 10.0.21.78 using esphome API
INFO Successfully connected to ble-proxy-01 @ 10.0.21.78 in 0.083s
INFO Successful handshake with ble-proxy-01 @ 10.0.21.78 in 0.120s
[13:07:30][I][app:100]: ESPHome version 2024.5.1 compiled on May 20 2024, 11:32:26
[13:07:30][C][wifi:580]: WiFi:
[13:07:30][C][wifi:408]:   Local MAC: REDACTED
[13:07:30][C][wifi:413]:   SSID: [redacted]
[13:07:30][C][wifi:416]:   IP Address: 10.0.21.78
[13:07:30][C][wifi:420]:   BSSID: [redacted]
[13:07:30][C][wifi:421]:   Hostname: 'ble-proxy-01'
[13:07:30][C][wifi:423]:   Signal strength: -61 dB ▂▄▆█
[13:07:30][C][wifi:427]:   Channel: 6
[13:07:30][C][wifi:428]:   Subnet: 255.255.254.0
[13:07:30][C][wifi:429]:   Gateway: 10.0.20.1
[13:07:30][C][wifi:430]:   DNS1: 10.0.30.43
[13:07:30][C][wifi:431]:   DNS2: 1.1.1.1
[13:07:30][C][logger:185]: Logger:
[13:07:30][C][logger:186]:   Level: DEBUG
[13:07:30][C][logger:188]:   Log Baud Rate: 115200
[13:07:30][C][logger:189]:   Hardware UART: UART0
[13:07:30][C][bluetooth_proxy:088]: Bluetooth Proxy:
[13:07:30][C][bluetooth_proxy:089]:   Active: YES
[13:07:30][C][esp32_ble:374]: ESP32 BLE:
[13:07:30][C][esp32_ble:376]:   MAC address: EC:94:CB:4B:33:AA
[13:07:30][C][esp32_ble:377]:   IO Capability: none
[13:07:30][C][esp32_ble_tracker:649]: BLE Tracker:
[13:07:30][C][esp32_ble_tracker:650]:   Scan Duration: 300 s
[13:07:30][C][esp32_ble_tracker:651]:   Scan Interval: 1100.0 ms
[13:07:30][C][esp32_ble_tracker:652]:   Scan Window: 1100.0 ms
[13:07:30][C][esp32_ble_tracker:653]:   Scan Type: ACTIVE
[13:07:30][C][esp32_ble_tracker:654]:   Continuous Scanning: True
[13:07:30][C][captive_portal:088]: Captive Portal:
[13:07:30][C][mdns:115]: mDNS:
[13:07:30][C][mdns:116]:   Hostname: ble-proxy-01
[13:07:30][C][ota:096]: Over-The-Air Updates:
[13:07:30][C][ota:097]:   Address: ble-proxy-01.local:3232
[13:07:30][C][ota:100]:   Using Password.
[13:07:30][C][ota:103]:   OTA version: 2.
[13:07:30][C][api:139]: API Server:
[13:07:30][C][api:140]:   Address: ble-proxy-01.local:6053
[13:07:30][C][api:142]:   Using noise encryption: YES
[13:08:19][D][esp32_ble_tracker:266]: Starting scan...

but nothing happens for a few minutes after the “Staring scan…”

and this is the log output after a power cycle
INFO ESPHome 2024.5.1
INFO Reading configuration /config/esphome/ble-proxy-01.yaml...
INFO Starting log output from ble-proxy-01.local using esphome API
WARNING Can't connect to ESPHome API for ble-proxy-01.local: Error resolving IP address: [Errno -5] No address associated with hostname (APIConnectionError)
INFO Trying to connect to ble-proxy-01.local in the background
INFO Successfully connected to ble-proxy-01 @ 10.0.21.78 in 0.029s
INFO Successful handshake with ble-proxy-01 @ 10.0.21.78 in 0.120s
[13:11:03][I][app:100]: ESPHome version 2024.5.1 compiled on May 20 2024, 11:32:26
[13:11:03][C][wifi:580]: WiFi:
[13:11:03][C][wifi:408]:   Local MAC: EC:94:CB:4B:33:A8
[13:11:03][C][wifi:413]:   SSID: [redacted]
[13:11:03][C][wifi:416]:   IP Address: 10.0.21.78
[13:11:03][C][wifi:420]:   BSSID: [redacted]
[13:11:03][C][wifi:421]:   Hostname: 'ble-proxy-01'
[13:11:03][C][wifi:423]:   Signal strength: -89 dB ▂▄▆█
[13:11:03][C][wifi:427]:   Channel: 6
[13:11:03][C][wifi:428]:   Subnet: 255.255.254.0
[13:11:03][C][wifi:429]:   Gateway: 10.0.20.1
[13:11:03][C][wifi:430]:   DNS1: 10.0.30.43
[13:11:03][C][wifi:431]:   DNS2: 1.1.1.1
[13:11:03][C][logger:185]: Logger:
[13:11:03][C][logger:186]:   Level: DEBUG
[13:11:03][C][logger:188]:   Log Baud Rate: 115200
[13:11:03][C][logger:189]:   Hardware UART: UART0
[13:11:03][C][bluetooth_proxy:088]: Bluetooth Proxy:
[13:11:03][C][bluetooth_proxy:089]:   Active: YES
[13:11:03][C][esp32_ble:374]: ESP32 BLE:
[13:11:03][C][esp32_ble:377]:   IO Capability: none
[13:11:03][C][esp32_ble_tracker:649]: BLE Tracker:
[13:11:03][C][esp32_ble_tracker:650]:   Scan Duration: 300 s
[13:11:03][C][mdns:115]: mDNS:
[13:11:03][C][mdns:116]:   Hostname: ble-proxy-01
[13:11:03][C][ota:096]: Over-The-Air Updates:
[13:11:03][C][ota:097]:   Address: ble-proxy-01.local:3232
[13:11:03][C][ota:100]:   Using Password.
[13:11:03][C][ota:103]:   OTA version: 2.
[13:11:03][C][api:139]: API Server:
[13:11:03][C][api:140]:   Address: ble-proxy-01.local:6053
[13:11:03][C][api:142]:   Using noise encryption: YES
[13:11:06][I][bluetooth_proxy:278]: [0] [DC:23:50:2A:2C:AB] Connecting v3 with cache
[13:11:07][D][esp32_ble_tracker:215]: Pausing scan to make connection...
[13:11:07][I][esp32_ble_client:067]: [0] [DC:23:50:2A:2C:AB] 0x00 Attempting BLE connection
[13:11:08][I][bluetooth_proxy:278]: [1] [80:6F:B0:5A:2B:1B] Connecting v3 with cache
[13:11:08][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_CONNECT_EVT
[13:11:08][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_OPEN_EVT
[13:11:08][I][esp32_ble_client:154]: [0] [DC:23:50:2A:2C:AB] Connected
[13:11:08][I][esp32_ble_client:067]: [1] [80:6F:B0:5A:2B:1B] 0x00 Attempting BLE connection
[13:11:08][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_REG_FOR_NOTIFY_EVT
[13:11:09][D][esp32_ble_client:306]: [0] [DC:23:50:2A:2C:AB] Event 46
[13:11:09][D][esp32_ble_client:188]: [0] [DC:23:50:2A:2C:AB] cfg_mtu status 0, mtu 23
[13:11:09][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_DESCR_EVT
[13:11:09][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:09][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:09][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_NOTIFY_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:10][D][esp32_ble_client:110]: [0] [DC:23:50:2A:2C:AB] ESP_GATTC_WRITE_CHAR_EVT
[13:11:15][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_CONNECT_EVT
[13:11:15][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_OPEN_EVT
[13:11:15][I][esp32_ble_client:154]: [1] [80:6F:B0:5A:2B:1B] Connected
[13:11:15][D][esp32_ble_tracker:266]: Starting scan...
[13:11:17][D][esp32_ble_client:306]: [1] [80:6F:B0:5A:2B:1B] Event 46
[13:11:17][D][esp32_ble_client:188]: [1] [80:6F:B0:5A:2B:1B] cfg_mtu status 0, mtu 247
[13:11:17][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_READ_CHAR_EVT
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_READ_CHAR_EVT
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_REG_FOR_NOTIFY_EVT
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_WRITE_DESCR_EVT
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_WRITE_CHAR_EVT
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_NOTIFY_EVT
[13:11:18][D][esp32_ble_client:306]: [1] [80:6F:B0:5A:2B:1B] Event 39
[13:11:18][I][esp32_ble_client:084]: [1] [80:6F:B0:5A:2B:1B] Disconnecting.
[13:11:18][D][esp32_ble_client:110]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_CLOSE_EVT
[13:15:48][I][ota:117]: Boot seems successful, resetting boot loop counter.
[13:15:48][D][esp32.preferences:114]: Saving 1 preferences to flash...
[13:15:48][D][esp32.preferences:143]: Saving 1 preferences to flash: 0 cached, 1 written, 0 failed
[13:16:15][D][esp32_ble_tracker:266]: Starting scan...
[13:16:18][I][bluetooth_proxy:278]: [1] [80:6F:B0:5A:2B:1B] Connecting v3 with cache
[13:16:18][D][esp32_ble_tracker:215]: Pausing scan to make connection...
[13:16:18][I][esp32_ble_client:067]: [1] [80:6F:B0:5A:2B:1B] 0x00 Attempting BLE connection
[13:16:38][I][esp32_ble_client:084]: [1] [80:6F:B0:5A:2B:1B] Disconnecting.
[13:16:48][D][esp32_ble_client:172]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_DISCONNECT_EVT, reason 256
[13:16:48][D][esp32_ble_tracker:266]: Starting scan...
[13:16:48][I][bluetooth_proxy:278]: [1] [80:6F:B0:5A:2B:1B] Connecting v3 with cache
[13:16:48][D][esp32_ble_tracker:215]: Pausing scan to make connection...
[13:16:48][I][esp32_ble_client:067]: [1] [80:6F:B0:5A:2B:1B] 0x00 Attempting BLE connection
[13:17:08][I][esp32_ble_client:084]: [1] [80:6F:B0:5A:2B:1B] Disconnecting.
[13:17:18][D][esp32_ble_client:172]: [1] [80:6F:B0:5A:2B:1B] ESP_GATTC_DISCONNECT_EVT, reason 256
[13:17:18][D][esp32_ble_tracker:266]: Starting scan...
[13:17:18][I][bluetooth_proxy:278]: [1] [80:6F:B0:5A:2B:1B] Connecting v3 with cache
[13:17:18][D][esp32_ble_tracker:215]: Pausing scan to make connection...
[13:17:18][I][esp32_ble_client:067]: [1] [80:6F:B0:5A:2B:1B] 0x00 Attempting BLE connection

where it starts reporting values for the BLE devices nearby.

If i see correct you have arduino framework. Did you try esp-idf? It’s recommended over Arduino…

These lines are only for a board connected via Ethernet. Remove them if that’s not the case.

EDIT: If setting up from HA UI, it automatically makes it arduino, so that was Home Assistant’s choice, not mine.

Thanks both, I have tried this and will see how it behaves.

Update:

After 2h30, all the BLE devices became “unavailable” again, and have been so for about 15 minutes.

As before, power cycling restores.

This is the "new" config as recommended above
esphome:
  name: ble-proxy-01
  friendly_name: ble-proxy-01

esp32:
  board: esp32dev
  framework:
    type: esp-idf

# Enable logging
logger:

# Enable Home Assistant API
api:
  encryption:
    key: "SZudq9V2JxAU1zsu/3vqAySh12QqJ6o2b7/T0e38ltU="

ota:
  password: "a5fc51a0059b2c3d776f8bd315579d72"

wifi:
  ssid: !secret wifi_ssid
  password: !secret wifi_password

  # Enable fallback hotspot (captive portal) in case wifi connection fails
  ap:
    ssid: "Ble-Proxy-01 Fallback Hotspot"
    password: "gsbZ2Jw6MCQC"

esp32_ble_tracker:
  scan_parameters:
    active: true

bluetooth_proxy:
  active: true

captive_portal:
    

That’s why you have to read esphome’s help for each thing you add into esphome, for BT it states that esp idf is recommended for bt. Esphome just selects defaults…

Back to topic: i’d change esp module first and see if module is faulty. Another thing is power supply: is it good quality? Strong enough?

So, I changed:

But after a couple of days of testing (at least one where I also removed the ESP32 from direct sun, so it won’t overheat), the issue persists.

At first, it looked like it only occasionally dropped the BLE connections for a few minutes, and they came back. But that only lasts for less than half a day, then it’s back to needing a power cycling.

When it’s not working, this is what I see in the logs (I waited for a few minutes, and nothing more showed up):

INFO ESPHome 2024.5.2
INFO Reading configuration /config/esphome/esp32-bluetooth-proxy-6e7034.yaml...
INFO Starting log output from 10.0.21.79 using esphome API
INFO Successfully connected to esp32-bluetooth-proxy-6e7034 @ 10.0.21.79 in 0.106s
INFO Successful handshake with esp32-bluetooth-proxy-6e7034 @ 10.0.21.79 in 0.106s
[17:25:10][I][app:100]: ESPHome version 2024.5.2 compiled on May 21 2024, 08:14:38
[17:25:10][I][app:102]: Project esphome.bluetooth-proxy version 1.0
[17:25:10][C][wifi:580]: WiFi:
[17:25:10][C][wifi:408]:   Local MAC: [redacted]
[17:25:10][C][wifi:413]:   SSID: [redacted]
[17:25:10][C][wifi:416]:   IP Address: 10.0.21.79
[17:25:10][C][wifi:420]:   BSSID: [redacted]
[17:25:10][C][wifi:421]:   Hostname: 'esp32-bluetooth-proxy-6e7034'
[17:25:10][C][wifi:423]:   Signal strength: -65 dB ▂▄▆█
[17:25:10][C][wifi:427]:   Channel: 6
[17:25:10][C][wifi:428]:   Subnet: 255.255.254.0
[17:25:10][C][wifi:429]:   Gateway: 10.0.20.1
[17:25:10][C][wifi:430]:   DNS1: 10.0.30.43
[17:25:10][C][wifi:431]:   DNS2: 1.1.1.1
[17:25:10][C][logger:185]: Logger:
[17:25:10][C][logger:186]:   Level: DEBUG
[17:25:10][C][logger:188]:   Log Baud Rate: 115200
[17:25:10][C][logger:189]:   Hardware UART: UART0
[17:25:10][C][bluetooth_proxy:088]: Bluetooth Proxy:
[17:25:10][C][bluetooth_proxy:089]:   Active: YES
[17:25:10][C][safe_mode.button:022]: Safe Mode Button 'Safe Mode Boot'
[17:25:10][C][safe_mode.button:022]:   Icon: 'mdi:restart-alert'
[17:25:10][C][esp32_ble:374]: ESP32 BLE:
[17:25:10][C][api:139]: API Server:
[17:25:10][C][api:140]:   Address: esp32-bluetooth-proxy-6e7034.local:6053
[17:25:10][C][api:142]:   Using noise encryption: YES
[17:25:10][C][improv_serial:032]: Improv Serial:

EDIT:

And I’ve tried with both a generic 4A power supply (that I used to run a Raspberry Pi 3 on with no issues or low voltage warnings), and an official 10W Apple iPad power supply, same result.

I should also mention that I have two different ESP BLE Proxy (one for Plant sensors and water irrigation in rthe garden, the other for Airthings Wave Radon sensors in the house) that both lose connection to their BLE devices, though I haven’t been as keen measuring how often for the radon sensors.

Had a similar issue.

This helped me to find a workaround:
I did implement a template sensor to count the free connections:

  - platform: template
    name: "BT Proxy Connections Free"
    id: bluetooth_proxy_connections_free
    icon: "mdi:bluetooth-settings"
    update_interval: 30s
    accuracy_decimals: 0
    entity_category: "diagnostic"
    lambda: |-
      int free = bluetooth_proxy::global_bluetooth_proxy->get_bluetooth_connections_free();
      ESP_LOGD("bluetooth_proxy_sensor", "Current connections free => %d", free);
      return free;

Source: Template Sensor for Bluetooth Proxy

This made me realise that a connection was no longer possible because there were no more free connections. The cause was that some device was not terminating the Bluetooth connection properly and over time more and more connections were being used up.

I am still trying to find the actual cause on my Bluetooth device (Gardena valve). At the moment my guess is a low battery in the valve or too much distance between the valve and the proxy.

As a workaround, I restart the proxy as soon as the number of open connections on the proxy remains constant for 10 minutes (via an automation in Home Assistant). This happens 5-7 times a day.