mirror of
https://github.com/home-assistant/core.git
synced 2025-07-22 12:47:08 +00:00
Add transition and flash feature flags for MQTT JSON light (#142692)
This commit is contained in:
parent
0b02b43b11
commit
7cf63d1985
@ -56,6 +56,7 @@ ABBREVIATIONS = {
|
||||
"ent_pic": "entity_picture",
|
||||
"evt_typ": "event_types",
|
||||
"fanspd_lst": "fan_speed_list",
|
||||
"flsh": "flash",
|
||||
"flsh_tlng": "flash_time_long",
|
||||
"flsh_tsht": "flash_time_short",
|
||||
"fx_cmd_tpl": "effect_command_template",
|
||||
@ -253,6 +254,7 @@ ABBREVIATIONS = {
|
||||
"tilt_status_tpl": "tilt_status_template",
|
||||
"tit": "title",
|
||||
"t": "topic",
|
||||
"trns": "transition",
|
||||
"uniq_id": "unique_id",
|
||||
"unit_of_meas": "unit_of_measurement",
|
||||
"url_t": "url_topic",
|
||||
|
@ -87,6 +87,7 @@ CONF_EFFECT_TEMPLATE = "effect_template"
|
||||
CONF_EFFECT_VALUE_TEMPLATE = "effect_value_template"
|
||||
CONF_ENTITY_PICTURE = "entity_picture"
|
||||
CONF_EXPIRE_AFTER = "expire_after"
|
||||
CONF_FLASH = "flash"
|
||||
CONF_FLASH_TIME_LONG = "flash_time_long"
|
||||
CONF_FLASH_TIME_SHORT = "flash_time_short"
|
||||
CONF_GREEN_TEMPLATE = "green_template"
|
||||
@ -139,6 +140,7 @@ CONF_TEMP_STATE_TOPIC = "temperature_state_topic"
|
||||
CONF_TEMP_INITIAL = "initial"
|
||||
CONF_TEMP_MAX = "max_temp"
|
||||
CONF_TEMP_MIN = "min_temp"
|
||||
CONF_TRANSITION = "transition"
|
||||
CONF_XY_COMMAND_TEMPLATE = "xy_command_template"
|
||||
CONF_XY_COMMAND_TOPIC = "xy_command_topic"
|
||||
CONF_XY_STATE_TOPIC = "xy_state_topic"
|
||||
|
@ -59,6 +59,7 @@ from ..const import (
|
||||
CONF_COLOR_TEMP_KELVIN,
|
||||
CONF_COMMAND_TOPIC,
|
||||
CONF_EFFECT_LIST,
|
||||
CONF_FLASH,
|
||||
CONF_FLASH_TIME_LONG,
|
||||
CONF_FLASH_TIME_SHORT,
|
||||
CONF_MAX_KELVIN,
|
||||
@ -69,6 +70,7 @@ from ..const import (
|
||||
CONF_RETAIN,
|
||||
CONF_STATE_TOPIC,
|
||||
CONF_SUPPORTED_COLOR_MODES,
|
||||
CONF_TRANSITION,
|
||||
DEFAULT_BRIGHTNESS,
|
||||
DEFAULT_BRIGHTNESS_SCALE,
|
||||
DEFAULT_EFFECT,
|
||||
@ -93,6 +95,9 @@ DOMAIN = "mqtt_json"
|
||||
|
||||
DEFAULT_NAME = "MQTT JSON Light"
|
||||
|
||||
DEFAULT_FLASH = True
|
||||
DEFAULT_TRANSITION = True
|
||||
|
||||
_PLATFORM_SCHEMA_BASE = (
|
||||
MQTT_RW_SCHEMA.extend(
|
||||
{
|
||||
@ -103,6 +108,7 @@ _PLATFORM_SCHEMA_BASE = (
|
||||
vol.Optional(CONF_COLOR_TEMP_KELVIN, default=False): cv.boolean,
|
||||
vol.Optional(CONF_EFFECT, default=DEFAULT_EFFECT): cv.boolean,
|
||||
vol.Optional(CONF_EFFECT_LIST): vol.All(cv.ensure_list, [cv.string]),
|
||||
vol.Optional(CONF_FLASH, default=DEFAULT_FLASH): cv.boolean,
|
||||
vol.Optional(
|
||||
CONF_FLASH_TIME_LONG, default=DEFAULT_FLASH_TIME_LONG
|
||||
): cv.positive_int,
|
||||
@ -125,6 +131,7 @@ _PLATFORM_SCHEMA_BASE = (
|
||||
vol.Unique(),
|
||||
valid_supported_color_modes,
|
||||
),
|
||||
vol.Optional(CONF_TRANSITION, default=DEFAULT_TRANSITION): cv.boolean,
|
||||
vol.Optional(CONF_WHITE_SCALE, default=DEFAULT_WHITE_SCALE): vol.All(
|
||||
vol.Coerce(int), vol.Range(min=1)
|
||||
),
|
||||
@ -199,12 +206,13 @@ class MqttLightJson(MqttEntity, LightEntity, RestoreEntity):
|
||||
for key in (CONF_FLASH_TIME_SHORT, CONF_FLASH_TIME_LONG)
|
||||
}
|
||||
|
||||
self._attr_supported_features = (
|
||||
LightEntityFeature.TRANSITION | LightEntityFeature.FLASH
|
||||
)
|
||||
self._attr_supported_features |= (
|
||||
config[CONF_EFFECT] and LightEntityFeature.EFFECT
|
||||
)
|
||||
self._attr_supported_features |= config[CONF_FLASH] and LightEntityFeature.FLASH
|
||||
self._attr_supported_features |= (
|
||||
config[CONF_TRANSITION] and LightEntityFeature.TRANSITION
|
||||
)
|
||||
if supported_color_modes := self._config.get(CONF_SUPPORTED_COLOR_MODES):
|
||||
self._attr_supported_color_modes = supported_color_modes
|
||||
if self.supported_color_modes and len(self.supported_color_modes) == 1:
|
||||
|
@ -330,7 +330,9 @@ async def test_no_color_brightness_color_temp_if_no_topics(
|
||||
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
expected_features = light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
expected_features = (
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
assert state.attributes.get("rgb_color") is None
|
||||
assert state.attributes.get("brightness") is None
|
||||
@ -581,6 +583,104 @@ async def test_controlling_state_color_temp_kelvin(
|
||||
assert state.attributes.get("hs_color") == (44.098, 2.43) # temp converted to color
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("hass_config", "expected_features"),
|
||||
[
|
||||
(
|
||||
{
|
||||
mqtt.DOMAIN: {
|
||||
light.DOMAIN: {
|
||||
"schema": "json",
|
||||
"name": "test",
|
||||
"state_topic": "test_light_rgb",
|
||||
"command_topic": "test_light_rgb/set",
|
||||
}
|
||||
}
|
||||
},
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION,
|
||||
),
|
||||
(
|
||||
{
|
||||
mqtt.DOMAIN: {
|
||||
light.DOMAIN: {
|
||||
"schema": "json",
|
||||
"name": "test",
|
||||
"state_topic": "test_light_rgb",
|
||||
"command_topic": "test_light_rgb/set",
|
||||
"flash": True,
|
||||
"transition": True,
|
||||
}
|
||||
}
|
||||
},
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION,
|
||||
),
|
||||
(
|
||||
{
|
||||
mqtt.DOMAIN: {
|
||||
light.DOMAIN: {
|
||||
"schema": "json",
|
||||
"name": "test",
|
||||
"state_topic": "test_light_rgb",
|
||||
"command_topic": "test_light_rgb/set",
|
||||
"flash": True,
|
||||
"transition": False,
|
||||
}
|
||||
}
|
||||
},
|
||||
light.LightEntityFeature.FLASH,
|
||||
),
|
||||
(
|
||||
{
|
||||
mqtt.DOMAIN: {
|
||||
light.DOMAIN: {
|
||||
"schema": "json",
|
||||
"name": "test",
|
||||
"state_topic": "test_light_rgb",
|
||||
"command_topic": "test_light_rgb/set",
|
||||
"flash": False,
|
||||
"transition": True,
|
||||
}
|
||||
}
|
||||
},
|
||||
light.LightEntityFeature.TRANSITION,
|
||||
),
|
||||
(
|
||||
{
|
||||
mqtt.DOMAIN: {
|
||||
light.DOMAIN: {
|
||||
"schema": "json",
|
||||
"name": "test",
|
||||
"state_topic": "test_light_rgb",
|
||||
"command_topic": "test_light_rgb/set",
|
||||
"flash": False,
|
||||
"transition": False,
|
||||
}
|
||||
}
|
||||
},
|
||||
light.LightEntityFeature(0),
|
||||
),
|
||||
],
|
||||
ids=[
|
||||
"default",
|
||||
"explicit_on",
|
||||
"flash_only",
|
||||
"transition_only",
|
||||
"no_flash_not_transition",
|
||||
],
|
||||
)
|
||||
async def test_flash_and_transition_feature_flags(
|
||||
hass: HomeAssistant,
|
||||
mqtt_mock_entry: MqttMockHAClientGenerator,
|
||||
expected_features: light.LightEntityFeature,
|
||||
) -> None:
|
||||
"""Test for no RGB, brightness, color temp, effector XY."""
|
||||
await mqtt_mock_entry()
|
||||
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
"hass_config",
|
||||
[
|
||||
@ -601,9 +701,11 @@ async def test_controlling_state_via_topic(
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
expected_features = (
|
||||
light.SUPPORT_EFFECT | light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
light.LightEntityFeature.EFFECT
|
||||
| light.LightEntityFeature.FLASH
|
||||
| light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
assert state.attributes.get("brightness") is None
|
||||
assert state.attributes.get("color_mode") is None
|
||||
assert state.attributes.get("color_temp_kelvin") is None
|
||||
@ -799,9 +901,11 @@ async def test_sending_mqtt_commands_and_optimistic(
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_ON
|
||||
expected_features = (
|
||||
light.SUPPORT_EFFECT | light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
light.LightEntityFeature.EFFECT
|
||||
| light.LightEntityFeature.FLASH
|
||||
| light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
assert state.attributes.get("brightness") == 95
|
||||
assert state.attributes.get("color_mode") == "rgb"
|
||||
assert state.attributes.get("color_temp_kelvin") is None
|
||||
@ -1457,9 +1561,11 @@ async def test_effect(
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
expected_features = (
|
||||
light.SUPPORT_EFFECT | light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
light.LightEntityFeature.EFFECT
|
||||
| light.LightEntityFeature.FLASH
|
||||
| light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
|
||||
await common.async_turn_on(hass, "light.test")
|
||||
|
||||
@ -1523,8 +1629,10 @@ async def test_flash_short_and_long(
|
||||
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
expected_features = light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
expected_features = (
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
|
||||
await common.async_turn_on(hass, "light.test", flash="short")
|
||||
|
||||
@ -1586,8 +1694,10 @@ async def test_transition(
|
||||
|
||||
state = hass.states.get("light.test")
|
||||
assert state.state == STATE_UNKNOWN
|
||||
expected_features = light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
expected_features = (
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
await common.async_turn_on(hass, "light.test", transition=15)
|
||||
|
||||
mqtt_mock.async_publish.assert_called_once_with(
|
||||
@ -1766,8 +1876,10 @@ async def test_invalid_values(
|
||||
assert state.state == STATE_UNKNOWN
|
||||
color_modes = [light.ColorMode.COLOR_TEMP, light.ColorMode.HS]
|
||||
assert state.attributes.get(light.ATTR_SUPPORTED_COLOR_MODES) == color_modes
|
||||
expected_features = light.SUPPORT_FLASH | light.SUPPORT_TRANSITION
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) == expected_features
|
||||
expected_features = (
|
||||
light.LightEntityFeature.FLASH | light.LightEntityFeature.TRANSITION
|
||||
)
|
||||
assert state.attributes.get(ATTR_SUPPORTED_FEATURES) is expected_features
|
||||
assert state.attributes.get("rgb_color") is None
|
||||
assert state.attributes.get("brightness") is None
|
||||
assert state.attributes.get("color_temp_kelvin") is None
|
||||
|
Loading…
x
Reference in New Issue
Block a user