Fix search throwing on templated services (#79637)
parent
20c61af5b7
commit
146520b437
|
@ -227,6 +227,7 @@ CONF_SENSOR_TYPE: Final = "sensor_type"
|
|||
CONF_SEQUENCE: Final = "sequence"
|
||||
CONF_SERVICE: Final = "service"
|
||||
CONF_SERVICE_DATA: Final = "data"
|
||||
CONF_SERVICE_DATA_TEMPLATE: Final = "data_template"
|
||||
CONF_SERVICE_TEMPLATE: Final = "service_template"
|
||||
CONF_SHOW_ON_MAP: Final = "show_on_map"
|
||||
CONF_SLAVE: Final = "slave"
|
||||
|
|
|
@ -63,6 +63,8 @@ from homeassistant.const import (
|
|||
CONF_SCENE,
|
||||
CONF_SEQUENCE,
|
||||
CONF_SERVICE,
|
||||
CONF_SERVICE_DATA,
|
||||
CONF_SERVICE_DATA_TEMPLATE,
|
||||
CONF_SERVICE_TEMPLATE,
|
||||
CONF_STATE,
|
||||
CONF_STOP,
|
||||
|
@ -1119,8 +1121,10 @@ SERVICE_SCHEMA = vol.All(
|
|||
vol.Exclusive(CONF_SERVICE_TEMPLATE, "service name"): vol.Any(
|
||||
service, dynamic_template
|
||||
),
|
||||
vol.Optional("data"): vol.Any(template, vol.All(dict, template_complex)),
|
||||
vol.Optional("data_template"): vol.Any(
|
||||
vol.Optional(CONF_SERVICE_DATA): vol.Any(
|
||||
template, vol.All(dict, template_complex)
|
||||
),
|
||||
vol.Optional(CONF_SERVICE_DATA_TEMPLATE): vol.Any(
|
||||
template, vol.All(dict, template_complex)
|
||||
),
|
||||
vol.Optional(CONF_ENTITY_ID): comp_entity_ids,
|
||||
|
|
|
@ -50,6 +50,7 @@ from homeassistant.const import (
|
|||
CONF_SEQUENCE,
|
||||
CONF_SERVICE,
|
||||
CONF_SERVICE_DATA,
|
||||
CONF_SERVICE_DATA_TEMPLATE,
|
||||
CONF_STOP,
|
||||
CONF_TARGET,
|
||||
CONF_THEN,
|
||||
|
@ -1112,11 +1113,10 @@ async def _async_stop_scripts_at_shutdown(hass, event):
|
|||
_VarsType = Union[dict[str, Any], MappingProxyType]
|
||||
|
||||
|
||||
def _referenced_extract_ids(
|
||||
data: dict[str, Any] | None, key: str, found: set[str]
|
||||
) -> None:
|
||||
def _referenced_extract_ids(data: Any, key: str, found: set[str]) -> None:
|
||||
"""Extract referenced IDs."""
|
||||
if not data:
|
||||
# Data may not exist, or be a template
|
||||
if not isinstance(data, dict):
|
||||
return
|
||||
|
||||
item_ids = data.get(key)
|
||||
|
@ -1300,7 +1300,7 @@ class Script:
|
|||
for data in (
|
||||
step.get(CONF_TARGET),
|
||||
step.get(CONF_SERVICE_DATA),
|
||||
step.get(service.CONF_SERVICE_DATA_TEMPLATE),
|
||||
step.get(CONF_SERVICE_DATA_TEMPLATE),
|
||||
):
|
||||
_referenced_extract_ids(data, ATTR_AREA_ID, referenced)
|
||||
|
||||
|
@ -1340,7 +1340,7 @@ class Script:
|
|||
for data in (
|
||||
step.get(CONF_TARGET),
|
||||
step.get(CONF_SERVICE_DATA),
|
||||
step.get(service.CONF_SERVICE_DATA_TEMPLATE),
|
||||
step.get(CONF_SERVICE_DATA_TEMPLATE),
|
||||
):
|
||||
_referenced_extract_ids(data, ATTR_DEVICE_ID, referenced)
|
||||
|
||||
|
@ -1391,7 +1391,7 @@ class Script:
|
|||
step,
|
||||
step.get(CONF_TARGET),
|
||||
step.get(CONF_SERVICE_DATA),
|
||||
step.get(service.CONF_SERVICE_DATA_TEMPLATE),
|
||||
step.get(CONF_SERVICE_DATA_TEMPLATE),
|
||||
):
|
||||
_referenced_extract_ids(data, ATTR_ENTITY_ID, referenced)
|
||||
|
||||
|
|
|
@ -19,6 +19,7 @@ from homeassistant.const import (
|
|||
CONF_ENTITY_ID,
|
||||
CONF_SERVICE,
|
||||
CONF_SERVICE_DATA,
|
||||
CONF_SERVICE_DATA_TEMPLATE,
|
||||
CONF_SERVICE_TEMPLATE,
|
||||
CONF_TARGET,
|
||||
ENTITY_MATCH_ALL,
|
||||
|
@ -52,7 +53,6 @@ if TYPE_CHECKING:
|
|||
|
||||
|
||||
CONF_SERVICE_ENTITY_ID = "entity_id"
|
||||
CONF_SERVICE_DATA_TEMPLATE = "data_template"
|
||||
|
||||
_LOGGER = logging.getLogger(__name__)
|
||||
|
||||
|
|
|
@ -183,6 +183,22 @@ async def test_search(hass):
|
|||
},
|
||||
]
|
||||
},
|
||||
"script_with_templated_services": {
|
||||
"sequence": [
|
||||
{
|
||||
"service": "test.script",
|
||||
"target": "{{ {'entity_id':'test.test1'} }}",
|
||||
},
|
||||
{
|
||||
"service": "test.script",
|
||||
"data": "{{ {'entity_id':'test.test2'} }}",
|
||||
},
|
||||
{
|
||||
"service": "test.script",
|
||||
"data_template": "{{ {'entity_id':'test.test3'} }}",
|
||||
},
|
||||
]
|
||||
},
|
||||
}
|
||||
},
|
||||
)
|
||||
|
@ -304,6 +320,18 @@ async def test_search(hass):
|
|||
searcher = search.Searcher(hass, device_reg, entity_reg, entity_sources)
|
||||
assert searcher.async_search(search_type, search_id) == {}
|
||||
|
||||
# Test search of templated script. We can't find referenced areas, devices or
|
||||
# entities within templated services, but searching them should not raise or
|
||||
# otherwise fail.
|
||||
assert hass.states.get("script.script_with_templated_services")
|
||||
for search_type, search_id in (
|
||||
("area", "script.script_with_templated_services"),
|
||||
("device", "script.script_with_templated_services"),
|
||||
("entity", "script.script_with_templated_services"),
|
||||
):
|
||||
searcher = search.Searcher(hass, device_reg, entity_reg, entity_sources)
|
||||
assert searcher.async_search(search_type, search_id) == {}
|
||||
|
||||
searcher = search.Searcher(hass, device_reg, entity_reg, entity_sources)
|
||||
assert searcher.async_search("entity", "light.wled_config_entry_source") == {
|
||||
"config_entry": {wled_config_entry.entry_id},
|
||||
|
|
Loading…
Reference in New Issue