From 8994c18f730dd050ac002177bb8e85128043f9ba Mon Sep 17 00:00:00 2001 From: "J. Nick Koston" Date: Sun, 21 Jul 2024 08:19:33 -0500 Subject: [PATCH] Update xiaomi-ble to use entry.runtime_data (#122306) --- .../components/xiaomi_ble/__init__.py | 62 ++++++++----------- .../components/xiaomi_ble/binary_sensor.py | 14 ++--- .../components/xiaomi_ble/coordinator.py | 4 +- homeassistant/components/xiaomi_ble/event.py | 9 +-- homeassistant/components/xiaomi_ble/sensor.py | 14 ++--- homeassistant/components/xiaomi_ble/types.py | 10 +++ 6 files changed, 49 insertions(+), 64 deletions(-) create mode 100644 homeassistant/components/xiaomi_ble/types.py diff --git a/homeassistant/components/xiaomi_ble/__init__.py b/homeassistant/components/xiaomi_ble/__init__.py index 4a9753bfe85..fae5e4d0c91 100644 --- a/homeassistant/components/xiaomi_ble/__init__.py +++ b/homeassistant/components/xiaomi_ble/__init__.py @@ -2,12 +2,12 @@ from __future__ import annotations +from functools import partial import logging from typing import cast from xiaomi_ble import EncryptionScheme, SensorUpdate, XiaomiBluetoothDeviceData -from homeassistant import config_entries from homeassistant.components.bluetooth import ( DOMAIN as BLUETOOTH_DOMAIN, BluetoothScanningMode, @@ -29,6 +29,7 @@ from .const import ( XiaomiBleEvent, ) from .coordinator import XiaomiActiveBluetoothProcessorCoordinator +from .types import XiaomiBLEConfigEntry PLATFORMS: list[Platform] = [Platform.BINARY_SENSOR, Platform.EVENT, Platform.SENSOR] @@ -37,16 +38,14 @@ _LOGGER = logging.getLogger(__name__) def process_service_info( hass: HomeAssistant, - entry: config_entries.ConfigEntry, - data: XiaomiBluetoothDeviceData, - service_info: BluetoothServiceInfoBleak, + entry: XiaomiBLEConfigEntry, device_registry: DeviceRegistry, + service_info: BluetoothServiceInfoBleak, ) -> SensorUpdate: """Process a BluetoothServiceInfoBleak, running side effects and returning sensor data.""" + coordinator = entry.runtime_data + data = coordinator.device_data update = data.update(service_info) - coordinator: XiaomiActiveBluetoothProcessorCoordinator = hass.data[DOMAIN][ - entry.entry_id - ] discovered_event_classes = coordinator.discovered_event_classes if entry.data.get(CONF_SLEEPY_DEVICE, False) != data.sleepy_device: hass.config_entries.async_update_entry( @@ -165,38 +164,29 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: return await data.async_poll(connectable_device) device_registry = dr.async_get(hass) - coordinator = hass.data.setdefault(DOMAIN, {})[entry.entry_id] = ( - XiaomiActiveBluetoothProcessorCoordinator( - hass, - _LOGGER, - address=address, - mode=BluetoothScanningMode.PASSIVE, - update_method=lambda service_info: process_service_info( - hass, entry, data, service_info, device_registry - ), - needs_poll_method=_needs_poll, - device_data=data, - discovered_event_classes=set( - entry.data.get(CONF_DISCOVERED_EVENT_CLASSES, []) - ), - poll_method=_async_poll, - # We will take advertisements from non-connectable devices - # since we will trade the BLEDevice for a connectable one - # if we need to poll it - connectable=False, - entry=entry, - ) + coordinator = XiaomiActiveBluetoothProcessorCoordinator( + hass, + _LOGGER, + address=address, + mode=BluetoothScanningMode.PASSIVE, + update_method=partial(process_service_info, hass, entry, device_registry), + needs_poll_method=_needs_poll, + device_data=data, + discovered_event_classes=set(entry.data.get(CONF_DISCOVERED_EVENT_CLASSES, [])), + poll_method=_async_poll, + # We will take advertisements from non-connectable devices + # since we will trade the BLEDevice for a connectable one + # if we need to poll it + connectable=False, + entry=entry, ) + entry.runtime_data = coordinator await hass.config_entries.async_forward_entry_setups(entry, PLATFORMS) - entry.async_on_unload( - coordinator.async_start() - ) # only start after all platforms have had a chance to subscribe + # only start after all platforms have had a chance to subscribe + entry.async_on_unload(coordinator.async_start()) return True -async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: +async def async_unload_entry(hass: HomeAssistant, entry: XiaomiBLEConfigEntry) -> bool: """Unload a config entry.""" - if unload_ok := await hass.config_entries.async_unload_platforms(entry, PLATFORMS): - hass.data[DOMAIN].pop(entry.entry_id) - - return unload_ok + return await hass.config_entries.async_unload_platforms(entry, PLATFORMS) diff --git a/homeassistant/components/xiaomi_ble/binary_sensor.py b/homeassistant/components/xiaomi_ble/binary_sensor.py index 8734f45c405..5336c4d8f7f 100644 --- a/homeassistant/components/xiaomi_ble/binary_sensor.py +++ b/homeassistant/components/xiaomi_ble/binary_sensor.py @@ -8,7 +8,6 @@ from xiaomi_ble.parser import ( SensorUpdate, ) -from homeassistant import config_entries from homeassistant.components.binary_sensor import ( BinarySensorDeviceClass, BinarySensorEntity, @@ -22,12 +21,9 @@ from homeassistant.core import HomeAssistant from homeassistant.helpers.entity_platform import AddEntitiesCallback from homeassistant.helpers.sensor import sensor_device_info_to_hass_device_info -from .const import DOMAIN -from .coordinator import ( - XiaomiActiveBluetoothProcessorCoordinator, - XiaomiPassiveBluetoothDataProcessor, -) +from .coordinator import XiaomiPassiveBluetoothDataProcessor from .device import device_key_to_bluetooth_entity_key +from .types import XiaomiBLEConfigEntry BINARY_SENSOR_DESCRIPTIONS = { XiaomiBinarySensorDeviceClass.BATTERY: BinarySensorEntityDescription( @@ -134,13 +130,11 @@ def sensor_update_to_bluetooth_data_update( async def async_setup_entry( hass: HomeAssistant, - entry: config_entries.ConfigEntry, + entry: XiaomiBLEConfigEntry, async_add_entities: AddEntitiesCallback, ) -> None: """Set up the Xiaomi BLE sensors.""" - coordinator: XiaomiActiveBluetoothProcessorCoordinator = hass.data[DOMAIN][ - entry.entry_id - ] + coordinator = entry.runtime_data processor = XiaomiPassiveBluetoothDataProcessor( sensor_update_to_bluetooth_data_update ) diff --git a/homeassistant/components/xiaomi_ble/coordinator.py b/homeassistant/components/xiaomi_ble/coordinator.py index 1cd49e851ea..69fc427013a 100644 --- a/homeassistant/components/xiaomi_ble/coordinator.py +++ b/homeassistant/components/xiaomi_ble/coordinator.py @@ -16,11 +16,11 @@ from homeassistant.components.bluetooth.active_update_processor import ( from homeassistant.components.bluetooth.passive_update_processor import ( PassiveBluetoothDataProcessor, ) -from homeassistant.config_entries import ConfigEntry from homeassistant.core import HomeAssistant from homeassistant.helpers.debounce import Debouncer from .const import CONF_SLEEPY_DEVICE +from .types import XiaomiBLEConfigEntry class XiaomiActiveBluetoothProcessorCoordinator( @@ -45,7 +45,7 @@ class XiaomiActiveBluetoothProcessorCoordinator( ] | None = None, poll_debouncer: Debouncer[Coroutine[Any, Any, None]] | None = None, - entry: ConfigEntry, + entry: XiaomiBLEConfigEntry, connectable: bool = True, ) -> None: """Initialize the Xiaomi Bluetooth Active Update Processor Coordinator.""" diff --git a/homeassistant/components/xiaomi_ble/event.py b/homeassistant/components/xiaomi_ble/event.py index e39a4adb3c7..7265bcd112c 100644 --- a/homeassistant/components/xiaomi_ble/event.py +++ b/homeassistant/components/xiaomi_ble/event.py @@ -9,7 +9,6 @@ from homeassistant.components.event import ( EventEntity, EventEntityDescription, ) -from homeassistant.config_entries import ConfigEntry from homeassistant.core import HomeAssistant, callback from homeassistant.helpers import device_registry as dr, entity_registry as er from homeassistant.helpers.dispatcher import async_dispatcher_connect @@ -29,7 +28,7 @@ from .const import ( EVENT_TYPE, XiaomiBleEvent, ) -from .coordinator import XiaomiActiveBluetoothProcessorCoordinator +from .types import XiaomiBLEConfigEntry DESCRIPTIONS_BY_EVENT_CLASS = { EVENT_CLASS_BUTTON: EventEntityDescription( @@ -183,13 +182,11 @@ class XiaomiEventEntity(EventEntity): async def async_setup_entry( hass: HomeAssistant, - entry: ConfigEntry, + entry: XiaomiBLEConfigEntry, async_add_entities: AddEntitiesCallback, ) -> None: """Set up Xiaomi event.""" - coordinator: XiaomiActiveBluetoothProcessorCoordinator = hass.data[DOMAIN][ - entry.entry_id - ] + coordinator = entry.runtime_data address = coordinator.address ent_reg = er.async_get(hass) async_add_entities( diff --git a/homeassistant/components/xiaomi_ble/sensor.py b/homeassistant/components/xiaomi_ble/sensor.py index 65b33c3c559..3108c285dbe 100644 --- a/homeassistant/components/xiaomi_ble/sensor.py +++ b/homeassistant/components/xiaomi_ble/sensor.py @@ -7,7 +7,6 @@ from typing import cast from xiaomi_ble import DeviceClass, SensorUpdate, Units from xiaomi_ble.parser import ExtendedSensorDeviceClass -from homeassistant import config_entries from homeassistant.components.bluetooth.passive_update_processor import ( PassiveBluetoothDataUpdate, PassiveBluetoothProcessorEntity, @@ -35,12 +34,9 @@ from homeassistant.core import HomeAssistant from homeassistant.helpers.entity_platform import AddEntitiesCallback from homeassistant.helpers.sensor import sensor_device_info_to_hass_device_info -from .const import DOMAIN -from .coordinator import ( - XiaomiActiveBluetoothProcessorCoordinator, - XiaomiPassiveBluetoothDataProcessor, -) +from .coordinator import XiaomiPassiveBluetoothDataProcessor from .device import device_key_to_bluetooth_entity_key +from .types import XiaomiBLEConfigEntry SENSOR_DESCRIPTIONS = { (DeviceClass.BATTERY, Units.PERCENTAGE): SensorEntityDescription( @@ -193,13 +189,11 @@ def sensor_update_to_bluetooth_data_update( async def async_setup_entry( hass: HomeAssistant, - entry: config_entries.ConfigEntry, + entry: XiaomiBLEConfigEntry, async_add_entities: AddEntitiesCallback, ) -> None: """Set up the Xiaomi BLE sensors.""" - coordinator: XiaomiActiveBluetoothProcessorCoordinator = hass.data[DOMAIN][ - entry.entry_id - ] + coordinator = entry.runtime_data processor = XiaomiPassiveBluetoothDataProcessor( sensor_update_to_bluetooth_data_update ) diff --git a/homeassistant/components/xiaomi_ble/types.py b/homeassistant/components/xiaomi_ble/types.py new file mode 100644 index 00000000000..f0de8af9d06 --- /dev/null +++ b/homeassistant/components/xiaomi_ble/types.py @@ -0,0 +1,10 @@ +"""Support for xiaomi ble.""" + +from typing import TYPE_CHECKING + +from homeassistant.config_entries import ConfigEntry + +if TYPE_CHECKING: + from .coordinator import XiaomiActiveBluetoothProcessorCoordinator + +type XiaomiBLEConfigEntry = ConfigEntry[XiaomiActiveBluetoothProcessorCoordinator]