mirror of
https://github.com/home-assistant/core.git
synced 2025-07-22 20:57:21 +00:00
Add return value to conversation.process service (#94740)
* Add return value to conversation.process service * Adjust for new API
This commit is contained in:
parent
00075520c2
commit
3f10233833
@ -16,6 +16,7 @@ from homeassistant.components.http.data_validator import RequestDataValidator
|
|||||||
from homeassistant.config_entries import ConfigEntry
|
from homeassistant.config_entries import ConfigEntry
|
||||||
from homeassistant.const import MATCH_ALL
|
from homeassistant.const import MATCH_ALL
|
||||||
from homeassistant.core import HomeAssistant
|
from homeassistant.core import HomeAssistant
|
||||||
|
from homeassistant.exceptions import HomeAssistantError
|
||||||
from homeassistant.helpers import config_validation as cv, intent, singleton
|
from homeassistant.helpers import config_validation as cv, intent, singleton
|
||||||
from homeassistant.helpers.typing import ConfigType
|
from homeassistant.helpers.typing import ConfigType
|
||||||
from homeassistant.loader import bind_hass
|
from homeassistant.loader import bind_hass
|
||||||
@ -154,12 +155,12 @@ async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:
|
|||||||
if config_intents := config.get(DOMAIN, {}).get("intents"):
|
if config_intents := config.get(DOMAIN, {}).get("intents"):
|
||||||
hass.data[DATA_CONFIG] = config_intents
|
hass.data[DATA_CONFIG] = config_intents
|
||||||
|
|
||||||
async def handle_process(service: core.ServiceCall) -> None:
|
async def handle_process(service: core.ServiceCall) -> core.ServiceResponse:
|
||||||
"""Parse text into commands."""
|
"""Parse text into commands."""
|
||||||
text = service.data[ATTR_TEXT]
|
text = service.data[ATTR_TEXT]
|
||||||
_LOGGER.debug("Processing: <%s>", text)
|
_LOGGER.debug("Processing: <%s>", text)
|
||||||
try:
|
try:
|
||||||
await async_converse(
|
result = await async_converse(
|
||||||
hass=hass,
|
hass=hass,
|
||||||
text=text,
|
text=text,
|
||||||
conversation_id=None,
|
conversation_id=None,
|
||||||
@ -168,7 +169,12 @@ async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:
|
|||||||
agent_id=service.data.get(ATTR_AGENT_ID),
|
agent_id=service.data.get(ATTR_AGENT_ID),
|
||||||
)
|
)
|
||||||
except intent.IntentHandleError as err:
|
except intent.IntentHandleError as err:
|
||||||
_LOGGER.error("Error processing %s: %s", text, err)
|
raise HomeAssistantError(f"Error processing {text}: {err}") from err
|
||||||
|
|
||||||
|
if service.return_response:
|
||||||
|
return result.as_dict()
|
||||||
|
|
||||||
|
return None
|
||||||
|
|
||||||
async def handle_reload(service: core.ServiceCall) -> None:
|
async def handle_reload(service: core.ServiceCall) -> None:
|
||||||
"""Reload intents."""
|
"""Reload intents."""
|
||||||
@ -176,7 +182,11 @@ async def async_setup(hass: HomeAssistant, config: ConfigType) -> bool:
|
|||||||
await agent.async_reload(language=service.data.get(ATTR_LANGUAGE))
|
await agent.async_reload(language=service.data.get(ATTR_LANGUAGE))
|
||||||
|
|
||||||
hass.services.async_register(
|
hass.services.async_register(
|
||||||
DOMAIN, SERVICE_PROCESS, handle_process, schema=SERVICE_PROCESS_SCHEMA
|
DOMAIN,
|
||||||
|
SERVICE_PROCESS,
|
||||||
|
handle_process,
|
||||||
|
schema=SERVICE_PROCESS_SCHEMA,
|
||||||
|
supports_response=core.SupportsResponse.OPTIONAL,
|
||||||
)
|
)
|
||||||
hass.services.async_register(
|
hass.services.async_register(
|
||||||
DOMAIN, SERVICE_RELOAD, handle_reload, schema=SERVICE_RELOAD_SCHEMA
|
DOMAIN, SERVICE_RELOAD, handle_reload, schema=SERVICE_RELOAD_SCHEMA
|
||||||
|
@ -222,6 +222,126 @@
|
|||||||
]),
|
]),
|
||||||
})
|
})
|
||||||
# ---
|
# ---
|
||||||
|
# name: test_turn_on_intent[turn kitchen on-None]
|
||||||
|
dict({
|
||||||
|
'conversation_id': None,
|
||||||
|
'response': dict({
|
||||||
|
'card': dict({
|
||||||
|
}),
|
||||||
|
'data': dict({
|
||||||
|
'failed': list([
|
||||||
|
]),
|
||||||
|
'success': list([
|
||||||
|
dict({
|
||||||
|
'id': 'light.kitchen',
|
||||||
|
'name': 'kitchen',
|
||||||
|
'type': <IntentResponseTargetType.ENTITY: 'entity'>,
|
||||||
|
}),
|
||||||
|
]),
|
||||||
|
'targets': list([
|
||||||
|
]),
|
||||||
|
}),
|
||||||
|
'language': 'en',
|
||||||
|
'response_type': 'action_done',
|
||||||
|
'speech': dict({
|
||||||
|
'plain': dict({
|
||||||
|
'extra_data': None,
|
||||||
|
'speech': 'Turned on light',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
# ---
|
||||||
|
# name: test_turn_on_intent[turn kitchen on-homeassistant]
|
||||||
|
dict({
|
||||||
|
'conversation_id': None,
|
||||||
|
'response': dict({
|
||||||
|
'card': dict({
|
||||||
|
}),
|
||||||
|
'data': dict({
|
||||||
|
'failed': list([
|
||||||
|
]),
|
||||||
|
'success': list([
|
||||||
|
dict({
|
||||||
|
'id': 'light.kitchen',
|
||||||
|
'name': 'kitchen',
|
||||||
|
'type': <IntentResponseTargetType.ENTITY: 'entity'>,
|
||||||
|
}),
|
||||||
|
]),
|
||||||
|
'targets': list([
|
||||||
|
]),
|
||||||
|
}),
|
||||||
|
'language': 'en',
|
||||||
|
'response_type': 'action_done',
|
||||||
|
'speech': dict({
|
||||||
|
'plain': dict({
|
||||||
|
'extra_data': None,
|
||||||
|
'speech': 'Turned on light',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
# ---
|
||||||
|
# name: test_turn_on_intent[turn on kitchen-None]
|
||||||
|
dict({
|
||||||
|
'conversation_id': None,
|
||||||
|
'response': dict({
|
||||||
|
'card': dict({
|
||||||
|
}),
|
||||||
|
'data': dict({
|
||||||
|
'failed': list([
|
||||||
|
]),
|
||||||
|
'success': list([
|
||||||
|
dict({
|
||||||
|
'id': 'light.kitchen',
|
||||||
|
'name': 'kitchen',
|
||||||
|
'type': <IntentResponseTargetType.ENTITY: 'entity'>,
|
||||||
|
}),
|
||||||
|
]),
|
||||||
|
'targets': list([
|
||||||
|
]),
|
||||||
|
}),
|
||||||
|
'language': 'en',
|
||||||
|
'response_type': 'action_done',
|
||||||
|
'speech': dict({
|
||||||
|
'plain': dict({
|
||||||
|
'extra_data': None,
|
||||||
|
'speech': 'Turned on light',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
# ---
|
||||||
|
# name: test_turn_on_intent[turn on kitchen-homeassistant]
|
||||||
|
dict({
|
||||||
|
'conversation_id': None,
|
||||||
|
'response': dict({
|
||||||
|
'card': dict({
|
||||||
|
}),
|
||||||
|
'data': dict({
|
||||||
|
'failed': list([
|
||||||
|
]),
|
||||||
|
'success': list([
|
||||||
|
dict({
|
||||||
|
'id': 'light.kitchen',
|
||||||
|
'name': 'kitchen',
|
||||||
|
'type': <IntentResponseTargetType.ENTITY: 'entity'>,
|
||||||
|
}),
|
||||||
|
]),
|
||||||
|
'targets': list([
|
||||||
|
]),
|
||||||
|
}),
|
||||||
|
'language': 'en',
|
||||||
|
'response_type': 'action_done',
|
||||||
|
'speech': dict({
|
||||||
|
'plain': dict({
|
||||||
|
'extra_data': None,
|
||||||
|
'speech': 'Turned on light',
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
}),
|
||||||
|
})
|
||||||
|
# ---
|
||||||
# name: test_ws_get_agent_info
|
# name: test_ws_get_agent_info
|
||||||
dict({
|
dict({
|
||||||
'attribution': dict({
|
'attribution': dict({
|
||||||
|
@ -12,6 +12,7 @@ from homeassistant.components.cover import SERVICE_OPEN_COVER
|
|||||||
from homeassistant.components.light import DOMAIN as LIGHT_DOMAIN
|
from homeassistant.components.light import DOMAIN as LIGHT_DOMAIN
|
||||||
from homeassistant.const import ATTR_FRIENDLY_NAME
|
from homeassistant.const import ATTR_FRIENDLY_NAME
|
||||||
from homeassistant.core import Context, HomeAssistant
|
from homeassistant.core import Context, HomeAssistant
|
||||||
|
from homeassistant.exceptions import HomeAssistantError
|
||||||
from homeassistant.helpers import (
|
from homeassistant.helpers import (
|
||||||
area_registry as ar,
|
area_registry as ar,
|
||||||
device_registry as dr,
|
device_registry as dr,
|
||||||
@ -873,7 +874,7 @@ async def test_http_processing_intent_conversion_not_expose_new(
|
|||||||
@pytest.mark.parametrize("agent_id", AGENT_ID_OPTIONS)
|
@pytest.mark.parametrize("agent_id", AGENT_ID_OPTIONS)
|
||||||
@pytest.mark.parametrize("sentence", ("turn on kitchen", "turn kitchen on"))
|
@pytest.mark.parametrize("sentence", ("turn on kitchen", "turn kitchen on"))
|
||||||
async def test_turn_on_intent(
|
async def test_turn_on_intent(
|
||||||
hass: HomeAssistant, init_components, sentence, agent_id
|
hass: HomeAssistant, init_components, sentence, agent_id, snapshot
|
||||||
) -> None:
|
) -> None:
|
||||||
"""Test calling the turn on intent."""
|
"""Test calling the turn on intent."""
|
||||||
hass.states.async_set("light.kitchen", "off")
|
hass.states.async_set("light.kitchen", "off")
|
||||||
@ -882,8 +883,13 @@ async def test_turn_on_intent(
|
|||||||
data = {conversation.ATTR_TEXT: sentence}
|
data = {conversation.ATTR_TEXT: sentence}
|
||||||
if agent_id is not None:
|
if agent_id is not None:
|
||||||
data[conversation.ATTR_AGENT_ID] = agent_id
|
data[conversation.ATTR_AGENT_ID] = agent_id
|
||||||
await hass.services.async_call("conversation", "process", data)
|
result = await hass.services.async_call(
|
||||||
await hass.async_block_till_done()
|
"conversation",
|
||||||
|
"process",
|
||||||
|
data,
|
||||||
|
blocking=True,
|
||||||
|
return_response=True,
|
||||||
|
)
|
||||||
|
|
||||||
assert len(calls) == 1
|
assert len(calls) == 1
|
||||||
call = calls[0]
|
call = calls[0]
|
||||||
@ -891,6 +897,22 @@ async def test_turn_on_intent(
|
|||||||
assert call.service == "turn_on"
|
assert call.service == "turn_on"
|
||||||
assert call.data == {"entity_id": ["light.kitchen"]}
|
assert call.data == {"entity_id": ["light.kitchen"]}
|
||||||
|
|
||||||
|
assert result == snapshot
|
||||||
|
|
||||||
|
|
||||||
|
async def test_service_fails(hass: HomeAssistant, init_components) -> None:
|
||||||
|
"""Test calling the turn on intent."""
|
||||||
|
with pytest.raises(HomeAssistantError), patch(
|
||||||
|
"homeassistant.components.conversation.async_converse",
|
||||||
|
side_effect=intent.IntentHandleError,
|
||||||
|
):
|
||||||
|
await hass.services.async_call(
|
||||||
|
"conversation",
|
||||||
|
"process",
|
||||||
|
{"text": "bla"},
|
||||||
|
blocking=True,
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
@pytest.mark.parametrize("sentence", ("turn off kitchen", "turn kitchen off"))
|
@pytest.mark.parametrize("sentence", ("turn off kitchen", "turn kitchen off"))
|
||||||
async def test_turn_off_intent(hass: HomeAssistant, init_components, sentence) -> None:
|
async def test_turn_off_intent(hass: HomeAssistant, init_components, sentence) -> None:
|
||||||
|
Loading…
x
Reference in New Issue
Block a user