Improve tracking of existing entities in deconz (#40265)
* Store all entities in dict * Use stored unique id to select if to create entity or not * Remove unnecessary init * Change so same physical sensor doesnt try to create multiple battery sensors Change so groups get created properly * Add controls in tests that entities are logged correctly
This commit is contained in:
parent
e30acfbfee
commit
203c556ba3
16 changed files with 147 additions and 58 deletions
|
@ -8,6 +8,7 @@ from homeassistant.components.binary_sensor import (
|
||||||
DEVICE_CLASS_OPENING,
|
DEVICE_CLASS_OPENING,
|
||||||
DEVICE_CLASS_SMOKE,
|
DEVICE_CLASS_SMOKE,
|
||||||
DEVICE_CLASS_VIBRATION,
|
DEVICE_CLASS_VIBRATION,
|
||||||
|
DOMAIN,
|
||||||
BinarySensorEntity,
|
BinarySensorEntity,
|
||||||
)
|
)
|
||||||
from homeassistant.const import ATTR_TEMPERATURE
|
from homeassistant.const import ATTR_TEMPERATURE
|
||||||
|
@ -39,17 +40,18 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
|
||||||
async def async_setup_entry(hass, config_entry, async_add_entities):
|
async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
"""Set up the deCONZ binary sensor."""
|
"""Set up the deCONZ binary sensor."""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_sensor(sensors, new=True):
|
def async_add_sensor(sensors):
|
||||||
"""Add binary sensor from deCONZ."""
|
"""Add binary sensor from deCONZ."""
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for sensor in sensors:
|
for sensor in sensors:
|
||||||
|
|
||||||
if (
|
if (
|
||||||
new
|
sensor.BINARY
|
||||||
and sensor.BINARY
|
and sensor.uniqueid not in gateway.entities[DOMAIN]
|
||||||
and (
|
and (
|
||||||
gateway.option_allow_clip_sensor
|
gateway.option_allow_clip_sensor
|
||||||
or not sensor.type.startswith("CLIP")
|
or not sensor.type.startswith("CLIP")
|
||||||
|
@ -73,6 +75,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzBinarySensor(DeconzDevice, BinarySensorEntity):
|
class DeconzBinarySensor(DeconzDevice, BinarySensorEntity):
|
||||||
"""Representation of a deCONZ binary sensor."""
|
"""Representation of a deCONZ binary sensor."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_callback(self, force_update=False, ignore_update=False):
|
def async_update_callback(self, force_update=False, ignore_update=False):
|
||||||
"""Update the sensor's state."""
|
"""Update the sensor's state."""
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
"""Support for deCONZ climate devices."""
|
"""Support for deCONZ climate devices."""
|
||||||
from pydeconz.sensor import Thermostat
|
from pydeconz.sensor import Thermostat
|
||||||
|
|
||||||
from homeassistant.components.climate import ClimateEntity
|
from homeassistant.components.climate import DOMAIN, ClimateEntity
|
||||||
from homeassistant.components.climate.const import (
|
from homeassistant.components.climate.const import (
|
||||||
HVAC_MODE_AUTO,
|
HVAC_MODE_AUTO,
|
||||||
HVAC_MODE_HEAT,
|
HVAC_MODE_HEAT,
|
||||||
|
@ -29,17 +29,18 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
Thermostats are based on the same device class as sensors in deCONZ.
|
Thermostats are based on the same device class as sensors in deCONZ.
|
||||||
"""
|
"""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_climate(sensors, new=True):
|
def async_add_climate(sensors):
|
||||||
"""Add climate devices from deCONZ."""
|
"""Add climate devices from deCONZ."""
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for sensor in sensors:
|
for sensor in sensors:
|
||||||
|
|
||||||
if (
|
if (
|
||||||
new
|
sensor.type in Thermostat.ZHATYPE
|
||||||
and sensor.type in Thermostat.ZHATYPE
|
and sensor.uniqueid not in gateway.entities[DOMAIN]
|
||||||
and (
|
and (
|
||||||
gateway.option_allow_clip_sensor
|
gateway.option_allow_clip_sensor
|
||||||
or not sensor.type.startswith("CLIP")
|
or not sensor.type.startswith("CLIP")
|
||||||
|
@ -61,6 +62,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzThermostat(DeconzDevice, ClimateEntity):
|
class DeconzThermostat(DeconzDevice, ClimateEntity):
|
||||||
"""Representation of a deCONZ thermostat."""
|
"""Representation of a deCONZ thermostat."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def supported_features(self):
|
def supported_features(self):
|
||||||
"""Return the list of supported features."""
|
"""Return the list of supported features."""
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
from homeassistant.components.cover import (
|
from homeassistant.components.cover import (
|
||||||
ATTR_POSITION,
|
ATTR_POSITION,
|
||||||
DEVICE_CLASS_WINDOW,
|
DEVICE_CLASS_WINDOW,
|
||||||
|
DOMAIN,
|
||||||
SUPPORT_CLOSE,
|
SUPPORT_CLOSE,
|
||||||
SUPPORT_OPEN,
|
SUPPORT_OPEN,
|
||||||
SUPPORT_SET_POSITION,
|
SUPPORT_SET_POSITION,
|
||||||
|
@ -23,9 +24,10 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
|
||||||
async def async_setup_entry(hass, config_entry, async_add_entities):
|
async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
"""Set up covers for deCONZ component.
|
"""Set up covers for deCONZ component.
|
||||||
|
|
||||||
Covers are based on same device class as lights in deCONZ.
|
Covers are based on the same device class as lights in deCONZ.
|
||||||
"""
|
"""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_cover(lights):
|
def async_add_cover(lights):
|
||||||
|
@ -33,7 +35,10 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for light in lights:
|
for light in lights:
|
||||||
if light.type in COVER_TYPES:
|
if (
|
||||||
|
light.type in COVER_TYPES
|
||||||
|
and light.uniqueid not in gateway.entities[DOMAIN]
|
||||||
|
):
|
||||||
entities.append(DeconzCover(light, gateway))
|
entities.append(DeconzCover(light, gateway))
|
||||||
|
|
||||||
async_add_entities(entities, True)
|
async_add_entities(entities, True)
|
||||||
|
@ -50,6 +55,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzCover(DeconzDevice, CoverEntity):
|
class DeconzCover(DeconzDevice, CoverEntity):
|
||||||
"""Representation of a deCONZ cover."""
|
"""Representation of a deCONZ cover."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
def __init__(self, device, gateway):
|
||||||
"""Set up cover device."""
|
"""Set up cover device."""
|
||||||
super().__init__(device, gateway)
|
super().__init__(device, gateway)
|
||||||
|
|
|
@ -10,11 +10,17 @@ from .const import DOMAIN as DECONZ_DOMAIN
|
||||||
class DeconzBase:
|
class DeconzBase:
|
||||||
"""Common base for deconz entities and events."""
|
"""Common base for deconz entities and events."""
|
||||||
|
|
||||||
|
TYPE = ""
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
def __init__(self, device, gateway):
|
||||||
"""Set up device and add update callback to get data from websocket."""
|
"""Set up device and add update callback to get data from websocket."""
|
||||||
self._device = device
|
self._device = device
|
||||||
self.gateway = gateway
|
self.gateway = gateway
|
||||||
self.listeners = []
|
self.gateway.entities[self.TYPE].add(self.unique_id)
|
||||||
|
|
||||||
|
async def async_will_remove_from_hass(self) -> None:
|
||||||
|
"""Remove unique id."""
|
||||||
|
self.gateway.entities[self.TYPE].remove(self.unique_id)
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def unique_id(self):
|
def unique_id(self):
|
||||||
|
@ -51,12 +57,6 @@ class DeconzBase:
|
||||||
class DeconzDevice(DeconzBase, Entity):
|
class DeconzDevice(DeconzBase, Entity):
|
||||||
"""Representation of a deCONZ device."""
|
"""Representation of a deCONZ device."""
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
|
||||||
"""Set up device and add update callback to get data from websocket."""
|
|
||||||
super().__init__(device, gateway)
|
|
||||||
|
|
||||||
self.unsub_dispatcher = None
|
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def entity_registry_enabled_default(self):
|
def entity_registry_enabled_default(self):
|
||||||
"""Return if the entity should be enabled when first added to the entity registry.
|
"""Return if the entity should be enabled when first added to the entity registry.
|
||||||
|
@ -72,7 +72,7 @@ class DeconzDevice(DeconzBase, Entity):
|
||||||
"""Subscribe to device events."""
|
"""Subscribe to device events."""
|
||||||
self._device.register_callback(self.async_update_callback)
|
self._device.register_callback(self.async_update_callback)
|
||||||
self.gateway.deconz_ids[self.entity_id] = self._device.deconz_id
|
self.gateway.deconz_ids[self.entity_id] = self._device.deconz_id
|
||||||
self.listeners.append(
|
self.async_on_remove(
|
||||||
async_dispatcher_connect(
|
async_dispatcher_connect(
|
||||||
self.hass, self.gateway.signal_reachable, self.async_update_callback
|
self.hass, self.gateway.signal_reachable, self.async_update_callback
|
||||||
)
|
)
|
||||||
|
@ -83,8 +83,7 @@ class DeconzDevice(DeconzBase, Entity):
|
||||||
self._device.remove_callback(self.async_update_callback)
|
self._device.remove_callback(self.async_update_callback)
|
||||||
if self.entity_id in self.gateway.deconz_ids:
|
if self.entity_id in self.gateway.deconz_ids:
|
||||||
del self.gateway.deconz_ids[self.entity_id]
|
del self.gateway.deconz_ids[self.entity_id]
|
||||||
for unsub_dispatcher in self.listeners:
|
await super().async_will_remove_from_hass()
|
||||||
unsub_dispatcher()
|
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_callback(self, force_update=False, ignore_update=False):
|
def async_update_callback(self, force_update=False, ignore_update=False):
|
||||||
|
|
|
@ -11,19 +11,25 @@ from .deconz_device import DeconzBase
|
||||||
|
|
||||||
CONF_DECONZ_EVENT = "deconz_event"
|
CONF_DECONZ_EVENT = "deconz_event"
|
||||||
|
|
||||||
|
EVENT = "Event"
|
||||||
|
|
||||||
|
|
||||||
async def async_setup_events(gateway) -> None:
|
async def async_setup_events(gateway) -> None:
|
||||||
"""Set up the deCONZ events."""
|
"""Set up the deCONZ events."""
|
||||||
|
gateway.entities[EVENT] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_sensor(sensors, new=True):
|
def async_add_sensor(sensors):
|
||||||
"""Create DeconzEvent."""
|
"""Create DeconzEvent."""
|
||||||
for sensor in sensors:
|
for sensor in sensors:
|
||||||
|
|
||||||
if not gateway.option_allow_clip_sensor and sensor.type.startswith("CLIP"):
|
if not gateway.option_allow_clip_sensor and sensor.type.startswith("CLIP"):
|
||||||
continue
|
continue
|
||||||
|
|
||||||
if not new or sensor.type not in Switch.ZHATYPE:
|
if (
|
||||||
|
sensor.type not in Switch.ZHATYPE
|
||||||
|
or sensor.uniqueid in gateway.entities[EVENT]
|
||||||
|
):
|
||||||
continue
|
continue
|
||||||
|
|
||||||
new_event = DeconzEvent(sensor, gateway)
|
new_event = DeconzEvent(sensor, gateway)
|
||||||
|
@ -44,7 +50,7 @@ async def async_setup_events(gateway) -> None:
|
||||||
async def async_unload_events(gateway) -> None:
|
async def async_unload_events(gateway) -> None:
|
||||||
"""Unload all deCONZ events."""
|
"""Unload all deCONZ events."""
|
||||||
for event in gateway.events:
|
for event in gateway.events:
|
||||||
event.async_will_remove_from_hass()
|
await event.async_will_remove_from_hass()
|
||||||
|
|
||||||
gateway.events.clear()
|
gateway.events.clear()
|
||||||
|
|
||||||
|
@ -56,6 +62,8 @@ class DeconzEvent(DeconzBase):
|
||||||
instead of a sensor entity in hass.
|
instead of a sensor entity in hass.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
|
TYPE = EVENT
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
def __init__(self, device, gateway):
|
||||||
"""Register callback that will be used for signals."""
|
"""Register callback that will be used for signals."""
|
||||||
super().__init__(device, gateway)
|
super().__init__(device, gateway)
|
||||||
|
@ -71,11 +79,10 @@ class DeconzEvent(DeconzBase):
|
||||||
"""Return Event device."""
|
"""Return Event device."""
|
||||||
return self._device
|
return self._device
|
||||||
|
|
||||||
@callback
|
async def async_will_remove_from_hass(self) -> None:
|
||||||
def async_will_remove_from_hass(self) -> None:
|
|
||||||
"""Disconnect event object when removed."""
|
"""Disconnect event object when removed."""
|
||||||
self._device.remove_callback(self.async_update_callback)
|
self._device.remove_callback(self.async_update_callback)
|
||||||
self._device = None
|
await super().async_will_remove_from_hass()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_callback(self, force_update=False, ignore_update=False):
|
def async_update_callback(self, force_update=False, ignore_update=False):
|
||||||
|
|
|
@ -49,6 +49,8 @@ class DeconzGateway:
|
||||||
self.events = []
|
self.events = []
|
||||||
self.listeners = []
|
self.listeners = []
|
||||||
|
|
||||||
|
self.entities = {}
|
||||||
|
|
||||||
self._current_option_allow_clip_sensor = self.option_allow_clip_sensor
|
self._current_option_allow_clip_sensor = self.option_allow_clip_sensor
|
||||||
self._current_option_allow_deconz_groups = self.option_allow_deconz_groups
|
self._current_option_allow_deconz_groups = self.option_allow_deconz_groups
|
||||||
|
|
||||||
|
|
|
@ -6,6 +6,7 @@ from homeassistant.components.light import (
|
||||||
ATTR_FLASH,
|
ATTR_FLASH,
|
||||||
ATTR_HS_COLOR,
|
ATTR_HS_COLOR,
|
||||||
ATTR_TRANSITION,
|
ATTR_TRANSITION,
|
||||||
|
DOMAIN,
|
||||||
EFFECT_COLORLOOP,
|
EFFECT_COLORLOOP,
|
||||||
FLASH_LONG,
|
FLASH_LONG,
|
||||||
FLASH_SHORT,
|
FLASH_SHORT,
|
||||||
|
@ -40,6 +41,7 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
|
||||||
async def async_setup_entry(hass, config_entry, async_add_entities):
|
async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
"""Set up the deCONZ lights and groups from a config entry."""
|
"""Set up the deCONZ lights and groups from a config entry."""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_light(lights):
|
def async_add_light(lights):
|
||||||
|
@ -47,7 +49,10 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for light in lights:
|
for light in lights:
|
||||||
if light.type not in COVER_TYPES + SWITCH_TYPES:
|
if (
|
||||||
|
light.type not in COVER_TYPES + SWITCH_TYPES
|
||||||
|
and light.uniqueid not in gateway.entities[DOMAIN]
|
||||||
|
):
|
||||||
entities.append(DeconzLight(light, gateway))
|
entities.append(DeconzLight(light, gateway))
|
||||||
|
|
||||||
async_add_entities(entities, True)
|
async_add_entities(entities, True)
|
||||||
|
@ -67,8 +72,13 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for group in groups:
|
for group in groups:
|
||||||
if group.lights:
|
if not group.lights:
|
||||||
entities.append(DeconzGroup(group, gateway))
|
continue
|
||||||
|
|
||||||
|
known_groups = list(gateway.entities[DOMAIN])
|
||||||
|
new_group = DeconzGroup(group, gateway)
|
||||||
|
if new_group.unique_id not in known_groups:
|
||||||
|
entities.append(new_group)
|
||||||
|
|
||||||
async_add_entities(entities, True)
|
async_add_entities(entities, True)
|
||||||
|
|
||||||
|
@ -85,6 +95,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzBaseLight(DeconzDevice, LightEntity):
|
class DeconzBaseLight(DeconzDevice, LightEntity):
|
||||||
"""Representation of a deCONZ light."""
|
"""Representation of a deCONZ light."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
def __init__(self, device, gateway):
|
||||||
"""Set up light."""
|
"""Set up light."""
|
||||||
super().__init__(device, gateway)
|
super().__init__(device, gateway)
|
||||||
|
@ -223,14 +235,13 @@ class DeconzGroup(DeconzBaseLight):
|
||||||
|
|
||||||
def __init__(self, device, gateway):
|
def __init__(self, device, gateway):
|
||||||
"""Set up group and create an unique id."""
|
"""Set up group and create an unique id."""
|
||||||
|
group_id_base = gateway.config_entry.unique_id
|
||||||
|
if CONF_GROUP_ID_BASE in gateway.config_entry.data:
|
||||||
|
group_id_base = gateway.config_entry.data[CONF_GROUP_ID_BASE]
|
||||||
|
self._unique_id = f"{group_id_base}-{device.deconz_id}"
|
||||||
|
|
||||||
super().__init__(device, gateway)
|
super().__init__(device, gateway)
|
||||||
|
|
||||||
group_id_base = self.gateway.config_entry.unique_id
|
|
||||||
if CONF_GROUP_ID_BASE in self.gateway.config_entry.data:
|
|
||||||
group_id_base = self.gateway.config_entry.data[CONF_GROUP_ID_BASE]
|
|
||||||
|
|
||||||
self._unique_id = f"{group_id_base}-{self._device.deconz_id}"
|
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def unique_id(self):
|
def unique_id(self):
|
||||||
"""Return a unique identifier for this device."""
|
"""Return a unique identifier for this device."""
|
||||||
|
|
|
@ -12,6 +12,7 @@ from pydeconz.sensor import (
|
||||||
Thermostat,
|
Thermostat,
|
||||||
)
|
)
|
||||||
|
|
||||||
|
from homeassistant.components.sensor import DOMAIN
|
||||||
from homeassistant.const import (
|
from homeassistant.const import (
|
||||||
ATTR_TEMPERATURE,
|
ATTR_TEMPERATURE,
|
||||||
ATTR_VOLTAGE,
|
ATTR_VOLTAGE,
|
||||||
|
@ -74,43 +75,43 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
|
||||||
async def async_setup_entry(hass, config_entry, async_add_entities):
|
async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
"""Set up the deCONZ sensors."""
|
"""Set up the deCONZ sensors."""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
batteries = set()
|
|
||||||
battery_handler = DeconzBatteryHandler(gateway)
|
battery_handler = DeconzBatteryHandler(gateway)
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_sensor(sensors, new=True):
|
def async_add_sensor(sensors):
|
||||||
"""Add sensors from deCONZ.
|
"""Add sensors from deCONZ.
|
||||||
|
|
||||||
Create DeconzSensor if not a ZHAType and not a binary sensor.
|
|
||||||
Create DeconzBattery if sensor has a battery attribute.
|
Create DeconzBattery if sensor has a battery attribute.
|
||||||
If new is false it means an existing sensor has got a battery state reported.
|
Create DeconzSensor if not a battery, switch or thermostat and not a binary sensor.
|
||||||
"""
|
"""
|
||||||
entities = []
|
entities = []
|
||||||
|
|
||||||
for sensor in sensors:
|
for sensor in sensors:
|
||||||
|
|
||||||
if (
|
if not gateway.option_allow_clip_sensor and sensor.type.startswith("CLIP"):
|
||||||
new
|
continue
|
||||||
and sensor.BINARY is False
|
|
||||||
and sensor.type
|
|
||||||
not in Battery.ZHATYPE + Switch.ZHATYPE + Thermostat.ZHATYPE
|
|
||||||
and (
|
|
||||||
gateway.option_allow_clip_sensor
|
|
||||||
or not sensor.type.startswith("CLIP")
|
|
||||||
)
|
|
||||||
):
|
|
||||||
entities.append(DeconzSensor(sensor, gateway))
|
|
||||||
|
|
||||||
if sensor.battery is not None:
|
if sensor.battery is not None:
|
||||||
|
battery_handler.remove_tracker(sensor)
|
||||||
|
|
||||||
|
known_batteries = list(gateway.entities[DOMAIN])
|
||||||
new_battery = DeconzBattery(sensor, gateway)
|
new_battery = DeconzBattery(sensor, gateway)
|
||||||
if new_battery.unique_id not in batteries:
|
if new_battery.unique_id not in known_batteries:
|
||||||
batteries.add(new_battery.unique_id)
|
|
||||||
entities.append(new_battery)
|
entities.append(new_battery)
|
||||||
battery_handler.remove_tracker(sensor)
|
|
||||||
else:
|
else:
|
||||||
battery_handler.create_tracker(sensor)
|
battery_handler.create_tracker(sensor)
|
||||||
|
|
||||||
|
if (
|
||||||
|
not sensor.BINARY
|
||||||
|
and sensor.type
|
||||||
|
not in Battery.ZHATYPE + Switch.ZHATYPE + Thermostat.ZHATYPE
|
||||||
|
and sensor.uniqueid not in gateway.entities[DOMAIN]
|
||||||
|
):
|
||||||
|
entities.append(DeconzSensor(sensor, gateway))
|
||||||
|
|
||||||
async_add_entities(entities, True)
|
async_add_entities(entities, True)
|
||||||
|
|
||||||
gateway.listeners.append(
|
gateway.listeners.append(
|
||||||
|
@ -127,6 +128,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzSensor(DeconzDevice):
|
class DeconzSensor(DeconzDevice):
|
||||||
"""Representation of a deCONZ sensor."""
|
"""Representation of a deCONZ sensor."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_callback(self, force_update=False, ignore_update=False):
|
def async_update_callback(self, force_update=False, ignore_update=False):
|
||||||
"""Update the sensor's state."""
|
"""Update the sensor's state."""
|
||||||
|
@ -192,6 +195,8 @@ class DeconzSensor(DeconzDevice):
|
||||||
class DeconzBattery(DeconzDevice):
|
class DeconzBattery(DeconzDevice):
|
||||||
"""Battery class for when a device is only represented as an event."""
|
"""Battery class for when a device is only represented as an event."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_callback(self, force_update=False, ignore_update=False):
|
def async_update_callback(self, force_update=False, ignore_update=False):
|
||||||
"""Update the battery's state, if needed."""
|
"""Update the battery's state, if needed."""
|
||||||
|
@ -264,7 +269,6 @@ class DeconzSensorStateTracker:
|
||||||
self.gateway.hass,
|
self.gateway.hass,
|
||||||
self.gateway.async_signal_new_device(NEW_SENSOR),
|
self.gateway.async_signal_new_device(NEW_SENSOR),
|
||||||
[self.sensor],
|
[self.sensor],
|
||||||
False,
|
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -1,5 +1,5 @@
|
||||||
"""Support for deCONZ switches."""
|
"""Support for deCONZ switches."""
|
||||||
from homeassistant.components.switch import SwitchEntity
|
from homeassistant.components.switch import DOMAIN, SwitchEntity
|
||||||
from homeassistant.core import callback
|
from homeassistant.core import callback
|
||||||
from homeassistant.helpers.dispatcher import async_dispatcher_connect
|
from homeassistant.helpers.dispatcher import async_dispatcher_connect
|
||||||
|
|
||||||
|
@ -15,9 +15,10 @@ async def async_setup_platform(hass, config, async_add_entities, discovery_info=
|
||||||
async def async_setup_entry(hass, config_entry, async_add_entities):
|
async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
"""Set up switches for deCONZ component.
|
"""Set up switches for deCONZ component.
|
||||||
|
|
||||||
Switches are based same device class as lights in deCONZ.
|
Switches are based on the same device class as lights in deCONZ.
|
||||||
"""
|
"""
|
||||||
gateway = get_gateway_from_config_entry(hass, config_entry)
|
gateway = get_gateway_from_config_entry(hass, config_entry)
|
||||||
|
gateway.entities[DOMAIN] = set()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_add_switch(lights):
|
def async_add_switch(lights):
|
||||||
|
@ -26,10 +27,15 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
|
|
||||||
for light in lights:
|
for light in lights:
|
||||||
|
|
||||||
if light.type in POWER_PLUGS:
|
if (
|
||||||
|
light.type in POWER_PLUGS
|
||||||
|
and light.uniqueid not in gateway.entities[DOMAIN]
|
||||||
|
):
|
||||||
entities.append(DeconzPowerPlug(light, gateway))
|
entities.append(DeconzPowerPlug(light, gateway))
|
||||||
|
|
||||||
elif light.type in SIRENS:
|
elif (
|
||||||
|
light.type in SIRENS and light.uniqueid not in gateway.entities[DOMAIN]
|
||||||
|
):
|
||||||
entities.append(DeconzSiren(light, gateway))
|
entities.append(DeconzSiren(light, gateway))
|
||||||
|
|
||||||
async_add_entities(entities, True)
|
async_add_entities(entities, True)
|
||||||
|
@ -46,6 +52,8 @@ async def async_setup_entry(hass, config_entry, async_add_entities):
|
||||||
class DeconzPowerPlug(DeconzDevice, SwitchEntity):
|
class DeconzPowerPlug(DeconzDevice, SwitchEntity):
|
||||||
"""Representation of a deCONZ power plug."""
|
"""Representation of a deCONZ power plug."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def is_on(self):
|
def is_on(self):
|
||||||
"""Return true if switch is on."""
|
"""Return true if switch is on."""
|
||||||
|
@ -65,6 +73,8 @@ class DeconzPowerPlug(DeconzDevice, SwitchEntity):
|
||||||
class DeconzSiren(DeconzDevice, SwitchEntity):
|
class DeconzSiren(DeconzDevice, SwitchEntity):
|
||||||
"""Representation of a deCONZ siren."""
|
"""Representation of a deCONZ siren."""
|
||||||
|
|
||||||
|
TYPE = DOMAIN
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def is_on(self):
|
def is_on(self):
|
||||||
"""Return true if switch is on."""
|
"""Return true if switch is on."""
|
||||||
|
|
|
@ -67,6 +67,7 @@ async def test_no_binary_sensors(hass):
|
||||||
"""Test that no sensors in deconz results in no sensor entities."""
|
"""Test that no sensors in deconz results in no sensor entities."""
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
|
||||||
|
|
||||||
|
@ -80,6 +81,7 @@ async def test_binary_sensors(hass):
|
||||||
assert "binary_sensor.clip_presence_sensor" not in gateway.deconz_ids
|
assert "binary_sensor.clip_presence_sensor" not in gateway.deconz_ids
|
||||||
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 2
|
||||||
|
|
||||||
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
||||||
assert presence_sensor.state == "off"
|
assert presence_sensor.state == "off"
|
||||||
|
@ -111,6 +113,7 @@ async def test_binary_sensors(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_allow_clip_sensor(hass):
|
async def test_allow_clip_sensor(hass):
|
||||||
|
@ -127,6 +130,7 @@ async def test_allow_clip_sensor(hass):
|
||||||
assert "binary_sensor.clip_presence_sensor" in gateway.deconz_ids
|
assert "binary_sensor.clip_presence_sensor" in gateway.deconz_ids
|
||||||
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 4
|
assert len(hass.states.async_all()) == 4
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 3
|
||||||
|
|
||||||
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
||||||
assert presence_sensor.state == "off"
|
assert presence_sensor.state == "off"
|
||||||
|
@ -150,6 +154,7 @@ async def test_allow_clip_sensor(hass):
|
||||||
assert "binary_sensor.clip_presence_sensor" not in gateway.deconz_ids
|
assert "binary_sensor.clip_presence_sensor" not in gateway.deconz_ids
|
||||||
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 2
|
||||||
|
|
||||||
hass.config_entries.async_update_entry(
|
hass.config_entries.async_update_entry(
|
||||||
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
||||||
|
@ -161,12 +166,14 @@ async def test_allow_clip_sensor(hass):
|
||||||
assert "binary_sensor.clip_presence_sensor" in gateway.deconz_ids
|
assert "binary_sensor.clip_presence_sensor" in gateway.deconz_ids
|
||||||
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
assert "binary_sensor.vibration_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 4
|
assert len(hass.states.async_all()) == 4
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 3
|
||||||
|
|
||||||
|
|
||||||
async def test_add_new_binary_sensor(hass):
|
async def test_add_new_binary_sensor(hass):
|
||||||
"""Test that adding a new binary sensor works."""
|
"""Test that adding a new binary sensor works."""
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 0
|
||||||
|
|
||||||
state_added_event = {
|
state_added_event = {
|
||||||
"t": "event",
|
"t": "event",
|
||||||
|
@ -182,3 +189,4 @@ async def test_add_new_binary_sensor(hass):
|
||||||
|
|
||||||
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
presence_sensor = hass.states.get("binary_sensor.presence_sensor")
|
||||||
assert presence_sensor.state == "off"
|
assert presence_sensor.state == "off"
|
||||||
|
assert len(gateway.entities[binary_sensor.DOMAIN]) == 1
|
||||||
|
|
|
@ -59,6 +59,7 @@ async def test_no_sensors(hass):
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_climate_devices(hass):
|
async def test_climate_devices(hass):
|
||||||
|
@ -72,6 +73,7 @@ async def test_climate_devices(hass):
|
||||||
assert "climate.presence_sensor" not in gateway.deconz_ids
|
assert "climate.presence_sensor" not in gateway.deconz_ids
|
||||||
assert "climate.clip_thermostat" not in gateway.deconz_ids
|
assert "climate.clip_thermostat" not in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 1
|
||||||
|
|
||||||
thermostat = hass.states.get("climate.thermostat")
|
thermostat = hass.states.get("climate.thermostat")
|
||||||
assert thermostat.state == "auto"
|
assert thermostat.state == "auto"
|
||||||
|
@ -181,6 +183,7 @@ async def test_climate_devices(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_clip_climate_device(hass):
|
async def test_clip_climate_device(hass):
|
||||||
|
@ -198,6 +201,7 @@ async def test_clip_climate_device(hass):
|
||||||
assert "climate.presence_sensor" not in gateway.deconz_ids
|
assert "climate.presence_sensor" not in gateway.deconz_ids
|
||||||
assert "climate.clip_thermostat" in gateway.deconz_ids
|
assert "climate.clip_thermostat" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 4
|
assert len(hass.states.async_all()) == 4
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 2
|
||||||
|
|
||||||
thermostat = hass.states.get("climate.thermostat")
|
thermostat = hass.states.get("climate.thermostat")
|
||||||
assert thermostat.state == "auto"
|
assert thermostat.state == "auto"
|
||||||
|
@ -225,6 +229,7 @@ async def test_clip_climate_device(hass):
|
||||||
assert "climate.presence_sensor" not in gateway.deconz_ids
|
assert "climate.presence_sensor" not in gateway.deconz_ids
|
||||||
assert "climate.clip_thermostat" not in gateway.deconz_ids
|
assert "climate.clip_thermostat" not in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 1
|
||||||
|
|
||||||
hass.config_entries.async_update_entry(
|
hass.config_entries.async_update_entry(
|
||||||
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
||||||
|
@ -237,6 +242,7 @@ async def test_clip_climate_device(hass):
|
||||||
assert "climate.presence_sensor" not in gateway.deconz_ids
|
assert "climate.presence_sensor" not in gateway.deconz_ids
|
||||||
assert "climate.clip_thermostat" in gateway.deconz_ids
|
assert "climate.clip_thermostat" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 4
|
assert len(hass.states.async_all()) == 4
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 2
|
||||||
|
|
||||||
|
|
||||||
async def test_verify_state_update(hass):
|
async def test_verify_state_update(hass):
|
||||||
|
@ -268,6 +274,7 @@ async def test_add_new_climate_device(hass):
|
||||||
"""Test that adding a new climate device works."""
|
"""Test that adding a new climate device works."""
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 0
|
||||||
|
|
||||||
state_added_event = {
|
state_added_event = {
|
||||||
"t": "event",
|
"t": "event",
|
||||||
|
@ -283,3 +290,4 @@ async def test_add_new_climate_device(hass):
|
||||||
|
|
||||||
thermostat = hass.states.get("climate.thermostat")
|
thermostat = hass.states.get("climate.thermostat")
|
||||||
assert thermostat.state == "auto"
|
assert thermostat.state == "auto"
|
||||||
|
assert len(gateway.entities[climate.DOMAIN]) == 1
|
||||||
|
|
|
@ -67,6 +67,7 @@ async def test_no_covers(hass):
|
||||||
"""Test that no cover entities are created."""
|
"""Test that no cover entities are created."""
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
|
assert len(gateway.entities[cover.DOMAIN]) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
|
||||||
|
|
||||||
|
@ -81,6 +82,7 @@ async def test_cover(hass):
|
||||||
assert "cover.deconz_old_brightness_cover" in gateway.deconz_ids
|
assert "cover.deconz_old_brightness_cover" in gateway.deconz_ids
|
||||||
assert "cover.window_covering_controller" in gateway.deconz_ids
|
assert "cover.window_covering_controller" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[cover.DOMAIN]) == 4
|
||||||
|
|
||||||
level_controllable_cover = hass.states.get("cover.level_controllable_cover")
|
level_controllable_cover = hass.states.get("cover.level_controllable_cover")
|
||||||
assert level_controllable_cover.state == "open"
|
assert level_controllable_cover.state == "open"
|
||||||
|
@ -158,3 +160,4 @@ async def test_cover(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[cover.DOMAIN]) == 0
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
"""Test deCONZ remote events."""
|
"""Test deCONZ remote events."""
|
||||||
from copy import deepcopy
|
from copy import deepcopy
|
||||||
|
|
||||||
from homeassistant.components.deconz.deconz_event import CONF_DECONZ_EVENT
|
from homeassistant.components.deconz.deconz_event import CONF_DECONZ_EVENT, EVENT
|
||||||
|
|
||||||
from .test_gateway import DECONZ_WEB_REQUEST, setup_deconz_integration
|
from .test_gateway import DECONZ_WEB_REQUEST, setup_deconz_integration
|
||||||
|
|
||||||
|
@ -62,6 +62,7 @@ async def test_deconz_events(hass):
|
||||||
assert "sensor.switch_2_battery_level" in gateway.deconz_ids
|
assert "sensor.switch_2_battery_level" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
assert len(gateway.events) == 5
|
assert len(gateway.events) == 5
|
||||||
|
assert len(gateway.entities[EVENT]) == 5
|
||||||
|
|
||||||
switch_1 = hass.states.get("sensor.switch_1")
|
switch_1 = hass.states.get("sensor.switch_1")
|
||||||
assert switch_1 is None
|
assert switch_1 is None
|
||||||
|
@ -127,3 +128,4 @@ async def test_deconz_events(hass):
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
assert len(gateway.events) == 0
|
assert len(gateway.events) == 0
|
||||||
|
assert len(gateway.entities[EVENT]) == 0
|
||||||
|
|
|
@ -95,6 +95,7 @@ async def test_no_lights_or_groups(hass):
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_lights_and_groups(hass):
|
async def test_lights_and_groups(hass):
|
||||||
|
@ -111,6 +112,7 @@ async def test_lights_and_groups(hass):
|
||||||
assert "light.on_off_light" in gateway.deconz_ids
|
assert "light.on_off_light" in gateway.deconz_ids
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 6
|
assert len(hass.states.async_all()) == 6
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 5
|
||||||
|
|
||||||
rgb_light = hass.states.get("light.rgb_light")
|
rgb_light = hass.states.get("light.rgb_light")
|
||||||
assert rgb_light.state == "on"
|
assert rgb_light.state == "on"
|
||||||
|
@ -256,6 +258,7 @@ async def test_lights_and_groups(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_disable_light_groups(hass):
|
async def test_disable_light_groups(hass):
|
||||||
|
@ -275,6 +278,7 @@ async def test_disable_light_groups(hass):
|
||||||
assert "light.on_off_switch" not in gateway.deconz_ids
|
assert "light.on_off_switch" not in gateway.deconz_ids
|
||||||
# 3 entities
|
# 3 entities
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 4
|
||||||
|
|
||||||
rgb_light = hass.states.get("light.rgb_light")
|
rgb_light = hass.states.get("light.rgb_light")
|
||||||
assert rgb_light is not None
|
assert rgb_light is not None
|
||||||
|
@ -300,6 +304,7 @@ async def test_disable_light_groups(hass):
|
||||||
assert "light.on_off_switch" not in gateway.deconz_ids
|
assert "light.on_off_switch" not in gateway.deconz_ids
|
||||||
# 3 entities
|
# 3 entities
|
||||||
assert len(hass.states.async_all()) == 6
|
assert len(hass.states.async_all()) == 6
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 5
|
||||||
|
|
||||||
hass.config_entries.async_update_entry(
|
hass.config_entries.async_update_entry(
|
||||||
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_DECONZ_GROUPS: False}
|
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_DECONZ_GROUPS: False}
|
||||||
|
@ -313,3 +318,4 @@ async def test_disable_light_groups(hass):
|
||||||
assert "light.on_off_switch" not in gateway.deconz_ids
|
assert "light.on_off_switch" not in gateway.deconz_ids
|
||||||
# 3 entities
|
# 3 entities
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[light.DOMAIN]) == 4
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
from copy import deepcopy
|
from copy import deepcopy
|
||||||
|
|
||||||
from homeassistant.components import deconz
|
from homeassistant.components import deconz
|
||||||
|
from homeassistant.components.deconz.deconz_event import EVENT
|
||||||
import homeassistant.components.sensor as sensor
|
import homeassistant.components.sensor as sensor
|
||||||
from homeassistant.const import (
|
from homeassistant.const import (
|
||||||
DEVICE_CLASS_BATTERY,
|
DEVICE_CLASS_BATTERY,
|
||||||
|
@ -96,6 +97,7 @@ async def test_no_sensors(hass):
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_sensors(hass):
|
async def test_sensors(hass):
|
||||||
|
@ -114,6 +116,7 @@ async def test_sensors(hass):
|
||||||
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
||||||
assert "sensor.clip_light_level_sensor" not in gateway.deconz_ids
|
assert "sensor.clip_light_level_sensor" not in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 5
|
||||||
|
|
||||||
light_level_sensor = hass.states.get("sensor.light_level_sensor")
|
light_level_sensor = hass.states.get("sensor.light_level_sensor")
|
||||||
assert light_level_sensor.state == "999.8"
|
assert light_level_sensor.state == "999.8"
|
||||||
|
@ -174,6 +177,8 @@ async def test_sensors(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
# Daylight sensor from deCONZ is added to set but is disabled by default
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 1
|
||||||
|
|
||||||
|
|
||||||
async def test_allow_clip_sensors(hass):
|
async def test_allow_clip_sensors(hass):
|
||||||
|
@ -196,6 +201,7 @@ async def test_allow_clip_sensors(hass):
|
||||||
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
||||||
assert "sensor.clip_light_level_sensor" in gateway.deconz_ids
|
assert "sensor.clip_light_level_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 6
|
assert len(hass.states.async_all()) == 6
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 6
|
||||||
|
|
||||||
light_level_sensor = hass.states.get("sensor.light_level_sensor")
|
light_level_sensor = hass.states.get("sensor.light_level_sensor")
|
||||||
assert light_level_sensor.state == "999.8"
|
assert light_level_sensor.state == "999.8"
|
||||||
|
@ -243,6 +249,7 @@ async def test_allow_clip_sensors(hass):
|
||||||
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
||||||
assert "sensor.clip_light_level_sensor" not in gateway.deconz_ids
|
assert "sensor.clip_light_level_sensor" not in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 5
|
||||||
|
|
||||||
hass.config_entries.async_update_entry(
|
hass.config_entries.async_update_entry(
|
||||||
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
gateway.config_entry, options={deconz.gateway.CONF_ALLOW_CLIP_SENSOR: True}
|
||||||
|
@ -260,6 +267,7 @@ async def test_allow_clip_sensors(hass):
|
||||||
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
assert "sensor.consumption_sensor" in gateway.deconz_ids
|
||||||
assert "sensor.clip_light_level_sensor" in gateway.deconz_ids
|
assert "sensor.clip_light_level_sensor" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 6
|
assert len(hass.states.async_all()) == 6
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 6
|
||||||
|
|
||||||
|
|
||||||
async def test_add_new_sensor(hass):
|
async def test_add_new_sensor(hass):
|
||||||
|
@ -292,6 +300,8 @@ async def test_add_battery_later(hass):
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
assert len(gateway.events) == 1
|
assert len(gateway.events) == 1
|
||||||
assert len(remote._callbacks) == 2
|
assert len(remote._callbacks) == 2
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 0
|
||||||
|
assert len(gateway.entities[EVENT]) == 1
|
||||||
|
|
||||||
remote.update({"config": {"battery": 50}})
|
remote.update({"config": {"battery": 50}})
|
||||||
await hass.async_block_till_done()
|
await hass.async_block_till_done()
|
||||||
|
@ -302,3 +312,5 @@ async def test_add_battery_later(hass):
|
||||||
|
|
||||||
battery_sensor = hass.states.get("sensor.switch_1_battery_level")
|
battery_sensor = hass.states.get("sensor.switch_1_battery_level")
|
||||||
assert battery_sensor is not None
|
assert battery_sensor is not None
|
||||||
|
assert len(gateway.entities[sensor.DOMAIN]) == 1
|
||||||
|
assert len(gateway.entities[EVENT]) == 1
|
||||||
|
|
|
@ -64,6 +64,7 @@ async def test_no_switches(hass):
|
||||||
gateway = await setup_deconz_integration(hass)
|
gateway = await setup_deconz_integration(hass)
|
||||||
assert len(gateway.deconz_ids) == 0
|
assert len(gateway.deconz_ids) == 0
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[switch.DOMAIN]) == 0
|
||||||
|
|
||||||
|
|
||||||
async def test_switches(hass):
|
async def test_switches(hass):
|
||||||
|
@ -77,6 +78,7 @@ async def test_switches(hass):
|
||||||
assert "switch.unsupported_switch" not in gateway.deconz_ids
|
assert "switch.unsupported_switch" not in gateway.deconz_ids
|
||||||
assert "switch.on_off_relay" in gateway.deconz_ids
|
assert "switch.on_off_relay" in gateway.deconz_ids
|
||||||
assert len(hass.states.async_all()) == 5
|
assert len(hass.states.async_all()) == 5
|
||||||
|
assert len(gateway.entities[switch.DOMAIN]) == 4
|
||||||
|
|
||||||
on_off_switch = hass.states.get("switch.on_off_switch")
|
on_off_switch = hass.states.get("switch.on_off_switch")
|
||||||
assert on_off_switch.state == "on"
|
assert on_off_switch.state == "on"
|
||||||
|
@ -173,3 +175,4 @@ async def test_switches(hass):
|
||||||
await gateway.async_reset()
|
await gateway.async_reset()
|
||||||
|
|
||||||
assert len(hass.states.async_all()) == 0
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert len(gateway.entities[switch.DOMAIN]) == 0
|
||||||
|
|
Loading…
Add table
Reference in a new issue