Add light tests for devolo_home_control (#74183)
This commit is contained in:
parent
3970639c34
commit
43595f7e17
3 changed files with 206 additions and 1 deletions
|
@ -210,7 +210,6 @@ omit =
|
||||||
homeassistant/components/denonavr/media_player.py
|
homeassistant/components/denonavr/media_player.py
|
||||||
homeassistant/components/denonavr/receiver.py
|
homeassistant/components/denonavr/receiver.py
|
||||||
homeassistant/components/deutsche_bahn/sensor.py
|
homeassistant/components/deutsche_bahn/sensor.py
|
||||||
homeassistant/components/devolo_home_control/light.py
|
|
||||||
homeassistant/components/devolo_home_control/sensor.py
|
homeassistant/components/devolo_home_control/sensor.py
|
||||||
homeassistant/components/devolo_home_control/switch.py
|
homeassistant/components/devolo_home_control/switch.py
|
||||||
homeassistant/components/digital_ocean/*
|
homeassistant/components/digital_ocean/*
|
||||||
|
|
|
@ -8,6 +8,9 @@ from devolo_home_control_api.homecontrol import HomeControl
|
||||||
from devolo_home_control_api.properties.binary_sensor_property import (
|
from devolo_home_control_api.properties.binary_sensor_property import (
|
||||||
BinarySensorProperty,
|
BinarySensorProperty,
|
||||||
)
|
)
|
||||||
|
from devolo_home_control_api.properties.binary_switch_property import (
|
||||||
|
BinarySwitchProperty,
|
||||||
|
)
|
||||||
from devolo_home_control_api.properties.multi_level_sensor_property import (
|
from devolo_home_control_api.properties.multi_level_sensor_property import (
|
||||||
MultiLevelSensorProperty,
|
MultiLevelSensorProperty,
|
||||||
)
|
)
|
||||||
|
@ -31,6 +34,15 @@ class BinarySensorPropertyMock(BinarySensorProperty):
|
||||||
self.state = False
|
self.state = False
|
||||||
|
|
||||||
|
|
||||||
|
class BinarySwitchPropertyMock(BinarySwitchProperty):
|
||||||
|
"""devolo Home Control binary sensor mock."""
|
||||||
|
|
||||||
|
def __init__(self, **kwargs: Any) -> None:
|
||||||
|
"""Initialize the mock."""
|
||||||
|
self._logger = MagicMock()
|
||||||
|
self.element_uid = "Test"
|
||||||
|
|
||||||
|
|
||||||
class MultiLevelSensorPropertyMock(MultiLevelSensorProperty):
|
class MultiLevelSensorPropertyMock(MultiLevelSensorProperty):
|
||||||
"""devolo Home Control multi level sensor mock."""
|
"""devolo Home Control multi level sensor mock."""
|
||||||
|
|
||||||
|
@ -134,6 +146,22 @@ class CoverMock(DeviceMock):
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
class LightMock(DeviceMock):
|
||||||
|
"""devolo Home Control light device mock."""
|
||||||
|
|
||||||
|
def __init__(self) -> None:
|
||||||
|
"""Initialize the mock."""
|
||||||
|
super().__init__()
|
||||||
|
self.binary_switch_property = {}
|
||||||
|
self.multi_level_switch_property = {
|
||||||
|
"devolo.Dimmer:Test": MultiLevelSwitchPropertyMock()
|
||||||
|
}
|
||||||
|
self.multi_level_switch_property["devolo.Dimmer:Test"].switch_type = "dimmer"
|
||||||
|
self.multi_level_switch_property[
|
||||||
|
"devolo.Dimmer:Test"
|
||||||
|
].element_uid = "devolo.Dimmer:Test"
|
||||||
|
|
||||||
|
|
||||||
class RemoteControlMock(DeviceMock):
|
class RemoteControlMock(DeviceMock):
|
||||||
"""devolo Home Control remote control device mock."""
|
"""devolo Home Control remote control device mock."""
|
||||||
|
|
||||||
|
@ -219,6 +247,19 @@ class HomeControlMockCover(HomeControlMock):
|
||||||
self.publisher.unregister = MagicMock()
|
self.publisher.unregister = MagicMock()
|
||||||
|
|
||||||
|
|
||||||
|
class HomeControlMockLight(HomeControlMock):
|
||||||
|
"""devolo Home Control gateway mock with light devices."""
|
||||||
|
|
||||||
|
def __init__(self, **kwargs: Any) -> None:
|
||||||
|
"""Initialize the mock."""
|
||||||
|
super().__init__()
|
||||||
|
self.devices = {
|
||||||
|
"Test": LightMock(),
|
||||||
|
}
|
||||||
|
self.publisher = Publisher(self.devices.keys())
|
||||||
|
self.publisher.unregister = MagicMock()
|
||||||
|
|
||||||
|
|
||||||
class HomeControlMockRemoteControl(HomeControlMock):
|
class HomeControlMockRemoteControl(HomeControlMock):
|
||||||
"""devolo Home Control gateway mock with remote control device."""
|
"""devolo Home Control gateway mock with remote control device."""
|
||||||
|
|
||||||
|
|
165
tests/components/devolo_home_control/test_light.py
Normal file
165
tests/components/devolo_home_control/test_light.py
Normal file
|
@ -0,0 +1,165 @@
|
||||||
|
"""Tests for the devolo Home Control light platform."""
|
||||||
|
from unittest.mock import patch
|
||||||
|
|
||||||
|
from homeassistant.components.light import (
|
||||||
|
ATTR_BRIGHTNESS,
|
||||||
|
ATTR_COLOR_MODE,
|
||||||
|
ATTR_SUPPORTED_COLOR_MODES,
|
||||||
|
DOMAIN,
|
||||||
|
ColorMode,
|
||||||
|
)
|
||||||
|
from homeassistant.const import (
|
||||||
|
ATTR_ENTITY_ID,
|
||||||
|
SERVICE_TURN_OFF,
|
||||||
|
SERVICE_TURN_ON,
|
||||||
|
STATE_OFF,
|
||||||
|
STATE_ON,
|
||||||
|
STATE_UNAVAILABLE,
|
||||||
|
)
|
||||||
|
from homeassistant.core import HomeAssistant
|
||||||
|
|
||||||
|
from . import configure_integration
|
||||||
|
from .mocks import BinarySwitchPropertyMock, HomeControlMock, HomeControlMockLight
|
||||||
|
|
||||||
|
|
||||||
|
async def test_light_without_binary_sensor(hass: HomeAssistant):
|
||||||
|
"""Test setup and state change of a light device that does not have an additional binary sensor."""
|
||||||
|
entry = configure_integration(hass)
|
||||||
|
test_gateway = HomeControlMockLight()
|
||||||
|
with patch(
|
||||||
|
"homeassistant.components.devolo_home_control.HomeControl",
|
||||||
|
side_effect=[test_gateway, HomeControlMock()],
|
||||||
|
):
|
||||||
|
await hass.config_entries.async_setup(entry.entry_id)
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state is not None
|
||||||
|
assert state.state == STATE_ON
|
||||||
|
assert state.attributes[ATTR_COLOR_MODE] == ColorMode.BRIGHTNESS
|
||||||
|
assert state.attributes[ATTR_SUPPORTED_COLOR_MODES] == [ColorMode.BRIGHTNESS]
|
||||||
|
assert state.attributes[ATTR_BRIGHTNESS] == round(
|
||||||
|
test_gateway.devices["Test"]
|
||||||
|
.multi_level_switch_property["devolo.Dimmer:Test"]
|
||||||
|
.value
|
||||||
|
/ 100
|
||||||
|
* 255
|
||||||
|
)
|
||||||
|
|
||||||
|
# Emulate websocket message: brightness changed
|
||||||
|
test_gateway.publisher.dispatch("Test", ("devolo.Dimmer:Test", 0.0))
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state.state == STATE_OFF
|
||||||
|
test_gateway.publisher.dispatch("Test", ("devolo.Dimmer:Test", 100.0))
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state.state == STATE_ON
|
||||||
|
assert state.attributes[ATTR_BRIGHTNESS] == 255
|
||||||
|
|
||||||
|
# Test setting brightness
|
||||||
|
with patch(
|
||||||
|
"devolo_home_control_api.properties.multi_level_switch_property.MultiLevelSwitchProperty.set"
|
||||||
|
) as set_value:
|
||||||
|
await hass.services.async_call(
|
||||||
|
DOMAIN,
|
||||||
|
SERVICE_TURN_ON,
|
||||||
|
{ATTR_ENTITY_ID: f"{DOMAIN}.test"},
|
||||||
|
blocking=True,
|
||||||
|
) # In reality, this leads to a websocket message like already tested above
|
||||||
|
set_value.assert_called_once_with(100)
|
||||||
|
|
||||||
|
set_value.reset_mock()
|
||||||
|
await hass.services.async_call(
|
||||||
|
DOMAIN,
|
||||||
|
SERVICE_TURN_OFF,
|
||||||
|
{ATTR_ENTITY_ID: f"{DOMAIN}.test"},
|
||||||
|
blocking=True,
|
||||||
|
) # In reality, this leads to a websocket message like already tested above
|
||||||
|
set_value.assert_called_once_with(0)
|
||||||
|
|
||||||
|
set_value.reset_mock()
|
||||||
|
await hass.services.async_call(
|
||||||
|
DOMAIN,
|
||||||
|
SERVICE_TURN_ON,
|
||||||
|
{ATTR_ENTITY_ID: f"{DOMAIN}.test", ATTR_BRIGHTNESS: 50},
|
||||||
|
blocking=True,
|
||||||
|
) # In reality, this leads to a websocket message like already tested above
|
||||||
|
set_value.assert_called_once_with(round(50 / 255 * 100))
|
||||||
|
|
||||||
|
# Emulate websocket message: device went offline
|
||||||
|
test_gateway.devices["Test"].status = 1
|
||||||
|
test_gateway.publisher.dispatch("Test", ("Status", False, "status"))
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
assert hass.states.get(f"{DOMAIN}.test").state == STATE_UNAVAILABLE
|
||||||
|
|
||||||
|
|
||||||
|
async def test_light_with_binary_sensor(hass: HomeAssistant):
|
||||||
|
"""Test setup and state change of a light device that has an additional binary sensor."""
|
||||||
|
entry = configure_integration(hass)
|
||||||
|
test_gateway = HomeControlMockLight()
|
||||||
|
test_gateway.devices["Test"].binary_switch_property = {
|
||||||
|
"devolo.BinarySwitch:Test": BinarySwitchPropertyMock()
|
||||||
|
}
|
||||||
|
with patch(
|
||||||
|
"homeassistant.components.devolo_home_control.HomeControl",
|
||||||
|
side_effect=[test_gateway, HomeControlMock()],
|
||||||
|
):
|
||||||
|
await hass.config_entries.async_setup(entry.entry_id)
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state is not None
|
||||||
|
assert state.state == STATE_ON
|
||||||
|
|
||||||
|
# Emulate websocket message: brightness changed
|
||||||
|
test_gateway.publisher.dispatch("Test", ("devolo.Dimmer:Test", 0.0))
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state.state == STATE_OFF
|
||||||
|
test_gateway.publisher.dispatch("Test", ("devolo.Dimmer:Test", 100.0))
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state.state == STATE_ON
|
||||||
|
assert state.attributes[ATTR_BRIGHTNESS] == 255
|
||||||
|
|
||||||
|
# Test setting brightness
|
||||||
|
with patch(
|
||||||
|
"devolo_home_control_api.properties.binary_switch_property.BinarySwitchProperty.set"
|
||||||
|
) as set_value:
|
||||||
|
await hass.services.async_call(
|
||||||
|
DOMAIN,
|
||||||
|
SERVICE_TURN_ON,
|
||||||
|
{ATTR_ENTITY_ID: f"{DOMAIN}.test"},
|
||||||
|
blocking=True,
|
||||||
|
) # In reality, this leads to a websocket message like already tested above
|
||||||
|
set_value.assert_called_once_with(True)
|
||||||
|
|
||||||
|
set_value.reset_mock()
|
||||||
|
await hass.services.async_call(
|
||||||
|
DOMAIN,
|
||||||
|
SERVICE_TURN_OFF,
|
||||||
|
{ATTR_ENTITY_ID: f"{DOMAIN}.test"},
|
||||||
|
blocking=True,
|
||||||
|
) # In reality, this leads to a websocket message like already tested above
|
||||||
|
set_value.assert_called_once_with(False)
|
||||||
|
|
||||||
|
|
||||||
|
async def test_remove_from_hass(hass: HomeAssistant):
|
||||||
|
"""Test removing entity."""
|
||||||
|
entry = configure_integration(hass)
|
||||||
|
test_gateway = HomeControlMockLight()
|
||||||
|
with patch(
|
||||||
|
"homeassistant.components.devolo_home_control.HomeControl",
|
||||||
|
side_effect=[test_gateway, HomeControlMock()],
|
||||||
|
):
|
||||||
|
await hass.config_entries.async_setup(entry.entry_id)
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
state = hass.states.get(f"{DOMAIN}.test")
|
||||||
|
assert state is not None
|
||||||
|
await hass.config_entries.async_remove(entry.entry_id)
|
||||||
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
assert len(hass.states.async_all()) == 0
|
||||||
|
assert test_gateway.publisher.unregister.call_count == 1
|
Loading…
Add table
Add a link
Reference in a new issue