Add preview support to all groups (#98951)
This commit is contained in:
parent
a741298461
commit
3e02fb1f07
9 changed files with 194 additions and 26 deletions
|
@ -24,7 +24,14 @@ from homeassistant.helpers.schema_config_entry_flow import (
|
||||||
from . import DOMAIN, GroupEntity
|
from . import DOMAIN, GroupEntity
|
||||||
from .binary_sensor import CONF_ALL, async_create_preview_binary_sensor
|
from .binary_sensor import CONF_ALL, async_create_preview_binary_sensor
|
||||||
from .const import CONF_HIDE_MEMBERS, CONF_IGNORE_NON_NUMERIC
|
from .const import CONF_HIDE_MEMBERS, CONF_IGNORE_NON_NUMERIC
|
||||||
|
from .cover import async_create_preview_cover
|
||||||
|
from .event import async_create_preview_event
|
||||||
|
from .fan import async_create_preview_fan
|
||||||
|
from .light import async_create_preview_light
|
||||||
|
from .lock import async_create_preview_lock
|
||||||
|
from .media_player import MediaPlayerGroup, async_create_preview_media_player
|
||||||
from .sensor import async_create_preview_sensor
|
from .sensor import async_create_preview_sensor
|
||||||
|
from .switch import async_create_preview_switch
|
||||||
|
|
||||||
_STATISTIC_MEASURES = [
|
_STATISTIC_MEASURES = [
|
||||||
"min",
|
"min",
|
||||||
|
@ -122,7 +129,7 @@ SENSOR_CONFIG_SCHEMA = basic_group_config_schema(
|
||||||
|
|
||||||
|
|
||||||
async def light_switch_options_schema(
|
async def light_switch_options_schema(
|
||||||
domain: str, handler: SchemaCommonFlowHandler
|
domain: str, handler: SchemaCommonFlowHandler | None
|
||||||
) -> vol.Schema:
|
) -> vol.Schema:
|
||||||
"""Generate options schema."""
|
"""Generate options schema."""
|
||||||
return (await basic_group_options_schema(domain, handler)).extend(
|
return (await basic_group_options_schema(domain, handler)).extend(
|
||||||
|
@ -177,26 +184,32 @@ CONFIG_FLOW = {
|
||||||
),
|
),
|
||||||
"cover": SchemaFlowFormStep(
|
"cover": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("cover"),
|
basic_group_config_schema("cover"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("cover"),
|
validate_user_input=set_group_type("cover"),
|
||||||
),
|
),
|
||||||
"event": SchemaFlowFormStep(
|
"event": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("event"),
|
basic_group_config_schema("event"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("event"),
|
validate_user_input=set_group_type("event"),
|
||||||
),
|
),
|
||||||
"fan": SchemaFlowFormStep(
|
"fan": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("fan"),
|
basic_group_config_schema("fan"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("fan"),
|
validate_user_input=set_group_type("fan"),
|
||||||
),
|
),
|
||||||
"light": SchemaFlowFormStep(
|
"light": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("light"),
|
basic_group_config_schema("light"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("light"),
|
validate_user_input=set_group_type("light"),
|
||||||
),
|
),
|
||||||
"lock": SchemaFlowFormStep(
|
"lock": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("lock"),
|
basic_group_config_schema("lock"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("lock"),
|
validate_user_input=set_group_type("lock"),
|
||||||
),
|
),
|
||||||
"media_player": SchemaFlowFormStep(
|
"media_player": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("media_player"),
|
basic_group_config_schema("media_player"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("media_player"),
|
validate_user_input=set_group_type("media_player"),
|
||||||
),
|
),
|
||||||
"sensor": SchemaFlowFormStep(
|
"sensor": SchemaFlowFormStep(
|
||||||
|
@ -206,6 +219,7 @@ CONFIG_FLOW = {
|
||||||
),
|
),
|
||||||
"switch": SchemaFlowFormStep(
|
"switch": SchemaFlowFormStep(
|
||||||
basic_group_config_schema("switch"),
|
basic_group_config_schema("switch"),
|
||||||
|
preview="group",
|
||||||
validate_user_input=set_group_type("switch"),
|
validate_user_input=set_group_type("switch"),
|
||||||
),
|
),
|
||||||
}
|
}
|
||||||
|
@ -217,11 +231,26 @@ OPTIONS_FLOW = {
|
||||||
binary_sensor_options_schema,
|
binary_sensor_options_schema,
|
||||||
preview="group",
|
preview="group",
|
||||||
),
|
),
|
||||||
"cover": SchemaFlowFormStep(partial(basic_group_options_schema, "cover")),
|
"cover": SchemaFlowFormStep(
|
||||||
"event": SchemaFlowFormStep(partial(basic_group_options_schema, "event")),
|
partial(basic_group_options_schema, "cover"),
|
||||||
"fan": SchemaFlowFormStep(partial(basic_group_options_schema, "fan")),
|
preview="group",
|
||||||
"light": SchemaFlowFormStep(partial(light_switch_options_schema, "light")),
|
),
|
||||||
"lock": SchemaFlowFormStep(partial(basic_group_options_schema, "lock")),
|
"event": SchemaFlowFormStep(
|
||||||
|
partial(basic_group_options_schema, "event"),
|
||||||
|
preview="group",
|
||||||
|
),
|
||||||
|
"fan": SchemaFlowFormStep(
|
||||||
|
partial(basic_group_options_schema, "fan"),
|
||||||
|
preview="group",
|
||||||
|
),
|
||||||
|
"light": SchemaFlowFormStep(
|
||||||
|
partial(light_switch_options_schema, "light"),
|
||||||
|
preview="group",
|
||||||
|
),
|
||||||
|
"lock": SchemaFlowFormStep(
|
||||||
|
partial(basic_group_options_schema, "lock"),
|
||||||
|
preview="group",
|
||||||
|
),
|
||||||
"media_player": SchemaFlowFormStep(
|
"media_player": SchemaFlowFormStep(
|
||||||
partial(basic_group_options_schema, "media_player"),
|
partial(basic_group_options_schema, "media_player"),
|
||||||
preview="group",
|
preview="group",
|
||||||
|
@ -230,17 +259,27 @@ OPTIONS_FLOW = {
|
||||||
partial(sensor_options_schema, "sensor"),
|
partial(sensor_options_schema, "sensor"),
|
||||||
preview="group",
|
preview="group",
|
||||||
),
|
),
|
||||||
"switch": SchemaFlowFormStep(partial(light_switch_options_schema, "switch")),
|
"switch": SchemaFlowFormStep(
|
||||||
|
partial(light_switch_options_schema, "switch"),
|
||||||
|
preview="group",
|
||||||
|
),
|
||||||
}
|
}
|
||||||
|
|
||||||
PREVIEW_OPTIONS_SCHEMA: dict[str, vol.Schema] = {}
|
PREVIEW_OPTIONS_SCHEMA: dict[str, vol.Schema] = {}
|
||||||
|
|
||||||
CREATE_PREVIEW_ENTITY: dict[
|
CREATE_PREVIEW_ENTITY: dict[
|
||||||
str,
|
str,
|
||||||
Callable[[str, dict[str, Any]], GroupEntity],
|
Callable[[str, dict[str, Any]], GroupEntity | MediaPlayerGroup],
|
||||||
] = {
|
] = {
|
||||||
"binary_sensor": async_create_preview_binary_sensor,
|
"binary_sensor": async_create_preview_binary_sensor,
|
||||||
|
"cover": async_create_preview_cover,
|
||||||
|
"event": async_create_preview_event,
|
||||||
|
"fan": async_create_preview_fan,
|
||||||
|
"light": async_create_preview_light,
|
||||||
|
"lock": async_create_preview_lock,
|
||||||
|
"media_player": async_create_preview_media_player,
|
||||||
"sensor": async_create_preview_sensor,
|
"sensor": async_create_preview_sensor,
|
||||||
|
"switch": async_create_preview_switch,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -96,6 +96,18 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_cover(
|
||||||
|
name: str, validated_config: dict[str, Any]
|
||||||
|
) -> CoverGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return CoverGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class CoverGroup(GroupEntity, CoverEntity):
|
class CoverGroup(GroupEntity, CoverEntity):
|
||||||
"""Representation of a CoverGroup."""
|
"""Representation of a CoverGroup."""
|
||||||
|
|
||||||
|
|
|
@ -2,6 +2,7 @@
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
import itertools
|
import itertools
|
||||||
|
from typing import Any
|
||||||
|
|
||||||
import voluptuous as vol
|
import voluptuous as vol
|
||||||
|
|
||||||
|
@ -87,6 +88,18 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_event(
|
||||||
|
name: str, validated_config: dict[str, Any]
|
||||||
|
) -> EventGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return EventGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class EventGroup(GroupEntity, EventEntity):
|
class EventGroup(GroupEntity, EventEntity):
|
||||||
"""Representation of an event group."""
|
"""Representation of an event group."""
|
||||||
|
|
||||||
|
|
|
@ -96,6 +96,16 @@ async def async_setup_entry(
|
||||||
async_add_entities([FanGroup(config_entry.entry_id, config_entry.title, entities)])
|
async_add_entities([FanGroup(config_entry.entry_id, config_entry.title, entities)])
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_fan(name: str, validated_config: dict[str, Any]) -> FanGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return FanGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class FanGroup(GroupEntity, FanEntity):
|
class FanGroup(GroupEntity, FanEntity):
|
||||||
"""Representation of a FanGroup."""
|
"""Representation of a FanGroup."""
|
||||||
|
|
||||||
|
|
|
@ -110,6 +110,19 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_light(
|
||||||
|
name: str, validated_config: dict[str, Any]
|
||||||
|
) -> LightGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return LightGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
validated_config.get(CONF_ALL, False),
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
FORWARDED_ATTRIBUTES = frozenset(
|
FORWARDED_ATTRIBUTES = frozenset(
|
||||||
{
|
{
|
||||||
ATTR_BRIGHTNESS,
|
ATTR_BRIGHTNESS,
|
||||||
|
|
|
@ -90,6 +90,16 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_lock(name: str, validated_config: dict[str, Any]) -> LockGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return LockGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class LockGroup(GroupEntity, LockEntity):
|
class LockGroup(GroupEntity, LockEntity):
|
||||||
"""Representation of a lock group."""
|
"""Representation of a lock group."""
|
||||||
|
|
||||||
|
|
|
@ -1,7 +1,7 @@
|
||||||
"""Platform allowing several media players to be grouped into one media player."""
|
"""Platform allowing several media players to be grouped into one media player."""
|
||||||
from __future__ import annotations
|
from __future__ import annotations
|
||||||
|
|
||||||
from collections.abc import Mapping
|
from collections.abc import Callable, Mapping
|
||||||
from contextlib import suppress
|
from contextlib import suppress
|
||||||
from typing import Any
|
from typing import Any
|
||||||
|
|
||||||
|
@ -44,7 +44,7 @@ from homeassistant.const import (
|
||||||
STATE_UNAVAILABLE,
|
STATE_UNAVAILABLE,
|
||||||
STATE_UNKNOWN,
|
STATE_UNKNOWN,
|
||||||
)
|
)
|
||||||
from homeassistant.core import HomeAssistant, State, callback
|
from homeassistant.core import CALLBACK_TYPE, HomeAssistant, State, callback
|
||||||
from homeassistant.helpers import config_validation as cv, entity_registry as er
|
from homeassistant.helpers import config_validation as cv, entity_registry as er
|
||||||
from homeassistant.helpers.entity_platform import AddEntitiesCallback
|
from homeassistant.helpers.entity_platform import AddEntitiesCallback
|
||||||
from homeassistant.helpers.event import (
|
from homeassistant.helpers.event import (
|
||||||
|
@ -107,6 +107,18 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_media_player(
|
||||||
|
name: str, validated_config: dict[str, Any]
|
||||||
|
) -> MediaPlayerGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return MediaPlayerGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class MediaPlayerGroup(MediaPlayerEntity):
|
class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
"""Representation of a Media Group."""
|
"""Representation of a Media Group."""
|
||||||
|
|
||||||
|
@ -139,7 +151,8 @@ class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
self.async_update_supported_features(
|
self.async_update_supported_features(
|
||||||
event.data["entity_id"], event.data["new_state"]
|
event.data["entity_id"], event.data["new_state"]
|
||||||
)
|
)
|
||||||
self.async_update_state()
|
self.async_update_group_state()
|
||||||
|
self.async_write_ha_state()
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_supported_features(
|
def async_update_supported_features(
|
||||||
|
@ -208,6 +221,26 @@ class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
else:
|
else:
|
||||||
self._features[KEY_ENQUEUE].discard(entity_id)
|
self._features[KEY_ENQUEUE].discard(entity_id)
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_start_preview(
|
||||||
|
self,
|
||||||
|
preview_callback: Callable[[str, Mapping[str, Any]], None],
|
||||||
|
) -> CALLBACK_TYPE:
|
||||||
|
"""Render a preview."""
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_state_changed_listener(
|
||||||
|
event: EventType[EventStateChangedData] | None,
|
||||||
|
) -> None:
|
||||||
|
"""Handle child updates."""
|
||||||
|
self.async_update_group_state()
|
||||||
|
preview_callback(*self._async_generate_attributes())
|
||||||
|
|
||||||
|
async_state_changed_listener(None)
|
||||||
|
return async_track_state_change_event(
|
||||||
|
self.hass, self._entities, async_state_changed_listener
|
||||||
|
)
|
||||||
|
|
||||||
async def async_added_to_hass(self) -> None:
|
async def async_added_to_hass(self) -> None:
|
||||||
"""Register listeners."""
|
"""Register listeners."""
|
||||||
for entity_id in self._entities:
|
for entity_id in self._entities:
|
||||||
|
@ -216,7 +249,8 @@ class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
async_track_state_change_event(
|
async_track_state_change_event(
|
||||||
self.hass, self._entities, self.async_on_state_change
|
self.hass, self._entities, self.async_on_state_change
|
||||||
)
|
)
|
||||||
self.async_update_state()
|
self.async_update_group_state()
|
||||||
|
self.async_write_ha_state()
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def name(self) -> str:
|
def name(self) -> str:
|
||||||
|
@ -391,7 +425,7 @@ class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
await self.async_set_volume_level(max(0, volume_level - 0.1))
|
await self.async_set_volume_level(max(0, volume_level - 0.1))
|
||||||
|
|
||||||
@callback
|
@callback
|
||||||
def async_update_state(self) -> None:
|
def async_update_group_state(self) -> None:
|
||||||
"""Query all members and determine the media group state."""
|
"""Query all members and determine the media group state."""
|
||||||
states = [
|
states = [
|
||||||
state.state
|
state.state
|
||||||
|
@ -455,4 +489,3 @@ class MediaPlayerGroup(MediaPlayerEntity):
|
||||||
supported_features |= MediaPlayerEntityFeature.MEDIA_ENQUEUE
|
supported_features |= MediaPlayerEntityFeature.MEDIA_ENQUEUE
|
||||||
|
|
||||||
self._attr_supported_features = supported_features
|
self._attr_supported_features = supported_features
|
||||||
self.async_write_ha_state()
|
|
||||||
|
|
|
@ -85,6 +85,19 @@ async def async_setup_entry(
|
||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@callback
|
||||||
|
def async_create_preview_switch(
|
||||||
|
name: str, validated_config: dict[str, Any]
|
||||||
|
) -> SwitchGroup:
|
||||||
|
"""Create a preview sensor."""
|
||||||
|
return SwitchGroup(
|
||||||
|
None,
|
||||||
|
name,
|
||||||
|
validated_config[CONF_ENTITIES],
|
||||||
|
validated_config.get(CONF_ALL, False),
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
class SwitchGroup(GroupEntity, SwitchEntity):
|
class SwitchGroup(GroupEntity, SwitchEntity):
|
||||||
"""Representation of a switch group."""
|
"""Representation of a switch group."""
|
||||||
|
|
||||||
|
|
|
@ -466,17 +466,34 @@ async def test_options_flow_hides_members(
|
||||||
assert registry.async_get(f"{group_type}.three").hidden_by == hidden_by
|
assert registry.async_get(f"{group_type}.three").hidden_by == hidden_by
|
||||||
|
|
||||||
|
|
||||||
|
COVER_ATTRS = [{"supported_features": 0}, {}]
|
||||||
|
EVENT_ATTRS = [{"event_types": []}, {"event_type": None}]
|
||||||
|
FAN_ATTRS = [{"supported_features": 0}, {"assumed_state": True}]
|
||||||
|
LIGHT_ATTRS = [
|
||||||
|
{
|
||||||
|
"icon": "mdi:lightbulb-group",
|
||||||
|
"supported_color_modes": ["onoff"],
|
||||||
|
"supported_features": 0,
|
||||||
|
},
|
||||||
|
{"color_mode": "onoff"},
|
||||||
|
]
|
||||||
|
LOCK_ATTRS = [{"supported_features": 1}, {}]
|
||||||
|
MEDIA_PLAYER_ATTRS = [{"supported_features": 0}, {}]
|
||||||
|
SENSOR_ATTRS = [{"icon": "mdi:calculator"}, {"max_entity_id": "sensor.input_two"}]
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize(
|
@pytest.mark.parametrize(
|
||||||
("domain", "extra_user_input", "input_states", "group_state", "extra_attributes"),
|
("domain", "extra_user_input", "input_states", "group_state", "extra_attributes"),
|
||||||
[
|
[
|
||||||
("binary_sensor", {"all": True}, ["on", "off"], "off", [{}, {}]),
|
("binary_sensor", {"all": True}, ["on", "off"], "off", [{}, {}]),
|
||||||
(
|
("cover", {}, ["open", "closed"], "open", COVER_ATTRS),
|
||||||
"sensor",
|
("event", {}, ["", ""], "unknown", EVENT_ATTRS),
|
||||||
{"type": "max"},
|
("fan", {}, ["on", "off"], "on", FAN_ATTRS),
|
||||||
["10", "20"],
|
("light", {}, ["on", "off"], "on", LIGHT_ATTRS),
|
||||||
"20.0",
|
("lock", {}, ["unlocked", "locked"], "unlocked", LOCK_ATTRS),
|
||||||
[{"icon": "mdi:calculator"}, {"max_entity_id": "sensor.input_two"}],
|
("media_player", {}, ["on", "off"], "on", MEDIA_PLAYER_ATTRS),
|
||||||
),
|
("sensor", {"type": "max"}, ["10", "20"], "20.0", SENSOR_ATTRS),
|
||||||
|
("switch", {}, ["on", "off"], "on", [{}, {}]),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
async def test_config_flow_preview(
|
async def test_config_flow_preview(
|
||||||
|
@ -553,15 +570,22 @@ async def test_config_flow_preview(
|
||||||
"extra_attributes",
|
"extra_attributes",
|
||||||
),
|
),
|
||||||
[
|
[
|
||||||
("binary_sensor", {"all": True}, {"all": False}, ["on", "off"], "on", {}),
|
("binary_sensor", {"all": True}, {"all": False}, ["on", "off"], "on", [{}, {}]),
|
||||||
|
("cover", {}, {}, ["open", "closed"], "open", COVER_ATTRS),
|
||||||
|
("event", {}, {}, ["", ""], "unknown", EVENT_ATTRS),
|
||||||
|
("fan", {}, {}, ["on", "off"], "on", FAN_ATTRS),
|
||||||
|
("light", {}, {}, ["on", "off"], "on", LIGHT_ATTRS),
|
||||||
|
("lock", {}, {}, ["unlocked", "locked"], "unlocked", LOCK_ATTRS),
|
||||||
|
("media_player", {}, {}, ["on", "off"], "on", MEDIA_PLAYER_ATTRS),
|
||||||
(
|
(
|
||||||
"sensor",
|
"sensor",
|
||||||
{"type": "min"},
|
{"type": "min"},
|
||||||
{"type": "max"},
|
{"type": "max"},
|
||||||
["10", "20"],
|
["10", "20"],
|
||||||
"20.0",
|
"20.0",
|
||||||
{"icon": "mdi:calculator", "max_entity_id": "sensor.input_two"},
|
SENSOR_ATTRS,
|
||||||
),
|
),
|
||||||
|
("switch", {}, {}, ["on", "off"], "on", [{}, {}]),
|
||||||
],
|
],
|
||||||
)
|
)
|
||||||
async def test_option_flow_preview(
|
async def test_option_flow_preview(
|
||||||
|
@ -575,8 +599,6 @@ async def test_option_flow_preview(
|
||||||
extra_attributes: dict[str, Any],
|
extra_attributes: dict[str, Any],
|
||||||
) -> None:
|
) -> None:
|
||||||
"""Test the option flow preview."""
|
"""Test the option flow preview."""
|
||||||
client = await hass_ws_client(hass)
|
|
||||||
|
|
||||||
input_entities = [f"{domain}.input_one", f"{domain}.input_two"]
|
input_entities = [f"{domain}.input_one", f"{domain}.input_two"]
|
||||||
|
|
||||||
# Setup the config entry
|
# Setup the config entry
|
||||||
|
@ -596,6 +618,8 @@ async def test_option_flow_preview(
|
||||||
assert await hass.config_entries.async_setup(config_entry.entry_id)
|
assert await hass.config_entries.async_setup(config_entry.entry_id)
|
||||||
await hass.async_block_till_done()
|
await hass.async_block_till_done()
|
||||||
|
|
||||||
|
client = await hass_ws_client(hass)
|
||||||
|
|
||||||
result = await hass.config_entries.options.async_init(config_entry.entry_id)
|
result = await hass.config_entries.options.async_init(config_entry.entry_id)
|
||||||
assert result["type"] == FlowResultType.FORM
|
assert result["type"] == FlowResultType.FORM
|
||||||
assert result["errors"] is None
|
assert result["errors"] is None
|
||||||
|
@ -619,7 +643,8 @@ async def test_option_flow_preview(
|
||||||
msg = await client.receive_json()
|
msg = await client.receive_json()
|
||||||
assert msg["event"] == {
|
assert msg["event"] == {
|
||||||
"attributes": {"entity_id": input_entities, "friendly_name": "My group"}
|
"attributes": {"entity_id": input_entities, "friendly_name": "My group"}
|
||||||
| extra_attributes,
|
| extra_attributes[0]
|
||||||
|
| extra_attributes[1],
|
||||||
"state": group_state,
|
"state": group_state,
|
||||||
}
|
}
|
||||||
assert len(hass.states.async_all()) == 3
|
assert len(hass.states.async_all()) == 3
|
||||||
|
|
Loading…
Add table
Reference in a new issue