ESPHome 2026.8.0: Bluetooth on more chips than ever

Release Overview
Section titled “Release Overview”ESPHome 2026.8.0 brings Bluetooth to more chips than ever: a new platform-neutral BLE layer moves all 39 BLE
sensor platforms off their ESP32-only foundation and powers new BLE trackers, and Bluetooth Proxy, on the
Raspberry Pi Pico W, BK72xx and LN882H. Builds get dramatically faster with ccache support on ESP8266, LibreTiny,
RP2040 and host, ESP-IDF toolchain installs shrink by roughly half, and ESP32 crash reports now capture the
faulting address. The release also delivers multi-interface networking with Ethernet and WiFi in one config, a
major Modbus overhaul with the new modbus_client component, multi-key OTA signature verification, and runtime
wake word management, alongside new components including the LD6002B 60 GHz presence radar and Hörmann garage
door support. The bundled Device Builder brings faster startup, parallel uploads, and one-click config
migration. The beta cycle also fixed ESP32 BLE trackers and proxies missing advertisements alongside WiFi on
ESP-IDF 5.5.5, and encrypted API connections and OTA uploads on ESP8266 that stalled for seconds now complete in
well under one second.
Upgrade Checklist
Section titled “Upgrade Checklist”- If you set
esp32_ble_idexplicitly on any BLE sensor platform, rename it toble_hub_id(the old key warns until 2027.2.0) - If you use
vocornoxsensor keys onsgp4x,sen5xorsen6x, rename them tovoc_indexandnox_index - If you use
command_throttleonmodbus_controller, move the setting toturnaround_timeon themodbuscomponent;allow_duplicate_commandsno longer has any effect - If you use
modbus_serverwithaddress: 0, assign a unique address from 1-247 instead - If you use
modbus_controllersensors withcustom_command: [0x17, ...], subtract one from theiroffset: - If you write
modbus_controllerlambdas, notedatais nowstd::spanandpayload_to_number()returns an optional, so add.value_or(0)or a check - If you use the
aqisensor, expect readings above the previous caps (301US AQI,101CAQI) to report real interpolated values during heavy pollution - If you use an
rc522_i2creader that relied on the old default address, setaddress: 0x2Cexplicitly - If you use LVGL animations with
ease_in/ease_outweights greater than 1.0, remove them; they are now rejected at validation - If you have a custom web server frontend or integration, update it for the new
idformat and thealarm_control_paneldomain spelling - If you use
pin: TEMPERATUREon theadcsensor for the RP2 on-die sensor, migrate to theinternal_temperaturecomponent - If your automations relied on non-iBeacon Apple manufacturer payloads being parsed as iBeacons, note these no longer match
- If you use
rgb_order,is_rgbworis_wrgbonesp32_rmt_led_strip,beken_spi_led_striporrp2040_pio_led_strip, switch to the singlechannel_colorskey (the old keys warn until 2027.3.0) - If you set
inverted: trueorallow_other_uses: trueon aninterrupt_pinforpcf8574,pca9554,tca9555,pca6416a,pi4ioe5v6408ormcp23016, remove them; both are now rejected at validation
Bluetooth on More Chips: Platform-Neutral BLE
Section titled “Bluetooth on More Chips: Platform-Neutral BLE”Led by @Bl00d-B0b across dozens of PRs, this release completes a major architectural
effort: the shared BLE advertisement layer moved out of esp32_ble_tracker into a new platform-neutral
ble_device_base component (#17150), and every one of the 39
advertisement-based BLE sensor platforms was migrated onto it in a 13-batch series
(#17716 through
#18183). BLE sensors like ble_rssi, atc_mithermometer,
BTHome, Mopeka, RuuviTag and the entire Xiaomi family are no longer tied to ESP32; they work on any chip with a
BLE tracker.
New BLE trackers this release:
- Raspberry Pi Pico W / Pico 2 W - the new rp2_ble_tracker scans passively and actively while WiFi holds an API connection
- BK72xx (Beken) - bk72xx_ble_tracker by @Bl00d-B0b brings BLE 5.x scanning to the chips inside many Tuya-based wall switches, thermostats and smart plugs, validated in production on a 20-device fleet
- LN882H - ln882h_ble_tracker by @Bl00d-B0b adds BLE 5.1 scanning with scan-response merging on LibreTiny LN882H devices
Bluetooth Proxy beyond ESP32: bluetooth_proxy now consumes the neutral layer (#17880), so more chips can feed advertisements to Home Assistant. The Pico W goes further: it supports full active connections (#18132) and now offers 3 connection slots with ESP32 parity (#18247), so Home Assistant can read, write and subscribe to BLE devices through a Pico W proxy. BK72xx gained active scanning by packing the vendor SDK’s start command (#18169), which admitted it to Bluetooth Proxy as well.
One config note: on migrated sensor platforms the auto-generated tracker reference key esp32_ble_id: is now
ble_hub_id:. Most configs never set it explicitly; those that do keep validating with a warning until
2027.2.0. See the Breaking Changes section for details.
ESP32 scan window with WiFi: ESP-IDF 5.5.5 fixed a coexistence bug that made BLE scans run far longer than
the configured window, and the default 30 ms window in a 320 ms interval had been relying on it; with the fix the
scanner listened only 9.4% of the time and trackers and proxies missed most advertisements alongside WiFi from
2026.7.1 on. With WiFi coexistence on ESP-IDF 5.5.5 or newer the
esp32_ble_tracker window now defaults to the interval, as Espressif
recommends; an explicit window is never changed (#18356).
bk72xx_ble also stops code generation with a clear message on Beken chips without a BLE 5.x stack (BK7231T,
BK7251, BK7231Q) instead of failing minutes into the build (#18406).
ESPHome Device Builder
Section titled “ESPHome Device Builder”This section covers everything that changed in the bundled ESPHome Device Builder since the 2026.7.0 release notes. Device Builder updates also ship in ESPHome patch releases for as long as the changes remain safe to include, so some of what follows already reached you during the 2026.7.x cycle; the rest is new with this release.
Faster Startup
On a small host with a lot of devices, the dashboard used to finish scanning every configuration before it would serve its first page. It now serves immediately from a shallow device scan and fills in the details in the background (#2514), and work not needed to serve that first page, from preferences loading to MQTT broker discovery, moved off the startup critical path or got cheaper (#2500, #2501, #2503). The validated-config cache is also read in the new JSON format ESPHome 2026.8 writes, so upgrading does not throw the cache away (#2517).
More Updates at Once
Updates used to upload to one device at a time. Uploads now run in parallel: four at a time, and up to nine when the Device Builder is running ESPHome 2026.8 or newer, whose leaner CLI fast paths keep that many upload subprocesses cheap (#2206, #2515, #2518). Queued offline updates benefit the most: a batch of deep sleep devices waking around the same time collect their queued updates concurrently instead of queueing behind one another (#2192), a freshly flashed deep-sleep device gets its new version read in a quick burst before it goes back to sleep (#2146), and the install dialog follows the flash that happens when the device wakes, so you can watch a queued update land (frontend#1616).
One-Click Config Migration
ESPHome renames configuration keys from time to time, and keeping up has been a manual chore. The Device Builder can
now migrate a configuration for you: when a config contains something with a known migration, the editor offers to
apply it, and the offer is backed by a backend dry run so it only appears when the migration will actually succeed
(#2432,
frontend#1538,
frontend#1550). The rules are discovered from the live
ESPHome schema rather than hand-maintained, covering renamed keys and component aliases
(#2444,
#2462), the rp2040 to rp2 platform rename
(#2460,
#2463,
frontend#1567), and the legacy api services
spelling, which is read on load and respelled to the canonical form on write
(#2420,
frontend#1534). Newest of all, a device whose config
has a pending migration shows a dot on its card and table row, and clicking it opens the editor to apply the migration
(#2563,
frontend#1652,
frontend#1653). The offer now names each change it
will make and shows a preview (frontend#1662),
only proposes migrations the installed ESPHome supports
(#2602), and covers the LED strip channel_colors rename
introduced in this release (#2585,
#2596,
#2600).
The Structured Editor Rounds Out
The structured editor spent this cycle learning to leave your file alone. Editing through the forms now preserves the
comments and flow style of the YAML it touches
(frontend#1377,
frontend#1380,
frontend#1383,
frontend#1386,
frontend#1387), and ${substitution} references
render and stay editable in pin and numeric fields instead of being clobbered by the widget
(frontend#1342,
frontend#1344,
frontend#1347,
frontend#1511). Lambdas on templatable fields are no
longer flagged as invalid (frontend#1529), and an
automation using an action the catalog does not know stays editable, rendering that one action read-only in place
instead of locking you out of the whole automation
(#2351,
frontend#1513).
The pin field gained guided wiring presets that show where to connect the part
(frontend#1412), and boards whose hardware fixes a pin
lock the GPIO select to it (frontend#1419). The
add-component dialog handles dependency chains as a stack of detours, so adding a component that needs a bus walks you
through creating the bus and returns you to where you were
(frontend#1586), detours to a new uart when no
existing bus can host the component (frontend#1554),
and prefills entity names and unique IDs
(frontend#1552,
frontend#1553). The YAML hints from 2026.7.0 grew new
one-click fixes: an empty or commented-out block behind expected a dictionary is named and fixed for you
(frontend#1314,
frontend#1316), and a stray top-level key that belongs
to the section above it is offered an indent fix
(frontend#1319).
Troubleshooting and Crash Reporting
The status badges on a device now open a connectivity troubleshooting dialog, which runs an on-demand probe from the Device Builder to the device and reports what worked and what did not (#2485, frontend#1597). Reporting problems got easier too: the bug report flow gained an optional device picker that attaches the selected device’s configuration with credentials masked (frontend#1595, frontend#1591), crash reports are titled by where the crash happened (frontend#1584), and the log viewer gained a crash report button (frontend#1250). Crashes captured over Web Serial have their backtraces decoded (#2105), including firmware compiled by a build server, through a hosted decoder (#2140), and Web Serial installs surface esptool-js connect diagnostics in the install log (frontend#1651).
Status You Can Trust
A run of work went into making Online, Offline, and the deployed version mean what they say. mDNS ownership now requires live evidence and honors goodbye packets, so a stale record can no longer keep a dead device Online or attach one device’s identity to another (#2376, #2386, #2393, #2395), stale addresses are dropped when a device is retargeted (#2488), and the device table’s Version column only shows a version the Device Builder can actually trust (frontend#1283). Renaming or cloning a device retargets its generated fallback-AP SSID (#2247), and MQTT device discovery now supports TLS brokers (#2256).
Windows
The Windows Device Builder had a round of hardening: the ESP-IDF toolchain is shared at a short path so deep build
trees fit inside MAX_PATH (#2281), the compile subprocess
tree runs in UTF-8 mode (#2283), cancelling a build actually
stops the running compile (#2554), and toolchain subprocesses
can no longer pop blocking “Bad Image” error dialogs
(#2569).
Remote Builds and Home Assistant
Build servers now advertise a friendly name, which shows up across the UI and in the pairing handshake (frontend#1252, #2526), and while remote building is off the dashboard shows a neutral Disabled badge with a turn-on action instead of hiding the feature (frontend#1392). Imported bundles upload over HTTP instead of the WebSocket, with a much higher size cap and an actionable error when a bundle still does not fit (#2340, #2320, #2324), and a dialog following a job reattaches after a connection loss instead of failing (frontend#1570). Home Assistant adoption gained an encryption-key handoff with adoption key reuse (#2496), and a device broadcasting its factory name is adopted under that name with the rename flow started for you (frontend#1533).
Beyond the headlines: configuration files are written atomically, so a crash mid-write can no longer leave a partial
file (#2188,
#2190), and a secrets.yaml with operator-set permissions
keeps them across rewrites (#2202). First-time installs are
guided to USB instead of a queued OTA that could never arrive
(frontend#1282), and the device card’s action buttons
and indicator icons gained tooltips (frontend#1280).
@stvncode moved toasts to the bottom-right corner
(frontend#1366) and refined the quickstart tour and
desktop setup flow (frontend#1334,
frontend#1337),
@rwalker777 labels compile-only jobs for offline devices as Offline Compile
(frontend#1266),
@jesserockz made ESPHome Web a standalone build target of the frontend
(frontend#1139),
@elcaptain put the official monochrome ESPHome logomarks in the header and navigation
(frontend#1141), and
@breti kept the UI copy honest across the release
(frontend#1409,
frontend#1428,
frontend#1521).
Faster Builds and Smaller Toolchain Installs
Section titled “Faster Builds and Smaller Toolchain Installs”Compilation now runs through ccache when it is installed on ESP8266, LibreTiny, RP2040 and host builds
(#17722,
#17726,
#17727,
#17728), matching what ESP-IDF builds already did. The cache is
shared across devices and projects, so a fleet of similar devices compiles almost entirely from cache: in testing,
six Sonoff S31 devices built in 15 seconds for the first and 4 to 5 seconds for each of the rest. Set
ESPHOME_CCACHE_ENABLE=0 to opt out; esphome clean-all removes the cache. A ccache on
PATH that does not run (a stale shim or a .bat wrapper on Windows) is now detected and skipped instead of
failing every compile step (#18407), the wrapper path is made
safe for cmd.exe so the ccache bundled with ESPHome Desktop works
(#18495), and framework downloads retry transient network
errors with a short backoff (#18330).
ESP-IDF installs also slimmed down considerably:
- Only the toolchains for the variants you build are installed (#17688), roughly halving a fresh install; the RISC-V toolchain alone is a 292 MB download and 2.0 GB on disk
- The gdb and ULP toolchains ESPHome never runs are skipped (#17687)
- Tool download caches are pruned after install (#17661)
Leaner and More Responsive CLI
Section titled “Leaner and More Responsive CLI”A long series of changes trimmed the esphome upload and esphome logs fast paths, which matters because the
device builder runs several of these subprocesses concurrently. Imports the fast path never uses are now
deferred (#18093,
#18105), and the validated-config cache is stored as JSON so a
cache hit never loads the YAML stack (#18106); cache parsing
dropped from 1-2 ms to 0.05 ms and the upload subprocess uses measurably less RAM.
Log and build output streaming also improved: output flushes live instead of buffering (#18261, #18264), complete lines are no longer held back behind an unfinished one (#18279), and an out-of-flash build now shows the helpful tip instead of crashing (#18280).
esphome logs can now also tail a device over the web_server event stream
(#17110), so a device with web_server: but no api: can
finally be followed from the CLI. The native API is still preferred, then MQTT, then the web server.
The beta cycle also removed some stalls. esphome logs no longer blocks for up to 25 seconds on MQTT IP
discovery when it already has a usable address; the lookup runs concurrently and feeds any address it finds
into the running client (#18313). esphome upload retries
network-level OTA failures such as a connect timeout or the device closing the connection mid-handshake, while
device-reported errors still fail immediately (#18332). The
component alias map is read from a generated registry instead of scanning all 744 component directories on every
CLI start, the source of a startup regression on slow hosts like the HA Green
(#18335), and PYTHONPATH no longer leaks into build
subprocesses (#18360).
Better ESP32 Crash Reports
Section titled “Better ESP32 Crash Reports”The esp32 crash handler now captures the faulting memory address (EXCVADDR on Xtensa, MTVAL on RISC-V) and the
raw exception cause, so heap corruption and pointer bugs leave a usable trail in the post-reboot report
(#17769). Crash records are also stamped with the build they
were captured by (#17770): a record left over from a previous
firmware is flagged instead of being decoded against the wrong ELF, which used to produce convincing but
meaningless backtraces. The addr2line hint is now one line per core, so decoders no longer merge two unrelated
stacks into one impossible call chain (#18418).
Ethernet and WiFi Together: Multi-Interface Networking
Section titled “Ethernet and WiFi Together: Multi-Interface Networking”Built by @rwalker777 and @kbx81, ESP32 devices can
now configure both ethernet: and wifi: in the same YAML. A new network: priority: list declares which
interface the device prefers (#14255), and the default route is
arbitrated at runtime from that list (#17797): the first
connected interface in your priority order carries the traffic, DNS follows the active interface, and failover
plus failback happen automatically within milliseconds of a link change. Verified on hardware with cable pulls,
VLAN changes and runtime enable/disable cycles. See network for configuration.
ESP8266 Networking and Stability
Section titled “ESP8266 Networking and Stability”Encrypted API connections took 2.5 to 3.3 seconds to establish on ESP8266, against about 63 ms on ESP32. WiFi and lwIP run in a cooperative context that only executes when the sketch yields, so a busy main loop let the WiFi RX queue overflow and TCP stalled on retransmission. Rate-limited yields in the raw TCP read and write paths (#18455) and inside the handshake crypto (#18473) took a device that stalled on every attempt to 0 stalls in 24 attempts, with a 357 ms median. OTA uses the same paths and benefits equally. The noise-c library behind the encrypted API was also bumped from 0.1.11 to 0.1.21 along the way, freeing about 670 bytes of heap per encrypted connection and making message encryption and decryption 13 to 31% faster in benchmarks (#18451, #18482, #18484).
Three crash classes are gone as well: a LoadProhibited in cnx_node_search after a WiFi disconnect, seen on
ratgdo and Athom devices, fixed by taking the STA interface down before lwIP can transmit into the freed driver
(#18333); watchdog resets from the software serial RX interrupt
posting a main loop wake for every byte, now only when no wake is pending
(#18416); and a reboot when the captive portal shut down after
WiFi connected, because deleting the web server also deleted the captive portal mid-teardown, which broke Improv
serial provisioning on the esphome-web ESP8266 image and applies to every ESPAsyncWebServer platform (ESP8266,
RP2040, LibreTiny, LN882x) (#18324).
Performance Optimizations
Section titled “Performance Optimizations”Several components stopped doing busy-work on every loop iteration:
- espnow no longer polls the WiFi driver every loop and disables its loop entirely while idle (#18027); it was one of the most expensive idle components at 0.056 ms per iteration, and its idle cost is now zero
- script components with queued mode stop polling while the queue is empty (#18121)
- improv_serial reduced its per-loop overhead (#16019)
- The blocking-warning log time no longer cascades into false warnings for subsequent components (#17710)
Modbus Overhaul Continues
Section titled “Modbus Overhaul Continues”Led by @exciton, the multi-release Modbus rework reached a milestone. The
modbus_controller message handling was rebuilt (#11781):
commands from all controllers now share the hub’s queue fairly (previously some controllers could starve),
responses are routed straight back to the command that sent them so a reply can no longer be applied to the
wrong sensor, offline devices are tracked per device instead of per command, and the common command path is
heap-free. Two controllers may now even share one device address to poll at different intervals.
A new modbus_client component (#17676) enables ad-hoc Modbus transactions straight from YAML automations, with typed read/write actions (#18078), a plain device handle for lambdas (#18146), and read/write multiple registers in one transaction (#18215).
Server mode grew too, with contributions from @zweckj and @marpi82: coil and discrete-input support (#17464), read/write multiple registers (function code 0x17, #17357), spec-compliant broadcast writes (#17387) and byte-swapped word types (#17829).
Note that command_throttle and allow_duplicate_commands on modbus_controller are deprecated and no longer
have any effect; use turnaround_time on the modbus hub instead. See Breaking Changes for migration details.
Multi-Key OTA Signature Verification
Section titled “Multi-Key OTA Signature Verification”For externally signed firmware, @kbx81 added ESPHome-side OTA signature verification with a compiled-in trusted key list (#17981). An update is accepted if any of up to three signature blocks matches a trusted key, which enables signing key rotation (dual-sign a bridge release with old and new keys) and independent backup keys across signing providers. Bootloader updates are now signature-checked as well, closing a path where they previously installed unverified. See the OTA documentation for setup.
Voice and Media
Section titled “Voice and Media”@kahrendt landed the groundwork for wake words that are not baked into firmware:
micro_wake_word can now add and remove wake word models at runtime
(#17927). Models load into PSRAM with validation, the models
option is now optional, and a follow-up voice assistant integration will download models advertised by Home
Assistant.
The sendspin media player gained an image platform for album and artist artwork (#17937): artwork decodes into double-buffered frames a display or LVGL can draw, with optional cross-fade transitions.
New Components
Section titled “New Components”- ld6002b by @hepter, built across 5 PRs (#17819 onward): the Hi-Link HLK-LD6002B 60 GHz 3D presence radar, with per-target position tracking, configurable detection zones, interference areas, sensitivity and power management
- hoermann_hcp by @zweckj: controls Hörmann garage door motors over the HCP bus, with cover control (#17355), garage light (#18190) and a connectivity sensor (#18189)
- ds248x by @tomwellnitz: DS2482-100/-101/-800 and
DS2484 I²C-to-1-Wire bridges as a
one_wireplatform, so Dallas temperature sensors can hang off up to 8 bridged channels (#12717) - zephyr_pwm by @wiomoc: PWM outputs on nRF52 (#16483)
- modbus_client by @exciton, covered in the Modbus section above
New Hardware Support
Section titled “New Hardware Support”- CH390 SPI Ethernet by @ptr727: the WCH CH390 single-chip 10/100 MAC and PHY joins the ethernet component, verified at 100 Mbps full duplex (#18226)
- Displays: the JC8012P4A1-V2 panel revision for mipi_dsi by @rayz90 (#17457), the Waveshare ESP32-S3-Touch-LCD-3.5B (#17513) and the ST77916-based ESP-VoCat round display by @rggammon (#17679) for mipi_spi, the Guition JC8012P4A1 touchscreen for gsl3670 by @mpoettgen (#17843), and the 7-color Soldered Inkplate 6COLOR e-paper by @franFodor (#17717)
- OpenThread diagnostics by @Ardumine: 13 new numeric sensors exposing MAC and MLE counters plus parent link quality and RSSI (#17276)
- Addressable LED channel order by @peterkeen and
@jesserockz: esp32_rmt_led_strip,
beken_spi_led_strip and
rp2040_pio_led_strip now describe their channel layout with a single
channel_colorskey, any permutation ofR,GandBwith an optionalWanywhere (GRBW,WRGB,RWGB), replacingrgb_order,is_rgbwandis_wrgb; the RP2040 strip gains white-channel positioning as a result, and the old keys keep working with a warning naming the replacement until 2027.3.0 (#18028, #18474) - Haier short IR messages for remote_transmitter and remote_receiver by @ssieb (#17826), and configurable I2S PDM microphone downsampling by @egormanga (#17751)
Other Notable Features
Section titled “Other Notable Features”- Deep sleep wake automations by @jesserockz: the new
on_waketrigger on deep_sleep fires when the device wakes with the wake cause, and eachesp32_ext1_wakeuppin can carry its ownon_wakeso different wake buttons perform different actions (#17569) - Mitsubishi CN105 vane control by @crnjan: the component gained a top-level
hub, a vertical vane direction select, a vane state trigger and a
vane.controlaction (#16987, #16723, #16727, #16737) - LVGL by @clydebarrow: runtime theme updates via
lvgl.theme.update(#17678), widget stacking control vialvgl.widget.set_z_index(#17993), and apauseoption forround_tripanimations (#17574) - AQI over-range handling by @jasstrong: hazardous air quality now
interpolates correctly across 301-500 instead of pinning at 301, with a new
extended_rangeoption to extrapolate beyond 500 (#17570) - Zigbee improvements by @luar123 and
@TesseractTimmee: an
on_startautomation, automatic rejoin after network failure, leave-on-factory-reset, sensor resolution attributes and more units (#18009, #18008, #17973); esp-zigbee-sdk is bumped to 2.0.4, which lets the coordinator remove an end device that is not its direct child and has routers send an explicit rejoin request (#18415) - CC1101 tuning options by @hn: frequency offset compensation and bit synchronization registers are now configurable from YAML for narrowband protocols like wM-Bus (#17577)
- Modbus garage doors and more covered in the Modbus section above
Notable Bug Fixes
Section titled “Notable Bug Fixes”- ESP32-P4:
variant: esp32p4without aboard:built the pre-v3 bootloader layout since 2026.7.0 and bootlooped on production (v3.x) silicon; the production layout is now the default, withengineering_samplestill available for pre-release chips (#18500) - image:
defaults:andfiles:work again onimage:platform entries (file,animation,online_image) to share options across several images, not only through the legacy format migration (#18032) - ld2420: An unknown command error from the radar indexed past a three-entry message table and caused a boot loop (#18322), and the component no longer shares the UART bus setup priority, which could run its setup before the bus was ready and leave the bus dead on ESP-IDF (#18428)
- Modbus custom commands: Responses with a function code outside the user-defined ranges (65-72 and 100-110),
such as the
0x49used by Sofar inverters, were dropped as parse failures since 2026.7 because only user-defined codes fell back to the CRC scan for the frame end. Every function code of unknown length is now CRC-scanned, and a server hub answers such a request withILLEGAL_FUNCTIONinstead of silence (#18483) - Sensor delta filter: NaN passes through again, so a
timeout:filter followed bydelta:marks the sensor unavailable instead of holding the last valid reading forever; this had been lost in 2026.2.0 (#18400) - Entity keys: The beta hashed API entity keys from the raw name, which made Home Assistant recreate every entity on first connect and drop helpers tied to them. Keys are back to the sanitized object ID hash for this release; the config-time duplicate check is kept (#18361)
- rotary_encoder: The reset pin now sets
min_valueinstead of0when the minimum is above zero (#18197) - esp32_ble: The
LOCAL_IRandLOCAL_ERGAP events the stack raises on first boot after a flash no longer log an “unexpected GAP event” warning (#18359) - cv.parse_esphome_version: Restored as a deprecated helper after its removal broke external components that
call it; it warns and points at
cv.require_esphome_version, and goes away in 2027.2.0 (#18366) - sendspin: sendspin-cpp 0.7.2 fixes the artwork image’s
on_clearnever firing (#18316)
Thank You, Contributors
Section titled “Thank You, Contributors”This release includes 348 pull requests from over 40 contributors. A huge thank you to everyone who made 2026.8.0 possible:
- @Bl00d-B0b - 42 PRs including the platform-neutral
ble_device_baselayer, the new BK72xx and LN882H BLE trackers, and the 13-batch migration of every BLE sensor platform - @jesserockz - 29 PRs including
deep_sleepon_waketriggers, RP2 platform cleanups and internal temperature fixes, and CI improvements - @swoboda1337 - 27 PRs including clang-tidy coverage for RP2 and LibreTiny, vendor SDK compatibility fixes, and security hardening
- @exciton - 25 PRs including the
modbus_controllerrefactor and the newmodbus_clientcomponent with typed actions - @kbx81 - 10 PRs including multi-key OTA signature verification, network
default-route arbitration, and the
veml3235auto-gain overhaul - @kahrendt - 7 PRs including runtime wake word model management and the
sendspinartwork image platform - @zweckj - 6 PRs including the new
hoermann_hcpgarage door component and Modbus server broadcast and 0x17 support - @bharvey88 - 6 PRs including the Sensirion
voc_index/nox_indexrenames andcv.rename_keyimprovements - @hepter - 6 PRs including the new
ld6002b60GHz presence radar component - @crnjan - 5 PRs including the
mitsubishi_cn105hub extraction and vertical vane control - @clydebarrow - 5 PRs including new LVGL actions and display models
- @tomaszduda23 - 4 PRs including nRF52 OTA support for the Adafruit bootloader and Zigbee radio stats
- @marpi82 - 3 PRs including byte-swapped Modbus word types with tests
- @luar123 - 3 PRs including Zigbee network handling improvements and the
on_startautomation - @p1ngb4ck - 2 PRs including
mcp4461persistence and wiper actions - @hn - 2 PRs including CC1101 frequency offset compensation options
- @jeroen85 - 2 PRs including OpenTherm and blocking-warning log fixes
- @egormanga - 2 PRs including I2S PDM microphone DSR selection
- @ximex - 2 PRs including unit capitalization fixes
- @ssieb - 2 PRs including Haier short IR message support
- @ptr727 - 2 PRs including CH390 SPI Ethernet support
- @TesseractTimmee - 2 PRs including Zigbee sensor resolution and units
- @tomwellnitz - the new
ds248xI²C-to-1-Wire bridge component - @rwalker777 - network priority for multi-interface support
- @wiomoc - the new
zephyr_pwmplatform for nRF52
Also thank you to @bdraco, @ShaTie, @Eelviny, @stas-sl, @jhenkens, @Rocco83, @matt123p, @rwrozelle, @jptrsn, @Ardumine, @rayz90, @lsellens, @ljungqvist, @jasstrong, @rggammon, @zerafachris, @franFodor, @mpoettgen, @kobihikri, @peterkeen, @youkorr for their contributions, and to everyone who reported issues, tested pre-releases, and helped in the community.
Breaking Changes
Section titled “Breaking Changes”BLE Sensor Platforms
Section titled “BLE Sensor Platforms”- All BLE sensor platforms: The auto-generated tracker reference key
esp32_ble_idis renamed toble_hub_idon every advertisement-based BLE platform (ble_presence,ble_rssi,ble_scanner, the mi-thermometer, BTHome, Mopeka, Ruuvi, Airthings, Inkbird, RadonEye, ThermoPro and Xiaomi families, andb_parasite,exposure_notifications). Most configurations never set this key explicitly; those that do keep validating with a warning until 2027.2.0, when the old key is removed #17716 #17950 #17951 #18161 #18165 #18168 #18170 #18171 #18172 #18174 #18178 #18180 #18183 - iBeacon parsing: A 23-byte Apple manufacturer payload must now carry the 0x02/0x15 iBeacon sub-type prefix to be treated as an iBeacon. Automations that matched spurious beacons with garbage UUIDs stop firing, which is the fix #18081
Component Changes
Section titled “Component Changes”- SGP4x / SEN5x / SEN6x: The
vocandnoxsensor keys are renamed tovoc_indexandnox_indexto reflect that they publish Sensirion’s unitless gas index, not a concentration. Old keys warn and auto-migrate until removal in 2027.2.0 #17723 #17724 #17725 - AQI: Over-range readings are no longer pinned to a flat value. US AQI readings above the top breakpoint now
interpolate correctly across 301-500 (and beyond with the new
extended_rangeoption), and CAQI is unbounded past 100 per the CITEAIR spec, so values reported during heavy pollution will change #17570 - LVGL: Animation weights greater than 1.0 in
ease_in/ease_outtiming are now rejected at validation (they previously produced out-of-range progress values), and the default ease timing changes slightly, which may be visible as a cosmetic difference #17574 - RC522 I²C: The default I²C address changed from
0x2Cto0x28to match the documentation and typical board wiring. If your reader relied on the old default, setaddress: 0x2Cexplicitly #17566 - Addressable LED strips:
rgb_order,is_rgbwandis_wrgbonesp32_rmt_led_strip,beken_spi_led_stripandrp2040_pio_led_stripare deprecated in favour ofchannel_colors; they migrate automatically with a warning until removal in 2027.3.0 #18474 - GPIO expanders:
inverted: trueandallow_other_uses: trueoninterrupt_pinare now validation errors forpcf8574,pca9554,tca9555,pca6416a,pi4ioe5v6408andmcp23016; an inverted pin caused an endless I²C read loop and a shared pin never delivered interrupts #18472
Modbus
Section titled “Modbus”- modbus_controller:
command_throttleandallow_duplicate_commandsno longer have any effect. They are still accepted with a validation warning and will be removed in 2027.2.0; useturnaround_timeon themodbuscomponent instead ofcommand_throttle#11781 - modbus_controller: When several sensors share a range’s start address, the polled range is now widened to cover the widest sensor. Devices that reject reads touching unmapped registers may return an exception where a shorter, registration-order-dependent read happened to succeed before #17677
- modbus_controller: Sensors polled with
custom_command: [0x17, ...](read/write multiple registers) no longer receive the leading byte-count byte in the payload; subtract one from theoffset:of any such sensor #18215 - modbus_server: Devices can no longer use
address: 0, which is the Modbus broadcast address. Broadcast writes are now correctly delivered to all server devices with no response; assign each server a unique address from 1-247 #17387
Web Server
Section titled “Web Server”- Entity IDs: The
idfield in the web server JSON now carries the{domain}/{device?}/{name}format and the transitionalname_idfield is removed, completing the migration announced in 2026.1. Current frontends handle this automatically; only pinned pre-2026.1.3 bundles or custom frontends keyed off the old id are affected #17586 - Alarm control panel domain: The JSON
domainfield now reportsalarm_control_panel(underscores) instead of the previously advertisedalarm-control-panel, matching the only route the server ever accepted #17594
Undocumented API Changes
Section titled “Undocumented API Changes”Advanced users with lambdas and external component maintainers should note the following internal C++ API changes. These are not covered by the formal breaking change policy, but lambdas sometimes depend on them.
- Modbus: The hub call
send_pdu()is renamed toqueue_pdu()to reflect that it queues a request rather than putting a frame on the wire;send_pdu()remains as a deprecated alias for the deprecation window, and asucceeded()helper replaces ad-hoc exception checks #18196 - Modbus server: Read lambdas can now decline a read by returning an empty optional, answering the request
with
SERVICE_DEVICE_FAILURE. A register lambda that literally wrotereturn {};previously produced0and now declines the read;ServerRegister::set_read_lambda<T>()widens its signature tooptional<T>#17464 - VEML3235:
gain: AUTOis removed from the schema (it never compiled; automatic mode remains the separateauto_gainoption, enabled by default), and the non-functionalset_power_on()/shutdown code path is removed #17551 - Zigbee:
is_connectedis renamed tois_joined(), and thejoined,startedandfactory_newmembers are now protected; useis_joined()andis_started()in lambdas instead #18007 #18008 - Web server base: The credential setters on
WebServerBasenow takeconst char *instead ofstd::string, and on non-ESP32 basic-auth buildsset_auth_username/set_auth_passwordare replaced byset_auth_basic_hash(part of the fix for basic auth failing with long credentials) #18237
Breaking Changes for Developers
Section titled “Breaking Changes for Developers”- ModbusController API: Handler signatures for
on_data_func,create_read_command()andcreate_custom_command()now takestd::span<const uint8_t>instead ofconst std::vector<uint8_t>&;on_register_data(),send_raw(),get_command_queue_length()and the 4-argumentcreate_read_command()overload are removed;ModbusCommandItemdata members are now protected (use the accessors); andModbusControllerno longer derives frommodbus::ModbusClientDevice#11781 - ModbusController sensor dispatch:
SensorItem::parse_and_publish()takesstd::span<const uint8_t>; external platforms must set addresses viaset_address()/set_offset_from_start_address()instead of assigningstart_address/offsetdirectly, andpayload_to_float()gains an explicitoffsetparameter #17677 - ESPBTDevice::address_str() deprecated: Use the buffer-based
address_str_to(); the old method is removed in 2027.2.0 #18092
For detailed migration guides and API documentation, see the ESPHome Developers Documentation.
Full List of Changes
Section titled “Full List of Changes”For the complete list of every merged pull request in this release, see the full 2026.8.0 changelog.



Comments