mirror of
https://github.com/home-assistant/core.git
synced 2025-04-24 09:17:53 +00:00
Improve axis tests (#114035)
* Combine binary sensor tests into more logical groups * Improve light tests * Clean up switch tests * Improve typing in conftest * Add typing to camera * Improve binary sensor * Improve light * Improve switch
This commit is contained in:
parent
26b6bd83fc
commit
bf8d880e5f
@ -2,8 +2,10 @@
|
||||
|
||||
from __future__ import annotations
|
||||
|
||||
from collections.abc import Generator
|
||||
from collections.abc import Callable, Generator
|
||||
from copy import deepcopy
|
||||
from types import MappingProxyType
|
||||
from typing import Any
|
||||
from unittest.mock import AsyncMock, patch
|
||||
|
||||
from axis.rtsp import Signal, State
|
||||
@ -11,6 +13,7 @@ import pytest
|
||||
import respx
|
||||
|
||||
from homeassistant.components.axis.const import DOMAIN as AXIS_DOMAIN
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.const import (
|
||||
CONF_HOST,
|
||||
CONF_MODEL,
|
||||
@ -19,6 +22,7 @@ from homeassistant.const import (
|
||||
CONF_PORT,
|
||||
CONF_USERNAME,
|
||||
)
|
||||
from homeassistant.core import HomeAssistant
|
||||
|
||||
from .const import (
|
||||
API_DISCOVERY_RESPONSE,
|
||||
@ -42,7 +46,6 @@ from .const import (
|
||||
)
|
||||
|
||||
from tests.common import MockConfigEntry
|
||||
from tests.components.light.conftest import mock_light_profiles # noqa: F401
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
@ -58,28 +61,33 @@ def mock_setup_entry() -> Generator[AsyncMock, None, None]:
|
||||
|
||||
|
||||
@pytest.fixture(name="config_entry")
|
||||
def config_entry_fixture(hass, config, options, config_entry_version):
|
||||
def config_entry_fixture(
|
||||
hass: HomeAssistant,
|
||||
config_entry_data: MappingProxyType[str, Any],
|
||||
config_entry_options: MappingProxyType[str, Any],
|
||||
config_entry_version: int,
|
||||
) -> ConfigEntry:
|
||||
"""Define a config entry fixture."""
|
||||
entry = MockConfigEntry(
|
||||
config_entry = MockConfigEntry(
|
||||
domain=AXIS_DOMAIN,
|
||||
entry_id="676abe5b73621446e6550a2e86ffe3dd",
|
||||
unique_id=FORMATTED_MAC,
|
||||
data=config,
|
||||
options=options,
|
||||
data=config_entry_data,
|
||||
options=config_entry_options,
|
||||
version=config_entry_version,
|
||||
)
|
||||
entry.add_to_hass(hass)
|
||||
return entry
|
||||
config_entry.add_to_hass(hass)
|
||||
return config_entry
|
||||
|
||||
|
||||
@pytest.fixture(name="config_entry_version")
|
||||
def config_entry_version_fixture(request):
|
||||
def config_entry_version_fixture() -> int:
|
||||
"""Define a config entry version fixture."""
|
||||
return 3
|
||||
|
||||
|
||||
@pytest.fixture(name="config")
|
||||
def config_fixture():
|
||||
@pytest.fixture(name="config_entry_data")
|
||||
def config_entry_data_fixture() -> MappingProxyType[str, Any]:
|
||||
"""Define a config entry data fixture."""
|
||||
return {
|
||||
CONF_HOST: DEFAULT_HOST,
|
||||
@ -91,8 +99,8 @@ def config_fixture():
|
||||
}
|
||||
|
||||
|
||||
@pytest.fixture(name="options")
|
||||
def options_fixture(request):
|
||||
@pytest.fixture(name="config_entry_options")
|
||||
def config_entry_options_fixture() -> MappingProxyType[str, Any]:
|
||||
"""Define a config entry options fixture."""
|
||||
return {}
|
||||
|
||||
@ -102,11 +110,14 @@ def options_fixture(request):
|
||||
|
||||
@pytest.fixture(name="mock_vapix_requests")
|
||||
def default_request_fixture(
|
||||
respx_mock, port_management_payload, param_properties_payload, param_ports_payload
|
||||
):
|
||||
respx_mock: respx,
|
||||
port_management_payload: dict[str, Any],
|
||||
param_properties_payload: dict[str, Any],
|
||||
param_ports_payload: dict[str, Any],
|
||||
) -> Callable[[str], None]:
|
||||
"""Mock default Vapix requests responses."""
|
||||
|
||||
def __mock_default_requests(host):
|
||||
def __mock_default_requests(host: str) -> None:
|
||||
respx_mock(base_url=f"http://{host}:80")
|
||||
|
||||
if host != DEFAULT_HOST:
|
||||
@ -196,13 +207,13 @@ def default_request_fixture(
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def api_discovery_items():
|
||||
def api_discovery_items() -> dict[str, Any]:
|
||||
"""Additional Apidiscovery items."""
|
||||
return {}
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def api_discovery_fixture(api_discovery_items):
|
||||
def api_discovery_fixture(api_discovery_items: dict[str, Any]) -> None:
|
||||
"""Apidiscovery mock response."""
|
||||
data = deepcopy(API_DISCOVERY_RESPONSE)
|
||||
if api_discovery_items:
|
||||
@ -211,34 +222,36 @@ def api_discovery_fixture(api_discovery_items):
|
||||
|
||||
|
||||
@pytest.fixture(name="port_management_payload")
|
||||
def io_port_management_data_fixture():
|
||||
def io_port_management_data_fixture() -> dict[str, Any]:
|
||||
"""Property parameter data."""
|
||||
return PORT_MANAGEMENT_RESPONSE
|
||||
|
||||
|
||||
@pytest.fixture(name="param_properties_payload")
|
||||
def param_properties_data_fixture():
|
||||
def param_properties_data_fixture() -> dict[str, Any]:
|
||||
"""Property parameter data."""
|
||||
return PROPERTIES_RESPONSE
|
||||
|
||||
|
||||
@pytest.fixture(name="param_ports_payload")
|
||||
def param_ports_data_fixture():
|
||||
def param_ports_data_fixture() -> dict[str, Any]:
|
||||
"""Property parameter data."""
|
||||
return PORTS_RESPONSE
|
||||
|
||||
|
||||
@pytest.fixture(name="setup_default_vapix_requests")
|
||||
def default_vapix_requests_fixture(mock_vapix_requests):
|
||||
def default_vapix_requests_fixture(mock_vapix_requests: Callable[[str], None]) -> None:
|
||||
"""Mock default Vapix requests responses."""
|
||||
mock_vapix_requests(DEFAULT_HOST)
|
||||
|
||||
|
||||
@pytest.fixture(name="prepare_config_entry")
|
||||
async def prep_config_entry_fixture(hass, config_entry, setup_default_vapix_requests):
|
||||
async def prep_config_entry_fixture(
|
||||
hass: HomeAssistant, config_entry: ConfigEntry, setup_default_vapix_requests: None
|
||||
) -> Callable[[], ConfigEntry]:
|
||||
"""Fixture factory to set up Axis network device."""
|
||||
|
||||
async def __mock_setup_config_entry():
|
||||
async def __mock_setup_config_entry() -> ConfigEntry:
|
||||
assert await hass.config_entries.async_setup(config_entry.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
return config_entry
|
||||
@ -247,7 +260,9 @@ async def prep_config_entry_fixture(hass, config_entry, setup_default_vapix_requ
|
||||
|
||||
|
||||
@pytest.fixture(name="setup_config_entry")
|
||||
async def setup_config_entry_fixture(hass, config_entry, setup_default_vapix_requests):
|
||||
async def setup_config_entry_fixture(
|
||||
hass: HomeAssistant, config_entry: ConfigEntry, setup_default_vapix_requests: None
|
||||
) -> ConfigEntry:
|
||||
"""Define a fixture to set up Axis network device."""
|
||||
assert await hass.config_entries.async_setup(config_entry.entry_id)
|
||||
await hass.async_block_till_done()
|
||||
@ -258,24 +273,24 @@ async def setup_config_entry_fixture(hass, config_entry, setup_default_vapix_req
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def mock_axis_rtspclient():
|
||||
def mock_axis_rtspclient() -> Generator[Callable[[dict | None, str], None], None, None]:
|
||||
"""No real RTSP communication allowed."""
|
||||
with patch("axis.stream_manager.RTSPClient") as rtsp_client_mock:
|
||||
rtsp_client_mock.return_value.session.state = State.STOPPED
|
||||
|
||||
async def start_stream():
|
||||
async def start_stream() -> None:
|
||||
"""Set state to playing when calling RTSPClient.start."""
|
||||
rtsp_client_mock.return_value.session.state = State.PLAYING
|
||||
|
||||
rtsp_client_mock.return_value.start = start_stream
|
||||
|
||||
def stop_stream():
|
||||
def stop_stream() -> None:
|
||||
"""Set state to stopped when calling RTSPClient.stop."""
|
||||
rtsp_client_mock.return_value.session.state = State.STOPPED
|
||||
|
||||
rtsp_client_mock.return_value.stop = stop_stream
|
||||
|
||||
def make_rtsp_call(data: dict | None = None, state: str = ""):
|
||||
def make_rtsp_call(data: dict | None = None, state: str = "") -> None:
|
||||
"""Generate a RTSP call."""
|
||||
axis_streammanager_session_callback = rtsp_client_mock.call_args[0][4]
|
||||
|
||||
@ -291,7 +306,9 @@ def mock_axis_rtspclient():
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def mock_rtsp_event(mock_axis_rtspclient):
|
||||
def mock_rtsp_event(
|
||||
mock_axis_rtspclient: Callable[[dict | None, str], None],
|
||||
) -> Callable[[str, str, str, str, str, str], None]:
|
||||
"""Fixture to allow mocking received RTSP events."""
|
||||
|
||||
def send_event(
|
||||
@ -342,7 +359,9 @@ def mock_rtsp_event(mock_axis_rtspclient):
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def mock_rtsp_signal_state(mock_axis_rtspclient):
|
||||
def mock_rtsp_signal_state(
|
||||
mock_axis_rtspclient: Callable[[dict | None, str], None],
|
||||
) -> Callable[[bool], None]:
|
||||
"""Fixture to allow mocking RTSP state signalling."""
|
||||
|
||||
def send_signal(connected: bool) -> None:
|
||||
|
@ -1,54 +1,20 @@
|
||||
"""Axis binary sensor platform tests."""
|
||||
|
||||
from collections.abc import Callable
|
||||
|
||||
import pytest
|
||||
|
||||
from homeassistant.components.axis.const import DOMAIN as AXIS_DOMAIN
|
||||
from homeassistant.components.binary_sensor import (
|
||||
DOMAIN as BINARY_SENSOR_DOMAIN,
|
||||
BinarySensorDeviceClass,
|
||||
)
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.const import STATE_OFF, STATE_ON
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.setup import async_setup_component
|
||||
|
||||
from .const import NAME
|
||||
|
||||
|
||||
async def test_platform_manually_configured(hass: HomeAssistant) -> None:
|
||||
"""Test that nothing happens when platform is manually configured."""
|
||||
assert (
|
||||
await async_setup_component(
|
||||
hass,
|
||||
BINARY_SENSOR_DOMAIN,
|
||||
{BINARY_SENSOR_DOMAIN: {"platform": AXIS_DOMAIN}},
|
||||
)
|
||||
is True
|
||||
)
|
||||
|
||||
assert AXIS_DOMAIN not in hass.data
|
||||
|
||||
|
||||
async def test_no_binary_sensors(hass: HomeAssistant, setup_config_entry) -> None:
|
||||
"""Test that no sensors in Axis results in no sensor entities."""
|
||||
assert not hass.states.async_entity_ids(BINARY_SENSOR_DOMAIN)
|
||||
|
||||
|
||||
async def test_unsupported_binary_sensors(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event
|
||||
) -> None:
|
||||
"""Test that unsupported sensors are not loaded."""
|
||||
mock_rtsp_event(
|
||||
topic="tns1:PTZController/tnsaxis:PTZPresets/Channel_1",
|
||||
data_type="on_preset",
|
||||
data_value="1",
|
||||
source_name="PresetToken",
|
||||
source_idx="0",
|
||||
)
|
||||
await hass.async_block_till_done()
|
||||
|
||||
assert len(hass.states.async_entity_ids(BINARY_SENSOR_DOMAIN)) == 0
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("event", "entity"),
|
||||
[
|
||||
@ -178,10 +144,41 @@ async def test_unsupported_binary_sensors(
|
||||
"device_class": BinarySensorDeviceClass.MOTION,
|
||||
},
|
||||
),
|
||||
# Events with names generated from event ID and topic
|
||||
(
|
||||
{
|
||||
"topic": "tnsaxis:CameraApplicationPlatform/VMD/Camera1Profile9",
|
||||
"data_type": "active",
|
||||
"data_value": "1",
|
||||
},
|
||||
{
|
||||
"id": f"{BINARY_SENSOR_DOMAIN}.{NAME}_vmd4_camera1profile9",
|
||||
"state": STATE_ON,
|
||||
"name": f"{NAME} VMD4 Camera1Profile9",
|
||||
"device_class": BinarySensorDeviceClass.MOTION,
|
||||
},
|
||||
),
|
||||
(
|
||||
{
|
||||
"topic": "tnsaxis:CameraApplicationPlatform/ObjectAnalytics/Device1Scenario8",
|
||||
"data_type": "active",
|
||||
"data_value": "1",
|
||||
},
|
||||
{
|
||||
"id": f"{BINARY_SENSOR_DOMAIN}.{NAME}_object_analytics_device1scenario8",
|
||||
"state": STATE_ON,
|
||||
"name": f"{NAME} Object Analytics Device1Scenario8",
|
||||
"device_class": BinarySensorDeviceClass.MOTION,
|
||||
},
|
||||
),
|
||||
],
|
||||
)
|
||||
async def test_binary_sensors(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event, event, entity
|
||||
hass: HomeAssistant,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
event: dict[str, str],
|
||||
entity: dict[str, str],
|
||||
) -> None:
|
||||
"""Test that sensors are loaded properly."""
|
||||
mock_rtsp_event(**event)
|
||||
@ -198,6 +195,15 @@ async def test_binary_sensors(
|
||||
@pytest.mark.parametrize(
|
||||
("event"),
|
||||
[
|
||||
# Event with unsupported topic
|
||||
{
|
||||
"topic": "tns1:PTZController/tnsaxis:PTZPresets/Channel_1",
|
||||
"data_type": "on_preset",
|
||||
"data_value": "1",
|
||||
"source_name": "PresetToken",
|
||||
"source_idx": "0",
|
||||
},
|
||||
# Event with unsupported source_idx
|
||||
{
|
||||
"topic": "tns1:Device/tnsaxis:IO/Port",
|
||||
"data_type": "state",
|
||||
@ -206,6 +212,7 @@ async def test_binary_sensors(
|
||||
"source_name": "port",
|
||||
"source_idx": "-1",
|
||||
},
|
||||
# Event with unsupported ID in topic 'ANY'
|
||||
{
|
||||
"topic": "tnsaxis:CameraApplicationPlatform/VMD/Camera1ProfileANY",
|
||||
"data_type": "active",
|
||||
@ -219,40 +226,12 @@ async def test_binary_sensors(
|
||||
],
|
||||
)
|
||||
async def test_unsupported_events(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event, event
|
||||
hass: HomeAssistant,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
event: dict[str, str],
|
||||
) -> None:
|
||||
"""Validate nothing breaks with unsupported events."""
|
||||
mock_rtsp_event(**event)
|
||||
await hass.async_block_till_done()
|
||||
assert len(hass.states.async_entity_ids(BINARY_SENSOR_DOMAIN)) == 0
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("event", "entity_id"),
|
||||
[
|
||||
(
|
||||
{
|
||||
"topic": "tnsaxis:CameraApplicationPlatform/VMD/Camera1Profile9",
|
||||
"data_type": "active",
|
||||
"data_value": "1",
|
||||
},
|
||||
"binary_sensor.name_vmd4_camera1profile9",
|
||||
),
|
||||
(
|
||||
{
|
||||
"topic": "tnsaxis:CameraApplicationPlatform/ObjectAnalytics/Device1Scenario8",
|
||||
"data_type": "active",
|
||||
"data_value": "1",
|
||||
},
|
||||
"binary_sensor.name_object_analytics_device1scenario8",
|
||||
),
|
||||
],
|
||||
)
|
||||
async def test_no_primary_name_for_event(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event, event, entity_id
|
||||
) -> None:
|
||||
"""Validate fallback method for getting name works."""
|
||||
mock_rtsp_event(**event)
|
||||
await hass.async_block_till_done()
|
||||
assert len(hass.states.async_entity_ids(BINARY_SENSOR_DOMAIN)) == 1
|
||||
assert hass.states.get(entity_id)
|
||||
|
@ -1,5 +1,7 @@
|
||||
"""Axis camera platform tests."""
|
||||
|
||||
from collections.abc import Callable
|
||||
|
||||
import pytest
|
||||
|
||||
from homeassistant.components import camera
|
||||
@ -8,6 +10,7 @@ from homeassistant.components.axis.const import (
|
||||
DOMAIN as AXIS_DOMAIN,
|
||||
)
|
||||
from homeassistant.components.camera import DOMAIN as CAMERA_DOMAIN
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.const import STATE_IDLE
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.setup import async_setup_component
|
||||
@ -27,7 +30,7 @@ async def test_platform_manually_configured(hass: HomeAssistant) -> None:
|
||||
assert AXIS_DOMAIN not in hass.data
|
||||
|
||||
|
||||
async def test_camera(hass: HomeAssistant, setup_config_entry) -> None:
|
||||
async def test_camera(hass: HomeAssistant, setup_config_entry: ConfigEntry) -> None:
|
||||
"""Test that Axis camera platform is loaded properly."""
|
||||
assert len(hass.states.async_entity_ids(CAMERA_DOMAIN)) == 1
|
||||
|
||||
@ -46,9 +49,9 @@ async def test_camera(hass: HomeAssistant, setup_config_entry) -> None:
|
||||
)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("options", [{CONF_STREAM_PROFILE: "profile_1"}])
|
||||
@pytest.mark.parametrize("config_entry_options", [{CONF_STREAM_PROFILE: "profile_1"}])
|
||||
async def test_camera_with_stream_profile(
|
||||
hass: HomeAssistant, setup_config_entry
|
||||
hass: HomeAssistant, setup_config_entry: ConfigEntry
|
||||
) -> None:
|
||||
"""Test that Axis camera entity is using the correct path with stream profike."""
|
||||
assert len(hass.states.async_entity_ids(CAMERA_DOMAIN)) == 1
|
||||
@ -83,7 +86,9 @@ root.Properties.System.SerialNumber={MAC}
|
||||
|
||||
|
||||
@pytest.mark.parametrize("param_properties_payload", [property_data])
|
||||
async def test_camera_disabled(hass: HomeAssistant, prepare_config_entry) -> None:
|
||||
async def test_camera_disabled(
|
||||
hass: HomeAssistant, prepare_config_entry: Callable[[], ConfigEntry]
|
||||
) -> None:
|
||||
"""Test that Axis camera platform is loaded properly but does not create camera entity."""
|
||||
await prepare_config_entry()
|
||||
assert len(hass.states.async_entity_ids(CAMERA_DOMAIN)) == 0
|
||||
|
@ -45,7 +45,7 @@ def hass_mock_forward_entry_setup(hass):
|
||||
async def test_device_setup(
|
||||
hass: HomeAssistant,
|
||||
forward_entry_setup,
|
||||
config,
|
||||
config_entry_data,
|
||||
setup_config_entry,
|
||||
device_registry: dr.DeviceRegistry,
|
||||
) -> None:
|
||||
@ -63,9 +63,9 @@ async def test_device_setup(
|
||||
assert forward_entry_setup.mock_calls[2][1][1] == "light"
|
||||
assert forward_entry_setup.mock_calls[3][1][1] == "switch"
|
||||
|
||||
assert hub.config.host == config[CONF_HOST]
|
||||
assert hub.config.model == config[CONF_MODEL]
|
||||
assert hub.config.name == config[CONF_NAME]
|
||||
assert hub.config.host == config_entry_data[CONF_HOST]
|
||||
assert hub.config.model == config_entry_data[CONF_MODEL]
|
||||
assert hub.config.name == config_entry_data[CONF_NAME]
|
||||
assert hub.unique_id == FORMATTED_MAC
|
||||
|
||||
device_entry = device_registry.async_get_device(
|
||||
@ -206,11 +206,11 @@ async def test_device_unknown_error(
|
||||
assert hass.data[AXIS_DOMAIN] == {}
|
||||
|
||||
|
||||
async def test_shutdown(config) -> None:
|
||||
async def test_shutdown(config_entry_data) -> None:
|
||||
"""Successful shutdown."""
|
||||
hass = Mock()
|
||||
entry = Mock()
|
||||
entry.data = config
|
||||
entry.data = config_entry_data
|
||||
|
||||
mock_api = Mock()
|
||||
mock_api.vapix.serial_number = FORMATTED_MAC
|
||||
@ -221,25 +221,27 @@ async def test_shutdown(config) -> None:
|
||||
assert len(axis_device.api.stream.stop.mock_calls) == 1
|
||||
|
||||
|
||||
async def test_get_device_fails(hass: HomeAssistant, config) -> None:
|
||||
async def test_get_device_fails(hass: HomeAssistant, config_entry_data) -> None:
|
||||
"""Device unauthorized yields authentication required error."""
|
||||
with patch(
|
||||
"axis.vapix.vapix.Vapix.initialize", side_effect=axislib.Unauthorized
|
||||
), pytest.raises(axis.errors.AuthenticationRequired):
|
||||
await axis.hub.get_axis_api(hass, config)
|
||||
await axis.hub.get_axis_api(hass, config_entry_data)
|
||||
|
||||
|
||||
async def test_get_device_device_unavailable(hass: HomeAssistant, config) -> None:
|
||||
async def test_get_device_device_unavailable(
|
||||
hass: HomeAssistant, config_entry_data
|
||||
) -> None:
|
||||
"""Device unavailable yields cannot connect error."""
|
||||
with patch(
|
||||
"axis.vapix.vapix.Vapix.request", side_effect=axislib.RequestError
|
||||
), pytest.raises(axis.errors.CannotConnect):
|
||||
await axis.hub.get_axis_api(hass, config)
|
||||
await axis.hub.get_axis_api(hass, config_entry_data)
|
||||
|
||||
|
||||
async def test_get_device_unknown_error(hass: HomeAssistant, config) -> None:
|
||||
async def test_get_device_unknown_error(hass: HomeAssistant, config_entry_data) -> None:
|
||||
"""Device yield unknown error."""
|
||||
with patch(
|
||||
"axis.vapix.vapix.Vapix.request", side_effect=axislib.AxisException
|
||||
), pytest.raises(axis.errors.AuthenticationRequired):
|
||||
await axis.hub.get_axis_api(hass, config)
|
||||
await axis.hub.get_axis_api(hass, config_entry_data)
|
||||
|
@ -1,13 +1,15 @@
|
||||
"""Axis light platform tests."""
|
||||
|
||||
from collections.abc import Callable
|
||||
from typing import Any
|
||||
from unittest.mock import patch
|
||||
|
||||
from axis.vapix.models.api import CONTEXT
|
||||
import pytest
|
||||
import respx
|
||||
|
||||
from homeassistant.components.axis.const import DOMAIN as AXIS_DOMAIN
|
||||
from homeassistant.components.light import ATTR_BRIGHTNESS, DOMAIN as LIGHT_DOMAIN
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.const import (
|
||||
ATTR_ENTITY_ID,
|
||||
SERVICE_TURN_OFF,
|
||||
@ -16,7 +18,6 @@ from homeassistant.const import (
|
||||
STATE_ON,
|
||||
)
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.setup import async_setup_component
|
||||
|
||||
from .const import DEFAULT_HOST, NAME
|
||||
|
||||
@ -28,7 +29,7 @@ API_DISCOVERY_LIGHT_CONTROL = {
|
||||
|
||||
|
||||
@pytest.fixture
|
||||
def light_control_items():
|
||||
def light_control_items() -> list[dict[str, Any]]:
|
||||
"""Available lights."""
|
||||
return [
|
||||
{
|
||||
@ -47,7 +48,7 @@ def light_control_items():
|
||||
|
||||
|
||||
@pytest.fixture(autouse=True)
|
||||
def light_control_fixture(light_control_items):
|
||||
def light_control_fixture(light_control_items: list[dict[str, Any]]) -> None:
|
||||
"""Light control mock response."""
|
||||
data = {
|
||||
"apiVersion": "1.1",
|
||||
@ -67,24 +68,12 @@ def light_control_fixture(light_control_items):
|
||||
)
|
||||
|
||||
|
||||
async def test_platform_manually_configured(hass: HomeAssistant) -> None:
|
||||
"""Test that nothing happens when platform is manually configured."""
|
||||
assert await async_setup_component(
|
||||
hass, LIGHT_DOMAIN, {LIGHT_DOMAIN: {"platform": AXIS_DOMAIN}}
|
||||
)
|
||||
|
||||
assert AXIS_DOMAIN not in hass.data
|
||||
|
||||
|
||||
async def test_no_lights(hass: HomeAssistant, setup_config_entry) -> None:
|
||||
"""Test that no light events in Axis results in no light entities."""
|
||||
assert not hass.states.async_entity_ids(LIGHT_DOMAIN)
|
||||
|
||||
|
||||
@pytest.mark.parametrize("api_discovery_items", [API_DISCOVERY_LIGHT_CONTROL])
|
||||
@pytest.mark.parametrize("light_control_items", [[]])
|
||||
async def test_no_light_entity_without_light_control_representation(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event
|
||||
hass: HomeAssistant,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
) -> None:
|
||||
"""Verify no lights entities get created without light control representation."""
|
||||
mock_rtsp_event(
|
||||
@ -102,10 +91,10 @@ async def test_no_light_entity_without_light_control_representation(
|
||||
@pytest.mark.parametrize("api_discovery_items", [API_DISCOVERY_LIGHT_CONTROL])
|
||||
async def test_lights(
|
||||
hass: HomeAssistant,
|
||||
respx_mock,
|
||||
setup_config_entry,
|
||||
mock_rtsp_event,
|
||||
api_discovery_items,
|
||||
respx_mock: respx,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
api_discovery_items: dict[str, Any],
|
||||
) -> None:
|
||||
"""Test that lights are loaded properly."""
|
||||
# Add light
|
||||
|
@ -1,12 +1,13 @@
|
||||
"""Axis switch platform tests."""
|
||||
|
||||
from collections.abc import Callable
|
||||
from unittest.mock import patch
|
||||
|
||||
from axis.vapix.models.api import CONTEXT
|
||||
import pytest
|
||||
|
||||
from homeassistant.components.axis.const import DOMAIN as AXIS_DOMAIN
|
||||
from homeassistant.components.switch import DOMAIN as SWITCH_DOMAIN
|
||||
from homeassistant.config_entries import ConfigEntry
|
||||
from homeassistant.const import (
|
||||
ATTR_ENTITY_ID,
|
||||
SERVICE_TURN_OFF,
|
||||
@ -15,25 +16,9 @@ from homeassistant.const import (
|
||||
STATE_ON,
|
||||
)
|
||||
from homeassistant.core import HomeAssistant
|
||||
from homeassistant.setup import async_setup_component
|
||||
|
||||
from .const import API_DISCOVERY_PORT_MANAGEMENT, NAME
|
||||
|
||||
|
||||
async def test_platform_manually_configured(hass: HomeAssistant) -> None:
|
||||
"""Test that nothing happens when platform is manually configured."""
|
||||
assert await async_setup_component(
|
||||
hass, SWITCH_DOMAIN, {SWITCH_DOMAIN: {"platform": AXIS_DOMAIN}}
|
||||
)
|
||||
|
||||
assert AXIS_DOMAIN not in hass.data
|
||||
|
||||
|
||||
async def test_no_switches(hass: HomeAssistant, setup_config_entry) -> None:
|
||||
"""Test that no output events in Axis results in no switch entities."""
|
||||
assert not hass.states.async_entity_ids(SWITCH_DOMAIN)
|
||||
|
||||
|
||||
PORT_DATA = """root.IOPort.I0.Configurable=yes
|
||||
root.IOPort.I0.Direction=output
|
||||
root.IOPort.I0.Output.Name=Doorbell
|
||||
@ -47,7 +32,9 @@ root.IOPort.I1.Output.Active=open
|
||||
|
||||
@pytest.mark.parametrize("param_ports_payload", [PORT_DATA])
|
||||
async def test_switches_with_port_cgi(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event
|
||||
hass: HomeAssistant,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
) -> None:
|
||||
"""Test that switches are loaded properly using port.cgi."""
|
||||
mock_rtsp_event(
|
||||
@ -130,7 +117,9 @@ PORT_MANAGEMENT_RESPONSE = {
|
||||
@pytest.mark.parametrize("api_discovery_items", [API_DISCOVERY_PORT_MANAGEMENT])
|
||||
@pytest.mark.parametrize("port_management_payload", [PORT_MANAGEMENT_RESPONSE])
|
||||
async def test_switches_with_port_management(
|
||||
hass: HomeAssistant, setup_config_entry, mock_rtsp_event
|
||||
hass: HomeAssistant,
|
||||
setup_config_entry: ConfigEntry,
|
||||
mock_rtsp_event: Callable[[str, str, str, str, str, str], None],
|
||||
) -> None:
|
||||
"""Test that switches are loaded properly using port management."""
|
||||
mock_rtsp_event(
|
||||
|
Loading…
x
Reference in New Issue
Block a user