Add Select entity support to Google Assistant (#51997)
This commit is contained in:
parent
0ca199d8d0
commit
655f797f67
4 changed files with 105 additions and 5 deletions
|
@ -15,6 +15,7 @@ from homeassistant.components import (
|
|||
media_player,
|
||||
scene,
|
||||
script,
|
||||
select,
|
||||
sensor,
|
||||
switch,
|
||||
vacuum,
|
||||
|
@ -39,6 +40,8 @@ CONF_PRIVATE_KEY = "private_key"
|
|||
|
||||
DEFAULT_EXPOSE_BY_DEFAULT = True
|
||||
DEFAULT_EXPOSED_DOMAINS = [
|
||||
"alarm_control_panel",
|
||||
"binary_sensor",
|
||||
"climate",
|
||||
"cover",
|
||||
"fan",
|
||||
|
@ -47,15 +50,14 @@ DEFAULT_EXPOSED_DOMAINS = [
|
|||
"input_boolean",
|
||||
"input_select",
|
||||
"light",
|
||||
"lock",
|
||||
"media_player",
|
||||
"scene",
|
||||
"script",
|
||||
"select",
|
||||
"sensor",
|
||||
"switch",
|
||||
"vacuum",
|
||||
"lock",
|
||||
"binary_sensor",
|
||||
"sensor",
|
||||
"alarm_control_panel",
|
||||
]
|
||||
|
||||
PREFIX_TYPES = "action.devices.types."
|
||||
|
@ -117,6 +119,7 @@ EVENT_QUERY_RECEIVED = "google_assistant_query"
|
|||
EVENT_SYNC_RECEIVED = "google_assistant_sync"
|
||||
|
||||
DOMAIN_TO_GOOGLE_TYPES = {
|
||||
alarm_control_panel.DOMAIN: TYPE_ALARM,
|
||||
camera.DOMAIN: TYPE_CAMERA,
|
||||
climate.DOMAIN: TYPE_THERMOSTAT,
|
||||
cover.DOMAIN: TYPE_BLINDS,
|
||||
|
@ -130,9 +133,9 @@ DOMAIN_TO_GOOGLE_TYPES = {
|
|||
media_player.DOMAIN: TYPE_SETTOP,
|
||||
scene.DOMAIN: TYPE_SCENE,
|
||||
script.DOMAIN: TYPE_SCENE,
|
||||
select.DOMAIN: TYPE_SENSOR,
|
||||
switch.DOMAIN: TYPE_SWITCH,
|
||||
vacuum.DOMAIN: TYPE_VACUUM,
|
||||
alarm_control_panel.DOMAIN: TYPE_ALARM,
|
||||
}
|
||||
|
||||
DEVICE_CLASS_TO_GOOGLE_TYPES = {
|
||||
|
|
|
@ -17,6 +17,7 @@ from homeassistant.components import (
|
|||
media_player,
|
||||
scene,
|
||||
script,
|
||||
select,
|
||||
sensor,
|
||||
switch,
|
||||
vacuum,
|
||||
|
@ -1384,6 +1385,9 @@ class ModesTrait(_Trait):
|
|||
if domain == input_select.DOMAIN:
|
||||
return True
|
||||
|
||||
if domain == select.DOMAIN:
|
||||
return True
|
||||
|
||||
if domain == humidifier.DOMAIN and features & humidifier.SUPPORT_MODES:
|
||||
return True
|
||||
|
||||
|
@ -1427,6 +1431,7 @@ class ModesTrait(_Trait):
|
|||
(fan.DOMAIN, fan.ATTR_PRESET_MODES, "preset mode"),
|
||||
(media_player.DOMAIN, media_player.ATTR_SOUND_MODE_LIST, "sound mode"),
|
||||
(input_select.DOMAIN, input_select.ATTR_OPTIONS, "option"),
|
||||
(select.DOMAIN, select.ATTR_OPTIONS, "option"),
|
||||
(humidifier.DOMAIN, humidifier.ATTR_AVAILABLE_MODES, "mode"),
|
||||
(light.DOMAIN, light.ATTR_EFFECT_LIST, "effect"),
|
||||
):
|
||||
|
@ -1459,6 +1464,8 @@ class ModesTrait(_Trait):
|
|||
mode_settings["sound mode"] = attrs.get(media_player.ATTR_SOUND_MODE)
|
||||
elif self.state.domain == input_select.DOMAIN:
|
||||
mode_settings["option"] = self.state.state
|
||||
elif self.state.domain == select.DOMAIN:
|
||||
mode_settings["option"] = self.state.state
|
||||
elif self.state.domain == humidifier.DOMAIN:
|
||||
if ATTR_MODE in attrs:
|
||||
mode_settings["mode"] = attrs.get(ATTR_MODE)
|
||||
|
@ -1503,6 +1510,20 @@ class ModesTrait(_Trait):
|
|||
)
|
||||
return
|
||||
|
||||
if self.state.domain == select.DOMAIN:
|
||||
option = settings["option"]
|
||||
await self.hass.services.async_call(
|
||||
select.DOMAIN,
|
||||
select.SERVICE_SELECT_OPTION,
|
||||
{
|
||||
ATTR_ENTITY_ID: self.state.entity_id,
|
||||
select.ATTR_OPTION: option,
|
||||
},
|
||||
blocking=True,
|
||||
context=data.context,
|
||||
)
|
||||
return
|
||||
|
||||
if self.state.domain == humidifier.DOMAIN:
|
||||
requested_mode = settings["mode"]
|
||||
await self.hass.services.async_call(
|
||||
|
|
|
@ -41,6 +41,7 @@ BASE_PLATFORMS = {
|
|||
"notify",
|
||||
"remote",
|
||||
"scene",
|
||||
"select",
|
||||
"sensor",
|
||||
"switch",
|
||||
"tts",
|
||||
|
|
|
@ -18,6 +18,7 @@ from homeassistant.components import (
|
|||
media_player,
|
||||
scene,
|
||||
script,
|
||||
select,
|
||||
sensor,
|
||||
switch,
|
||||
vacuum,
|
||||
|
@ -1799,6 +1800,80 @@ async def test_modes_input_select(hass):
|
|||
assert calls[0].data == {"entity_id": "input_select.bla", "option": "xyz"}
|
||||
|
||||
|
||||
async def test_modes_select(hass):
|
||||
"""Test Select Mode trait."""
|
||||
assert helpers.get_google_type(select.DOMAIN, None) is not None
|
||||
assert trait.ModesTrait.supported(select.DOMAIN, None, None, None)
|
||||
|
||||
trt = trait.ModesTrait(
|
||||
hass,
|
||||
State("select.bla", "unavailable"),
|
||||
BASIC_CONFIG,
|
||||
)
|
||||
assert trt.sync_attributes() == {"availableModes": []}
|
||||
|
||||
trt = trait.ModesTrait(
|
||||
hass,
|
||||
State(
|
||||
"select.bla",
|
||||
"abc",
|
||||
attributes={select.ATTR_OPTIONS: ["abc", "123", "xyz"]},
|
||||
),
|
||||
BASIC_CONFIG,
|
||||
)
|
||||
|
||||
attribs = trt.sync_attributes()
|
||||
assert attribs == {
|
||||
"availableModes": [
|
||||
{
|
||||
"name": "option",
|
||||
"name_values": [
|
||||
{
|
||||
"name_synonym": ["option", "setting", "mode", "value"],
|
||||
"lang": "en",
|
||||
}
|
||||
],
|
||||
"settings": [
|
||||
{
|
||||
"setting_name": "abc",
|
||||
"setting_values": [{"setting_synonym": ["abc"], "lang": "en"}],
|
||||
},
|
||||
{
|
||||
"setting_name": "123",
|
||||
"setting_values": [{"setting_synonym": ["123"], "lang": "en"}],
|
||||
},
|
||||
{
|
||||
"setting_name": "xyz",
|
||||
"setting_values": [{"setting_synonym": ["xyz"], "lang": "en"}],
|
||||
},
|
||||
],
|
||||
"ordered": False,
|
||||
}
|
||||
]
|
||||
}
|
||||
|
||||
assert trt.query_attributes() == {
|
||||
"currentModeSettings": {"option": "abc"},
|
||||
"on": True,
|
||||
}
|
||||
|
||||
assert trt.can_execute(
|
||||
trait.COMMAND_MODES,
|
||||
params={"updateModeSettings": {"option": "xyz"}},
|
||||
)
|
||||
|
||||
calls = async_mock_service(hass, select.DOMAIN, select.SERVICE_SELECT_OPTION)
|
||||
await trt.execute(
|
||||
trait.COMMAND_MODES,
|
||||
BASIC_DATA,
|
||||
{"updateModeSettings": {"option": "xyz"}},
|
||||
{},
|
||||
)
|
||||
|
||||
assert len(calls) == 1
|
||||
assert calls[0].data == {"entity_id": "select.bla", "option": "xyz"}
|
||||
|
||||
|
||||
async def test_modes_humidifier(hass):
|
||||
"""Test Humidifier Mode trait."""
|
||||
assert helpers.get_google_type(humidifier.DOMAIN, None) is not None
|
||||
|
|
Loading…
Add table
Reference in a new issue