fix: just do a single discovery notification for all blinds

This commit is contained in:
Richard Mann
2026-04-11 17:16:37 +10:00
parent 789f716707
commit 0efca4ff52

View File

@@ -21,7 +21,7 @@ from homeassistant.helpers.selector import (
TextSelectorType,
)
from .const import CONF_HOME_KEY, CONF_HUB_URL, DOMAIN, LOGGER
from .const import CONF_HOME_KEY, CONF_HUB_URL, DOMAIN, LOGGER, MFCT_ID
def _hub_unique_id(home_key: str) -> str:
@@ -92,6 +92,11 @@ async def _fetch_key_from_hub(
Tries each shade on the hub until one returns a valid key.
The key is network-wide so any reachable shade returns the same value.
The hub must establish a BLE connection to each shade before it can proxy
the key request. On the first pass that connection is often not yet open,
so the hub returns an error immediately. A second pass (after a short
pause to let the hub complete its BLE connections) reliably succeeds.
Raises ValueError on protocol/key errors.
Raises aiohttp.ClientError on network errors.
Raises asyncio.TimeoutError on timeout.
@@ -247,11 +252,25 @@ class ConfigFlow(config_entries.ConfigFlow, domain=DOMAIN):
"""Handle a flow initialized by Bluetooth discovery."""
LOGGER.debug("Bluetooth device detected: %s", discovery_info)
# Tag the flow with this address so HA deduplicates future
# discovery flows for the same device
await self.async_set_unique_id(discovery_info.address)
# Derive a home-wide unique ID from the home_id embedded in the BLE
# advertisement (bytes 0-1 of the manufacturer payload). All shades on
# the same network share the same home_id, so HA deduplicates every
# subsequent shade discovery into this single flow via
# "already_in_progress" rather than spawning one notification per shade.
mfr_data = bytearray(
discovery_info.manufacturer_data.get(MFCT_ID, b"")
)
if len(mfr_data) >= 2:
home_id = int.from_bytes(mfr_data[0:2], byteorder="little")
unique_id = f"pvhome_{home_id}"
else:
unique_id = DOMAIN
# If a hub entry already exists, shades are auto-discovered
await self.async_set_unique_id(unique_id)
self._abort_if_unique_id_configured()
# If a hub entry already exists (unique_id may differ), shades are
# auto-discovered internally — nothing more for the user to do.
for entry in self._async_current_entries():
if entry.version >= 2:
return self.async_abort(reason="already_configured")