core/tests/components/zwave_js/test_light.py

591 lines
18 KiB
Python

"""Test the Z-Wave JS light platform."""
from copy import deepcopy
from zwave_js_server.event import Event
from homeassistant.components.light import (
ATTR_BRIGHTNESS,
ATTR_COLOR_MODE,
ATTR_COLOR_TEMP,
ATTR_MAX_MIREDS,
ATTR_MIN_MIREDS,
ATTR_RGB_COLOR,
ATTR_RGBW_COLOR,
ATTR_SUPPORTED_COLOR_MODES,
ATTR_TRANSITION,
DOMAIN as LIGHT_DOMAIN,
LightEntityFeature,
)
from homeassistant.const import (
ATTR_ENTITY_ID,
ATTR_SUPPORTED_FEATURES,
SERVICE_TURN_OFF,
SERVICE_TURN_ON,
STATE_OFF,
STATE_ON,
)
from .common import (
AEON_SMART_SWITCH_LIGHT_ENTITY,
BULB_6_MULTI_COLOR_LIGHT_ENTITY,
EATON_RF9640_ENTITY,
ZEN_31_ENTITY,
)
HSM200_V1_ENTITY = "light.hsm200"
async def test_light(hass, client, bulb_6_multi_color, integration):
"""Test the light entity."""
node = bulb_6_multi_color
state = hass.states.get(BULB_6_MULTI_COLOR_LIGHT_ENTITY)
assert state
assert state.state == STATE_OFF
assert state.attributes[ATTR_MIN_MIREDS] == 153
assert state.attributes[ATTR_MAX_MIREDS] == 370
assert state.attributes[ATTR_SUPPORTED_FEATURES] == LightEntityFeature.TRANSITION
assert state.attributes[ATTR_SUPPORTED_COLOR_MODES] == ["color_temp", "hs"]
# Test turning on
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 0,
"property": "targetValue",
}
assert args["value"] == 255
client.async_send_command.reset_mock()
# Test turning on with transition
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_TRANSITION: 10},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 0,
"property": "targetValue",
}
assert args["value"] == 255
assert args["options"]["transitionDuration"] == "10s"
client.async_send_command.reset_mock()
# Test brightness update from value updated event
event = Event(
type="value updated",
data={
"source": "node",
"event": "value updated",
"nodeId": 39,
"args": {
"commandClassName": "Multilevel Switch",
"commandClass": 38,
"endpoint": 0,
"property": "currentValue",
"newValue": 99,
"prevValue": 0,
"propertyName": "currentValue",
},
},
)
node.receive_event(event)
state = hass.states.get(BULB_6_MULTI_COLOR_LIGHT_ENTITY)
assert state.state == STATE_ON
assert state.attributes[ATTR_COLOR_MODE] == "color_temp"
assert state.attributes[ATTR_BRIGHTNESS] == 255
assert state.attributes[ATTR_COLOR_TEMP] == 370
assert ATTR_RGB_COLOR in state.attributes
# Test turning on with same brightness
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_BRIGHTNESS: 255},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
client.async_send_command.reset_mock()
# Test turning on with brightness
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_BRIGHTNESS: 129},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 0,
"property": "targetValue",
}
assert args["value"] == 50
assert args["options"]["transitionDuration"] == "default"
client.async_send_command.reset_mock()
# Test turning on with brightness and transition
await hass.services.async_call(
"light",
"turn_on",
{
"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY,
ATTR_BRIGHTNESS: 129,
ATTR_TRANSITION: 20,
},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 0,
"property": "targetValue",
}
assert args["value"] == 50
assert args["options"]["transitionDuration"] == "20s"
client.async_send_command.reset_mock()
# Test turning on with rgb color
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_RGB_COLOR: (255, 76, 255)},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
args = client.async_send_command.call_args_list[0][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"]["commandClass"] == 51
assert args["valueId"]["endpoint"] == 0
assert args["valueId"]["property"] == "targetColor"
assert args["value"] == {
"blue": 255,
"coldWhite": 0,
"green": 76,
"red": 255,
"warmWhite": 0,
}
# Test rgb color update from value updated event
red_event = Event(
type="value updated",
data={
"source": "node",
"event": "value updated",
"nodeId": 39,
"args": {
"commandClassName": "Color Switch",
"commandClass": 51,
"endpoint": 0,
"property": "currentColor",
"newValue": 255,
"prevValue": 0,
"propertyKey": 2,
"propertyKeyName": "Red",
},
},
)
green_event = deepcopy(red_event)
green_event.data["args"].update(
{"newValue": 76, "propertyKey": 3, "propertyKeyName": "Green"}
)
blue_event = deepcopy(red_event)
blue_event.data["args"]["propertyKey"] = 4
blue_event.data["args"]["propertyKeyName"] = "Blue"
warm_white_event = deepcopy(red_event)
warm_white_event.data["args"].update(
{"newValue": 0, "propertyKey": 0, "propertyKeyName": "Warm White"}
)
node.receive_event(warm_white_event)
node.receive_event(red_event)
node.receive_event(green_event)
node.receive_event(blue_event)
state = hass.states.get(BULB_6_MULTI_COLOR_LIGHT_ENTITY)
assert state.state == STATE_ON
assert state.attributes[ATTR_COLOR_MODE] == "hs"
assert state.attributes[ATTR_BRIGHTNESS] == 255
assert state.attributes[ATTR_RGB_COLOR] == (255, 76, 255)
assert ATTR_COLOR_TEMP not in state.attributes
client.async_send_command.reset_mock()
# Test turning on with same rgb color
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_RGB_COLOR: (255, 76, 255)},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
client.async_send_command.reset_mock()
# Test turning on with rgb color and transition
await hass.services.async_call(
"light",
"turn_on",
{
"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY,
ATTR_RGB_COLOR: (128, 76, 255),
ATTR_TRANSITION: 20,
},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
args = client.async_send_command.call_args_list[0][0][0]
assert args["options"]["transitionDuration"] == "20s"
client.async_send_command.reset_mock()
# Test turning on with color temp
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_COLOR_TEMP: 170},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
args = client.async_send_command.call_args_list[0][0][0] # red 0
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"]["commandClass"] == 51
assert args["valueId"]["endpoint"] == 0
assert args["valueId"]["property"] == "targetColor"
assert args["value"] == {
"blue": 0,
"coldWhite": 235,
"green": 0,
"red": 0,
"warmWhite": 20,
}
client.async_send_command.reset_mock()
# Test color temp update from value updated event
red_event = Event(
type="value updated",
data={
"source": "node",
"event": "value updated",
"nodeId": 39,
"args": {
"commandClassName": "Color Switch",
"commandClass": 51,
"endpoint": 0,
"property": "currentColor",
"newValue": 0,
"prevValue": 255,
"propertyKey": 2,
"propertyKeyName": "Red",
},
},
)
green_event = deepcopy(red_event)
green_event.data["args"].update(
{"newValue": 0, "prevValue": 76, "propertyKey": 3, "propertyKeyName": "Green"}
)
blue_event = deepcopy(red_event)
blue_event.data["args"]["propertyKey"] = 4
blue_event.data["args"]["propertyKeyName"] = "Blue"
warm_white_event = deepcopy(red_event)
warm_white_event.data["args"].update(
{"newValue": 20, "propertyKey": 0, "propertyKeyName": "Warm White"}
)
cold_white_event = deepcopy(red_event)
cold_white_event.data["args"].update(
{"newValue": 235, "propertyKey": 1, "propertyKeyName": "Cold White"}
)
node.receive_event(red_event)
node.receive_event(green_event)
node.receive_event(blue_event)
node.receive_event(warm_white_event)
node.receive_event(cold_white_event)
state = hass.states.get(BULB_6_MULTI_COLOR_LIGHT_ENTITY)
assert state.state == STATE_ON
assert state.attributes[ATTR_COLOR_MODE] == "color_temp"
assert state.attributes[ATTR_BRIGHTNESS] == 255
assert state.attributes[ATTR_COLOR_TEMP] == 170
assert ATTR_RGB_COLOR in state.attributes
# Test turning on with same color temp
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY, ATTR_COLOR_TEMP: 170},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
client.async_send_command.reset_mock()
# Test turning on with color temp and transition
await hass.services.async_call(
"light",
"turn_on",
{
"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY,
ATTR_COLOR_TEMP: 170,
ATTR_TRANSITION: 35,
},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
args = client.async_send_command.call_args_list[0][0][0]
assert args["options"]["transitionDuration"] == "35s"
client.async_send_command.reset_mock()
# Test turning off
await hass.services.async_call(
"light",
"turn_off",
{"entity_id": BULB_6_MULTI_COLOR_LIGHT_ENTITY},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 39
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 0,
"property": "targetValue",
}
assert args["value"] == 0
async def test_v4_dimmer_light(hass, client, eaton_rf9640_dimmer, integration):
"""Test a light that supports MultiLevelSwitch CommandClass version 4."""
state = hass.states.get(EATON_RF9640_ENTITY)
assert state
assert state.state == STATE_ON
# the light should pick currentvalue which has zwave value 22
assert state.attributes[ATTR_BRIGHTNESS] == 57
async def test_optional_light(hass, client, aeon_smart_switch_6, integration):
"""Test a device that has an additional light endpoint being identified as light."""
state = hass.states.get(AEON_SMART_SWITCH_LIGHT_ENTITY)
assert state.state == STATE_ON
async def test_rgbw_light(hass, client, zen_31, integration):
"""Test the light entity."""
state = hass.states.get(ZEN_31_ENTITY)
assert state
assert state.state == STATE_ON
assert state.attributes[ATTR_SUPPORTED_FEATURES] == LightEntityFeature.TRANSITION
# Test turning on
await hass.services.async_call(
"light",
"turn_on",
{"entity_id": ZEN_31_ENTITY, ATTR_RGBW_COLOR: (0, 0, 0, 128)},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 2
args = client.async_send_command.call_args_list[0][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 94
assert args["valueId"] == {
"commandClass": 51,
"endpoint": 1,
"property": "targetColor",
}
assert args["value"] == {"blue": 0, "green": 0, "red": 0, "warmWhite": 128}
args = client.async_send_command.call_args_list[1][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == 94
assert args["valueId"] == {
"commandClass": 38,
"endpoint": 1,
"property": "targetValue",
}
assert args["value"] == 255
client.async_send_command.reset_mock()
async def test_light_none_color_value(hass, light_color_null_values, integration):
"""Test the light entity can handle None value in current color Value."""
entity_id = "light.repeater"
state = hass.states.get(entity_id)
assert state
assert state.state == STATE_ON
assert state.attributes[ATTR_SUPPORTED_FEATURES] == LightEntityFeature.TRANSITION
assert state.attributes[ATTR_SUPPORTED_COLOR_MODES] == ["hs"]
async def test_black_is_off(hass, client, express_controls_ezmultipli, integration):
"""Test the black is off light entity."""
node = express_controls_ezmultipli
state = hass.states.get(HSM200_V1_ENTITY)
assert state.state == STATE_ON
# Attempt to turn on the light and ensure it defaults to white
await hass.services.async_call(
LIGHT_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: HSM200_V1_ENTITY},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args_list[0][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == node.node_id
assert args["valueId"] == {
"commandClass": 51,
"endpoint": 0,
"property": "targetColor",
}
assert args["value"] == {"red": 255, "green": 255, "blue": 255}
client.async_send_command.reset_mock()
# Force the light to turn off
event = Event(
type="value updated",
data={
"source": "node",
"event": "value updated",
"nodeId": node.node_id,
"args": {
"commandClassName": "Color Switch",
"commandClass": 51,
"endpoint": 0,
"property": "currentColor",
"newValue": {
"red": 0,
"green": 0,
"blue": 0,
},
"prevValue": {
"red": 0,
"green": 255,
"blue": 0,
},
"propertyName": "currentColor",
},
},
)
node.receive_event(event)
await hass.async_block_till_done()
state = hass.states.get(HSM200_V1_ENTITY)
assert state.state == STATE_OFF
# Force the light to turn on
event = Event(
type="value updated",
data={
"source": "node",
"event": "value updated",
"nodeId": node.node_id,
"args": {
"commandClassName": "Color Switch",
"commandClass": 51,
"endpoint": 0,
"property": "currentColor",
"newValue": {
"red": 0,
"green": 255,
"blue": 0,
},
"prevValue": {
"red": 0,
"green": 0,
"blue": 0,
},
"propertyName": "currentColor",
},
},
)
node.receive_event(event)
await hass.async_block_till_done()
state = hass.states.get(HSM200_V1_ENTITY)
assert state.state == STATE_ON
await hass.services.async_call(
LIGHT_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: HSM200_V1_ENTITY},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args_list[0][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == node.node_id
assert args["valueId"] == {
"commandClass": 51,
"endpoint": 0,
"property": "targetColor",
}
assert args["value"] == {"red": 0, "green": 0, "blue": 0}
client.async_send_command.reset_mock()
# Assert that the last color is restored
await hass.services.async_call(
LIGHT_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: HSM200_V1_ENTITY},
blocking=True,
)
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args_list[0][0][0]
assert args["command"] == "node.set_value"
assert args["nodeId"] == node.node_id
assert args["valueId"] == {
"commandClass": 51,
"endpoint": 0,
"property": "targetColor",
}
assert args["value"] == {"red": 0, "green": 255, "blue": 0}
client.async_send_command.reset_mock()