Update service call return values and error handling (#94657)

* Update return signature of service calls

* Add timeout error handling in websocket api for service calls

* Update recorder tests to remove assertion on service call

* Remove timeout behavior and update callers that depend on it today

* Fix tests

* Add missing else

* await coro directly

* Fix more tests

* Update the intent task to use wait instead of timeout

* Remove script service call limits and limit constants

* Update tests that depend on service call limits

* Use wait instead of wait_for and add test

* Update homeassistant/helpers/intent.py

Co-authored-by: Martin Hjelmare <marhje52@gmail.com>

---------

Co-authored-by: Paulus Schoutsen <balloob@gmail.com>
Co-authored-by: Martin Hjelmare <marhje52@gmail.com>
This commit is contained in:
Allen Porter 2023-06-16 07:01:40 -07:00 committed by GitHub
parent 950b25bf42
commit 12129e9d21
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
63 changed files with 388 additions and 434 deletions

View file

@ -70,7 +70,9 @@ class OnOffIntentHandler(intent.ServiceIntentHandler):
if state.domain == COVER_DOMAIN:
# on = open
# off = close
await hass.services.async_call(
await self._run_then_background(
hass.async_create_task(
hass.services.async_call(
COVER_DOMAIN,
SERVICE_OPEN_COVER
if self.service == SERVICE_TURN_ON
@ -78,10 +80,12 @@ class OnOffIntentHandler(intent.ServiceIntentHandler):
{ATTR_ENTITY_ID: state.entity_id},
context=intent_obj.context,
blocking=True,
limit=self.service_timeout,
)
)
)
return
elif not hass.services.has_service(state.domain, self.service):
if not hass.services.has_service(state.domain, self.service):
raise intent.IntentHandleError(
f"Service {self.service} does not support entity {state.entity_id}"
)

View file

@ -130,9 +130,6 @@ DOMAIN = "homeassistant"
# How long to wait to log tasks that are blocking
BLOCK_LOG_TIMEOUT = 60
# How long we wait for the result of a service call
SERVICE_CALL_LIMIT = 10 # seconds
class ConfigSource(StrEnum):
"""Source of core configuration."""
@ -1807,7 +1804,6 @@ class ServiceRegistry:
service_data: dict[str, Any] | None = None,
blocking: bool = False,
context: Context | None = None,
limit: float | None = SERVICE_CALL_LIMIT,
target: dict[str, Any] | None = None,
) -> bool | None:
"""Call a service.
@ -1815,9 +1811,7 @@ class ServiceRegistry:
See description of async_call for details.
"""
return asyncio.run_coroutine_threadsafe(
self.async_call(
domain, service, service_data, blocking, context, limit, target
),
self.async_call(domain, service, service_data, blocking, context, target),
self._hass.loop,
).result()
@ -1828,16 +1822,11 @@ class ServiceRegistry:
service_data: dict[str, Any] | None = None,
blocking: bool = False,
context: Context | None = None,
limit: float | None = SERVICE_CALL_LIMIT,
target: dict[str, Any] | None = None,
) -> bool | None:
) -> None:
"""Call a service.
Specify blocking=True to wait until service is executed.
Waits a maximum of limit, which may be None for no timeout.
If blocking = True, will return boolean if service executed
successfully within limit.
This method will fire an event to indicate the service has been called.
@ -1888,33 +1877,9 @@ class ServiceRegistry:
coro = self._execute_service(handler, service_call)
if not blocking:
self._run_service_in_background(coro, service_call)
return None
return
task = self._hass.async_create_task(coro)
try:
await asyncio.wait({task}, timeout=limit)
except asyncio.CancelledError:
# Task calling us was cancelled, so cancel service call task, and wait for
# it to be cancelled, within reason, before leaving.
_LOGGER.debug("Service call was cancelled: %s", service_call)
task.cancel()
await asyncio.wait({task}, timeout=SERVICE_CALL_LIMIT)
raise
if task.cancelled():
# Service call task was cancelled some other way, such as during shutdown.
_LOGGER.debug("Service was cancelled: %s", service_call)
raise asyncio.CancelledError
if task.done():
# Propagate any exceptions that might have happened during service call.
task.result()
# Service call completed successfully!
return True
# Service call task did not complete before timeout expired.
# Let it keep running in background.
self._run_service_in_background(task, service_call)
_LOGGER.debug("Service did not complete before timeout: %s", service_call)
return False
await coro
def _run_service_in_background(
self,

View file

@ -493,14 +493,35 @@ class ServiceIntentHandler(IntentHandler):
async def async_call_service(self, intent_obj: Intent, state: State) -> None:
"""Call service on entity."""
hass = intent_obj.hass
await hass.services.async_call(
await self._run_then_background(
hass.async_create_task(
hass.services.async_call(
self.domain,
self.service,
{ATTR_ENTITY_ID: state.entity_id},
context=intent_obj.context,
blocking=True,
limit=self.service_timeout,
),
f"intent_call_service_{self.domain}_{self.service}",
)
)
async def _run_then_background(self, task: asyncio.Task) -> None:
"""Run task with timeout to (hopefully) catch validation errors.
After the timeout the task will continue to run in the background.
"""
try:
await asyncio.wait({task}, timeout=self.service_timeout)
except asyncio.TimeoutError:
pass
except asyncio.CancelledError:
# Task calling us was cancelled, so cancel service call task, and wait for
# it to be cancelled, within reason, before leaving.
_LOGGER.debug("Service call was cancelled: %s", task.get_name())
task.cancel()
await asyncio.wait({task}, timeout=5)
raise
class IntentCategory(Enum):

View file

@ -64,7 +64,6 @@ from homeassistant.const import (
SERVICE_TURN_ON,
)
from homeassistant.core import (
SERVICE_CALL_LIMIT,
Context,
Event,
HassJob,
@ -664,28 +663,16 @@ class _ScriptRun:
and params[CONF_SERVICE] == "trigger"
or params[CONF_DOMAIN] in ("python_script", "script")
)
# If this might start a script then disable the call timeout.
# Otherwise use the normal service call limit.
if running_script:
limit = None
else:
limit = SERVICE_CALL_LIMIT
trace_set_result(params=params, running_script=running_script, limit=limit)
service_task = self._hass.async_create_task(
trace_set_result(params=params, running_script=running_script)
await self._async_run_long_action(
self._hass.async_create_task(
self._hass.services.async_call(
**params,
blocking=True,
context=self._context,
limit=limit,
)
)
if limit is not None:
# There is a call limit, so just wait for it to finish.
await service_task
return
await self._async_run_long_action(service_task)
)
async def _async_device_step(self):
"""Perform the device automation specified in the action."""

View file

@ -1353,7 +1353,7 @@ def async_capture_events(hass: HomeAssistant, event_name: str) -> list[Event]:
def capture_events(event: Event) -> None:
events.append(event)
hass.bus.async_listen(event_name, capture_events)
hass.bus.async_listen(event_name, capture_events, run_immediately=True)
return events

View file

@ -63,7 +63,7 @@ async def test_switch_off(hass: HomeAssistant) -> None:
await setup_platform(hass, LIGHT_DOMAIN)
with patch("jaraco.abode.devices.light.Light.switch_off") as mock_switch_off:
assert await hass.services.async_call(
await hass.services.async_call(
LIGHT_DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: DEVICE_ID}, blocking=True
)
await hass.async_block_till_done()

View file

@ -49,7 +49,7 @@ async def test_switch_on(hass: HomeAssistant) -> None:
await setup_platform(hass, SWITCH_DOMAIN)
with patch("jaraco.abode.devices.switch.Switch.switch_on") as mock_switch_on:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN, SERVICE_TURN_ON, {ATTR_ENTITY_ID: DEVICE_ID}, blocking=True
)
await hass.async_block_till_done()
@ -62,7 +62,7 @@ async def test_switch_off(hass: HomeAssistant) -> None:
await setup_platform(hass, SWITCH_DOMAIN)
with patch("jaraco.abode.devices.switch.Switch.switch_off") as mock_switch_off:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: DEVICE_ID}, blocking=True
)
await hass.async_block_till_done()

View file

@ -1,4 +1,5 @@
"""Tests for the Android TV Remote remote platform."""
import asyncio
from unittest.mock import MagicMock, call
from androidtvremote2 import ConnectionClosed
@ -66,7 +67,7 @@ async def test_media_player_toggles(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"turn_off",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -76,7 +77,7 @@ async def test_media_player_toggles(
mock_api.send_key_command.assert_called_with("POWER", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"turn_on",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -95,7 +96,7 @@ async def test_media_player_volume(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"volume_up",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -105,7 +106,7 @@ async def test_media_player_volume(
mock_api.send_key_command.assert_called_with("VOLUME_UP", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"volume_down",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -115,7 +116,7 @@ async def test_media_player_volume(
mock_api.send_key_command.assert_called_with("VOLUME_DOWN", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"volume_mute",
{"entity_id": MEDIA_PLAYER_ENTITY, "is_volume_muted": True},
@ -125,7 +126,7 @@ async def test_media_player_volume(
mock_api.send_key_command.assert_called_with("VOLUME_MUTE", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"volume_mute",
{"entity_id": MEDIA_PLAYER_ENTITY, "is_volume_muted": False},
@ -144,7 +145,7 @@ async def test_media_player_controls(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_play",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -153,7 +154,7 @@ async def test_media_player_controls(
mock_api.send_key_command.assert_called_with("MEDIA_PLAY", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_pause",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -162,7 +163,7 @@ async def test_media_player_controls(
mock_api.send_key_command.assert_called_with("MEDIA_PAUSE", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_play_pause",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -171,7 +172,7 @@ async def test_media_player_controls(
mock_api.send_key_command.assert_called_with("MEDIA_PLAY_PAUSE", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_stop",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -180,7 +181,7 @@ async def test_media_player_controls(
mock_api.send_key_command.assert_called_with("MEDIA_STOP", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_previous_track",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -189,7 +190,7 @@ async def test_media_player_controls(
mock_api.send_key_command.assert_called_with("MEDIA_PREVIOUS", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"media_next_track",
{"entity_id": MEDIA_PLAYER_ENTITY},
@ -207,7 +208,7 @@ async def test_media_player_play_media(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"play_media",
{
@ -234,6 +235,10 @@ async def test_media_player_play_media(
},
blocking=False,
)
# Give background task time to run
await asyncio.sleep(0)
await hass.services.async_call(
"media_player",
"play_media",
@ -246,7 +251,7 @@ async def test_media_player_play_media(
)
assert mock_api.send_key_command.call_count == 2
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"play_media",
{
@ -259,7 +264,7 @@ async def test_media_player_play_media(
mock_api.send_launch_app_command.assert_called_with("https://www.youtube.com")
with pytest.raises(ValueError):
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"play_media",
{
@ -271,7 +276,7 @@ async def test_media_player_play_media(
)
with pytest.raises(ValueError):
assert await hass.services.async_call(
await hass.services.async_call(
"media_player",
"play_media",
{

View file

@ -48,7 +48,7 @@ async def test_remote_toggles(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"turn_off",
{"entity_id": REMOTE_ENTITY},
@ -58,7 +58,7 @@ async def test_remote_toggles(
mock_api.send_key_command.assert_called_with("POWER", "SHORT")
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"turn_on",
{"entity_id": REMOTE_ENTITY},
@ -69,7 +69,7 @@ async def test_remote_toggles(
mock_api.send_key_command.assert_called_with("POWER", "SHORT")
assert mock_api.send_key_command.call_count == 2
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"turn_on",
{"entity_id": REMOTE_ENTITY, "activity": "activity1"},
@ -89,7 +89,7 @@ async def test_remote_send_command(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"send_command",
{
@ -112,7 +112,7 @@ async def test_remote_send_command_multiple(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"send_command",
{
@ -136,7 +136,7 @@ async def test_remote_send_command_with_hold_secs(
await hass.config_entries.async_setup(mock_config_entry.entry_id)
assert mock_config_entry.state is ConfigEntryState.LOADED
assert await hass.services.async_call(
await hass.services.async_call(
"remote",
"send_command",
{

View file

@ -46,9 +46,7 @@ async def test_doorsense(hass: HomeAssistant) -> None:
assert binary_sensor_online_with_doorsense_name.state == STATE_ON
data = {ATTR_ENTITY_ID: "lock.online_with_doorsense_name"}
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True)
await hass.async_block_till_done()
binary_sensor_online_with_doorsense_name = hass.states.get(
@ -56,9 +54,7 @@ async def test_doorsense(hass: HomeAssistant) -> None:
)
assert binary_sensor_online_with_doorsense_name.state == STATE_ON
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True)
await hass.async_block_till_done()
binary_sensor_online_with_doorsense_name = hass.states.get(

View file

@ -16,7 +16,7 @@ async def test_wake_lock(hass: HomeAssistant) -> None:
binary_sensor_online_with_doorsense_name = hass.states.get(entity_id)
assert binary_sensor_online_with_doorsense_name is not None
api_instance.async_status_async.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
BUTTON_DOMAIN, SERVICE_PRESS, {ATTR_ENTITY_ID: entity_id}, blocking=True
)
await hass.async_block_till_done()

View file

@ -122,9 +122,7 @@ async def test_one_lock_operation(hass: HomeAssistant) -> None:
)
data = {ATTR_ENTITY_ID: "lock.online_with_doorsense_name"}
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True)
await hass.async_block_till_done()
lock_online_with_doorsense_name = hass.states.get("lock.online_with_doorsense_name")
@ -136,9 +134,7 @@ async def test_one_lock_operation(hass: HomeAssistant) -> None:
== "online_with_doorsense Name"
)
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True)
await hass.async_block_till_done()
lock_online_with_doorsense_name = hass.states.get("lock.online_with_doorsense_name")
@ -176,9 +172,7 @@ async def test_one_lock_operation_pubnub_connected(hass: HomeAssistant) -> None:
)
data = {ATTR_ENTITY_ID: "lock.online_with_doorsense_name"}
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True)
await hass.async_block_till_done()
pubnub.message(
@ -203,9 +197,7 @@ async def test_one_lock_operation_pubnub_connected(hass: HomeAssistant) -> None:
== "online_with_doorsense Name"
)
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_LOCK, data, blocking=True)
await hass.async_block_till_done()
pubnub.message(
@ -262,9 +254,7 @@ async def test_lock_jammed(hass: HomeAssistant) -> None:
)
data = {ATTR_ENTITY_ID: "lock.online_with_doorsense_name"}
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True)
await hass.async_block_till_done()
lock_online_with_doorsense_name = hass.states.get("lock.online_with_doorsense_name")
@ -300,9 +290,7 @@ async def test_lock_throws_exception_on_unknown_status_code(
data = {ATTR_ENTITY_ID: "lock.online_with_doorsense_name"}
with pytest.raises(ClientResponseError):
assert await hass.services.async_call(
LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True
)
await hass.services.async_call(LOCK_DOMAIN, SERVICE_UNLOCK, data, blocking=True)
await hass.async_block_till_done()

View file

@ -1011,6 +1011,7 @@ async def test_debug_logging(
{"homeassistant.components.bluetooth": "DEBUG"},
blocking=True,
)
await hass.async_block_till_done()
address = "44:44:33:11:23:41"
start_time_monotonic = 50.0

View file

@ -139,9 +139,7 @@ async def _async_load_color_extractor_url(hass, service_data):
assert state.state == STATE_OFF
# Call the shared service, our above mock should return the base64 decoded fixture 1x1 pixel
assert await hass.services.async_call(
DOMAIN, SERVICE_TURN_ON, service_data, blocking=True
)
await hass.services.async_call(DOMAIN, SERVICE_TURN_ON, service_data, blocking=True)
await hass.async_block_till_done()

View file

@ -94,7 +94,7 @@ async def test_command_line_output(hass: HomeAssistant) -> None:
assert hass.services.has_service(NOTIFY_DOMAIN, "test3")
assert await hass.services.async_call(
await hass.services.async_call(
NOTIFY_DOMAIN, "test3", {"message": message}, blocking=True
)
with open(filename, encoding="UTF-8") as handle:
@ -122,7 +122,7 @@ async def test_error_for_none_zero_exit_code(
) -> None:
"""Test if an error is logged for non zero exit codes."""
assert await hass.services.async_call(
await hass.services.async_call(
NOTIFY_DOMAIN, "test4", {"message": "error"}, blocking=True
)
assert "Command failed" in caplog.text
@ -149,7 +149,7 @@ async def test_timeout(
caplog: pytest.LogCaptureFixture, hass: HomeAssistant, load_yaml_integration: None
) -> None:
"""Test blocking is not forever."""
assert await hass.services.async_call(
await hass.services.async_call(
NOTIFY_DOMAIN, "test5", {"message": "error"}, blocking=True
)
assert "Timeout" in caplog.text
@ -185,13 +185,13 @@ async def test_subprocess_exceptions(
subprocess.SubprocessError(),
]
assert await hass.services.async_call(
await hass.services.async_call(
NOTIFY_DOMAIN, "test6", {"message": "error"}, blocking=True
)
assert check_output.call_count == 2
assert "Timeout for command" in caplog.text
assert await hass.services.async_call(
await hass.services.async_call(
NOTIFY_DOMAIN, "test6", {"message": "error"}, blocking=True
)
assert check_output.call_count == 4

View file

@ -305,6 +305,7 @@ async def test_addressable_light_pixel_config(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: pixels_per_segment_entity_id, ATTR_VALUE: 100},
blocking=True,
)
await hass.async_block_till_done()
bulb.async_set_device_config.assert_called_with(pixels_per_segment=100)
bulb.async_set_device_config.reset_mock()
@ -322,6 +323,7 @@ async def test_addressable_light_pixel_config(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: music_pixels_per_segment_entity_id, ATTR_VALUE: 100},
blocking=True,
)
await hass.async_block_till_done()
bulb.async_set_device_config.assert_called_with(music_pixels_per_segment=100)
bulb.async_set_device_config.reset_mock()
@ -339,6 +341,7 @@ async def test_addressable_light_pixel_config(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: segments_entity_id, ATTR_VALUE: 5},
blocking=True,
)
await hass.async_block_till_done()
bulb.async_set_device_config.assert_called_with(segments=5)
bulb.async_set_device_config.reset_mock()
@ -356,6 +359,7 @@ async def test_addressable_light_pixel_config(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: music_segments_entity_id, ATTR_VALUE: 5},
blocking=True,
)
await hass.async_block_till_done()
bulb.async_set_device_config.assert_called_with(music_segments=5)
bulb.async_set_device_config.reset_mock()

View file

@ -101,7 +101,7 @@ async def test_climate_set_off(hass: HomeAssistant, init_integration) -> None:
with patch(
"homeassistant.components.freedompro.climate.put_state"
) as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
CLIMATE_DOMAIN,
SERVICE_SET_HVAC_MODE,
{ATTR_ENTITY_ID: [entity_id], ATTR_HVAC_MODE: HVACMode.OFF},
@ -156,7 +156,7 @@ async def test_climate_set_temperature(hass: HomeAssistant, init_integration) ->
with patch(
"homeassistant.components.freedompro.climate.put_state"
) as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
CLIMATE_DOMAIN,
SERVICE_SET_TEMPERATURE,
{
@ -200,7 +200,7 @@ async def test_climate_set_temperature_unsupported_hvac_mode(
assert entry
assert entry.unique_id == uid
assert await hass.services.async_call(
await hass.services.async_call(
CLIMATE_DOMAIN,
SERVICE_SET_TEMPERATURE,
{

View file

@ -116,7 +116,7 @@ async def test_cover_set_position(
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.cover.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
COVER_DOMAIN,
SERVICE_SET_COVER_POSITION,
{ATTR_ENTITY_ID: [entity_id], ATTR_POSITION: 33},
@ -181,7 +181,7 @@ async def test_cover_close(
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.cover.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
COVER_DOMAIN,
SERVICE_CLOSE_COVER,
{ATTR_ENTITY_ID: [entity_id]},
@ -234,7 +234,7 @@ async def test_cover_open(
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.cover.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
COVER_DOMAIN,
SERVICE_OPEN_COVER,
{ATTR_ENTITY_ID: [entity_id]},

View file

@ -96,7 +96,7 @@ async def test_fan_set_off(hass: HomeAssistant, init_integration) -> None:
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.fan.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
FAN_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: [entity_id]},
@ -137,7 +137,7 @@ async def test_fan_set_on(hass: HomeAssistant, init_integration) -> None:
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.fan.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
FAN_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: [entity_id]},
@ -177,7 +177,7 @@ async def test_fan_set_percent(hass: HomeAssistant, init_integration) -> None:
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.fan.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
FAN_DOMAIN,
SERVICE_SET_PERCENTAGE,
{ATTR_ENTITY_ID: [entity_id], ATTR_PERCENTAGE: 40},

View file

@ -90,7 +90,7 @@ async def test_lock_set_unlock(hass: HomeAssistant, init_integration) -> None:
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.lock.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
LOCK_DOMAIN,
SERVICE_UNLOCK,
{ATTR_ENTITY_ID: [entity_id]},
@ -127,7 +127,7 @@ async def test_lock_set_lock(hass: HomeAssistant, init_integration) -> None:
assert entry.unique_id == uid
with patch("homeassistant.components.freedompro.lock.put_state") as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
LOCK_DOMAIN,
SERVICE_LOCK,
{ATTR_ENTITY_ID: [entity_id]},

View file

@ -80,7 +80,7 @@ async def test_switch_set_off(hass: HomeAssistant, init_integration) -> None:
with patch(
"homeassistant.components.freedompro.switch.put_state"
) as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: [entity_id]},
@ -119,7 +119,7 @@ async def test_switch_set_on(hass: HomeAssistant, init_integration) -> None:
with patch(
"homeassistant.components.freedompro.switch.put_state"
) as mock_put_state:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: [entity_id]},

View file

@ -113,7 +113,7 @@ async def test_available_update_can_be_installed(
assert update is not None
assert update.state == "on"
assert await hass.services.async_call(
await hass.services.async_call(
"update",
"install",
{"entity_id": "update.mock_title_fritz_os"},

View file

@ -37,7 +37,7 @@ async def test_apply_template(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], fritz=fritz, template=template
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_PRESS, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert fritz().apply_template.call_count == 1

View file

@ -255,7 +255,7 @@ async def test_set_temperature_temperature(hass: HomeAssistant, fritz: Mock) ->
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_TEMPERATURE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_TEMPERATURE: 123},
@ -271,7 +271,7 @@ async def test_set_temperature_mode_off(hass: HomeAssistant, fritz: Mock) -> Non
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_TEMPERATURE,
{
@ -291,7 +291,7 @@ async def test_set_temperature_mode_heat(hass: HomeAssistant, fritz: Mock) -> No
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_TEMPERATURE,
{
@ -311,7 +311,7 @@ async def test_set_hvac_mode_off(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_HVAC_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_HVAC_MODE: HVACMode.OFF},
@ -327,7 +327,7 @@ async def test_set_hvac_mode_heat(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_HVAC_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_HVAC_MODE: HVACMode.HEAT},
@ -343,7 +343,7 @@ async def test_set_preset_mode_comfort(hass: HomeAssistant, fritz: Mock) -> None
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_PRESET_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_PRESET_MODE: PRESET_COMFORT},
@ -359,7 +359,7 @@ async def test_set_preset_mode_eco(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_PRESET_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_PRESET_MODE: PRESET_ECO},

View file

@ -38,7 +38,7 @@ async def test_open_cover(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_OPEN_COVER, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_blind_open.call_count == 1
@ -51,7 +51,7 @@ async def test_close_cover(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_CLOSE_COVER, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_blind_close.call_count == 1
@ -64,7 +64,7 @@ async def test_set_position_cover(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_COVER_POSITION,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_POSITION: 50},
@ -80,7 +80,7 @@ async def test_stop_cover(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_STOP_COVER, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_blind_stop.call_count == 1

View file

@ -135,7 +135,7 @@ async def test_turn_on(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_BRIGHTNESS: 100, ATTR_COLOR_TEMP_KELVIN: 3000},
@ -158,7 +158,7 @@ async def test_turn_on_color(hass: HomeAssistant, fritz: Mock) -> None:
assert await setup_config_entry(
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_BRIGHTNESS: 100, ATTR_HS_COLOR: (100, 70)},
@ -192,7 +192,7 @@ async def test_turn_on_color_unsupported_api_method(
assert await setup_config_entry(
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_BRIGHTNESS: 100, ATTR_HS_COLOR: (100, 70)},
@ -215,7 +215,7 @@ async def test_turn_off(hass: HomeAssistant, fritz: Mock) -> None:
assert await setup_config_entry(
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_state_off.call_count == 1

View file

@ -107,7 +107,7 @@ async def test_turn_on(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_ON, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_switch_state_on.call_count == 1
@ -120,7 +120,7 @@ async def test_turn_off(hass: HomeAssistant, fritz: Mock) -> None:
hass, MOCK_CONFIG[FB_DOMAIN][CONF_DEVICES][0], ENTITY_ID, device, fritz
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert device.set_switch_state_off.call_count == 1

View file

@ -22,7 +22,7 @@ async def test_buttons(
entry = entity_registry.async_get("button.amazon_fire_restart_browser")
assert entry
assert entry.unique_id == "abcdef-123456-restartApp"
assert await hass.services.async_call(
await hass.services.async_call(
button.DOMAIN,
button.SERVICE_PRESS,
{ATTR_ENTITY_ID: "button.amazon_fire_restart_browser"},
@ -33,7 +33,7 @@ async def test_buttons(
entry = entity_registry.async_get("button.amazon_fire_reboot_device")
assert entry
assert entry.unique_id == "abcdef-123456-rebootDevice"
assert await hass.services.async_call(
await hass.services.async_call(
button.DOMAIN,
button.SERVICE_PRESS,
{ATTR_ENTITY_ID: "button.amazon_fire_reboot_device"},
@ -44,7 +44,7 @@ async def test_buttons(
entry = entity_registry.async_get("button.amazon_fire_bring_to_foreground")
assert entry
assert entry.unique_id == "abcdef-123456-toForeground"
assert await hass.services.async_call(
await hass.services.async_call(
button.DOMAIN,
button.SERVICE_PRESS,
{ATTR_ENTITY_ID: "button.amazon_fire_bring_to_foreground"},
@ -55,7 +55,7 @@ async def test_buttons(
entry = entity_registry.async_get("button.amazon_fire_send_to_background")
assert entry
assert entry.unique_id == "abcdef-123456-toBackground"
assert await hass.services.async_call(
await hass.services.async_call(
button.DOMAIN,
button.SERVICE_PRESS,
{ATTR_ENTITY_ID: "button.amazon_fire_send_to_background"},
@ -66,7 +66,7 @@ async def test_buttons(
entry = entity_registry.async_get("button.amazon_fire_load_start_url")
assert entry
assert entry.unique_id == "abcdef-123456-loadStartUrl"
assert await hass.services.async_call(
await hass.services.async_call(
button.DOMAIN,
button.SERVICE_PRESS,
{ATTR_ENTITY_ID: "button.amazon_fire_load_start_url"},

View file

@ -131,6 +131,7 @@ async def test_heater_input_boolean(hass: HomeAssistant, setup_comp_1) -> None:
_setup_sensor(hass, 18)
await hass.async_block_till_done()
await common.async_set_temperature(hass, 23)
await hass.async_block_till_done()
assert hass.states.get(heater_switch).state == STATE_ON

View file

@ -744,6 +744,7 @@ async def test_execute_times_out(
turn_on_wait.set()
await hass.async_block_till_done()
await hass.async_block_till_done()
# The remaining two calls should now have executed
assert call_service_mock.call_count == 4
expected_calls.extend(

View file

@ -230,6 +230,7 @@ async def test_send_text_command_expired_token_refresh_failure(
{"command": "turn on tv"},
blocking=True,
)
await hass.async_block_till_done()
assert any(entry.async_get_active_flows(hass, {"reauth"})) == requires_reauth

View file

@ -81,6 +81,9 @@ async def test_reauth_trigger(
blocking=True,
)
await hass.async_block_till_done()
await hass.async_block_till_done()
flows = hass.config_entries.flow.async_progress()
assert len(flows) == 1

View file

@ -326,7 +326,7 @@ async def test_send_command_device_timeout(
device().push_state_update.side_effect = DeviceTimeoutError
# Send failure should not raise exceptions or change device state
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: ENTITY_ID},
@ -342,7 +342,7 @@ async def test_send_power_on(hass: HomeAssistant, discovery, device, mock_now) -
"""Test for sending power on command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: ENTITY_ID},
@ -362,7 +362,7 @@ async def test_send_power_off_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: ENTITY_ID},
@ -393,7 +393,7 @@ async def test_send_target_temperature(
# Make sure we're trying to test something that isn't the default
assert fake_device.current_temperature != temperature
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_TEMPERATURE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_TEMPERATURE: temperature},
@ -428,7 +428,7 @@ async def test_send_target_temperature_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_TEMPERATURE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_TEMPERATURE: temperature},
@ -475,7 +475,7 @@ async def test_send_preset_mode(
"""Test for sending preset mode command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_PRESET_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_PRESET_MODE: preset},
@ -517,7 +517,7 @@ async def test_send_preset_mode_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_PRESET_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_PRESET_MODE: preset},
@ -565,7 +565,7 @@ async def test_send_hvac_mode(
"""Test for sending hvac mode command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_HVAC_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_HVAC_MODE: hvac_mode},
@ -589,7 +589,7 @@ async def test_send_hvac_mode_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_HVAC_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_HVAC_MODE: hvac_mode},
@ -636,7 +636,7 @@ async def test_send_fan_mode(
"""Test for sending fan mode command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_FAN_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_FAN_MODE: fan_mode},
@ -679,7 +679,7 @@ async def test_send_fan_mode_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_FAN_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_FAN_MODE: fan_mode},
@ -717,7 +717,7 @@ async def test_send_swing_mode(
"""Test for sending swing mode command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_SWING_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_SWING_MODE: swing_mode},
@ -759,7 +759,7 @@ async def test_send_swing_mode_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SET_SWING_MODE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_SWING_MODE: swing_mode},

View file

@ -66,7 +66,7 @@ async def test_send_switch_on(
"""Test for sending power on command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: entity},
@ -96,7 +96,7 @@ async def test_send_switch_on_device_timeout(
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: entity},
@ -124,7 +124,7 @@ async def test_send_switch_off(
"""Test for sending power on command to the device."""
await async_setup_gree(hass)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: entity},
@ -153,7 +153,7 @@ async def test_send_switch_toggle(
await async_setup_gree(hass)
# Turn the service on first
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: entity},
@ -165,7 +165,7 @@ async def test_send_switch_toggle(
assert state.state == STATE_ON
# Toggle it off
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TOGGLE,
{ATTR_ENTITY_ID: entity},
@ -177,7 +177,7 @@ async def test_send_switch_toggle(
assert state.state == STATE_OFF
# Toggle is back on
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_TOGGLE,
{ATTR_ENTITY_ID: entity},

View file

@ -123,7 +123,7 @@ async def test_service_call(
ATTR_PATH: ["tasks", "user", "post"],
ATTR_ARGS: TEST_API_CALL_ARGS,
}
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_API_CALL, TEST_SERVICE_DATA, blocking=True
)

View file

@ -247,7 +247,7 @@ async def test_update_addon(
json={"result": "ok", "data": {}},
)
assert await hass.services.async_call(
await hass.services.async_call(
"update",
"install",
{"entity_id": "update.test_update"},
@ -276,7 +276,7 @@ async def test_update_os(
json={"result": "ok", "data": {}},
)
assert await hass.services.async_call(
await hass.services.async_call(
"update",
"install",
{"entity_id": "update.home_assistant_operating_system_update"},
@ -305,7 +305,7 @@ async def test_update_core(
json={"result": "ok", "data": {}},
)
assert await hass.services.async_call(
await hass.services.async_call(
"update",
"install",
{"entity_id": "update.home_assistant_os_update"},
@ -334,7 +334,7 @@ async def test_update_supervisor(
json={"result": "ok", "data": {}},
)
assert await hass.services.async_call(
await hass.services.async_call(
"update",
"install",
{"entity_id": "update.home_assistant_supervisor_update"},

View file

@ -49,13 +49,13 @@ async def test_apply_service(hass: HomeAssistant) -> None:
assert await async_setup_component(hass, "light", {"light": {"platform": "demo"}})
await hass.async_block_till_done()
assert await hass.services.async_call(
await hass.services.async_call(
"scene", "apply", {"entities": {"light.bed_light": "off"}}, blocking=True
)
assert hass.states.get("light.bed_light").state == "off"
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"apply",
{"entities": {"light.bed_light": {"state": "on", "brightness": 50}}},
@ -67,7 +67,7 @@ async def test_apply_service(hass: HomeAssistant) -> None:
assert state.attributes["brightness"] == 50
turn_on_calls = async_mock_service(hass, "light", "turn_on")
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"apply",
{
@ -98,7 +98,7 @@ async def test_create_service(
assert hass.states.get("scene.hallo") is None
assert hass.states.get("scene.hallo_2") is not None
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{"scene_id": "hallo", "entities": {}, "snapshot_entities": []},
@ -108,7 +108,7 @@ async def test_create_service(
assert "Empty scenes are not allowed" in caplog.text
assert hass.states.get("scene.hallo") is None
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{
@ -126,7 +126,7 @@ async def test_create_service(
assert scene.state == STATE_UNKNOWN
assert scene.attributes.get("entity_id") == ["light.bed_light"]
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{
@ -144,7 +144,7 @@ async def test_create_service(
assert scene.state == STATE_UNKNOWN
assert scene.attributes.get("entity_id") == ["light.kitchen_light"]
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{
@ -173,7 +173,7 @@ async def test_snapshot_service(
hass.states.async_set("light.my_light", "on", {"hs_color": (345, 75)})
assert hass.states.get("scene.hallo") is None
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{"scene_id": "hallo", "snapshot_entities": ["light.my_light"]},
@ -186,7 +186,7 @@ async def test_snapshot_service(
hass.states.async_set("light.my_light", "off", {"hs_color": (123, 45)})
turn_on_calls = async_mock_service(hass, "light", "turn_on")
assert await hass.services.async_call(
await hass.services.async_call(
"scene", "turn_on", {"entity_id": "scene.hallo"}, blocking=True
)
await hass.async_block_till_done()
@ -194,7 +194,7 @@ async def test_snapshot_service(
assert turn_on_calls[0].data.get("entity_id") == "light.my_light"
assert turn_on_calls[0].data.get("hs_color") == (345, 75)
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{"scene_id": "hallo_2", "snapshot_entities": ["light.not_existent"]},
@ -207,7 +207,7 @@ async def test_snapshot_service(
in caplog.text
)
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{
@ -230,7 +230,7 @@ async def test_ensure_no_intersection(hass: HomeAssistant) -> None:
await hass.async_block_till_done()
with pytest.raises(vol.MultipleInvalid) as ex:
assert await hass.services.async_call(
await hass.services.async_call(
"scene",
"create",
{

View file

@ -683,7 +683,7 @@ async def test_matrix_flame_morph_effects(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: entity_id, ATTR_EFFECT: "effect_flame"},
blocking=True,
)
await hass.async_block_till_done()
assert len(bulb.set_power.calls) == 1
assert len(bulb.set_tile_effect.calls) == 1
@ -824,7 +824,7 @@ async def test_lightstrip_move_effect(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: entity_id, ATTR_EFFECT: "effect_move"},
blocking=True,
)
await hass.async_block_till_done()
assert len(bulb.set_power.calls) == 1
assert len(bulb.set_multizone_effect.calls) == 1
@ -881,6 +881,7 @@ async def test_lightstrip_move_effect(hass: HomeAssistant) -> None:
{ATTR_ENTITY_ID: entity_id, ATTR_EFFECT: "effect_stop"},
blocking=True,
)
await hass.async_block_till_done()
assert len(bulb.set_power.calls) == 0
assert len(bulb.set_multizone_effect.calls) == 1
call_dict = bulb.set_multizone_effect.calls[0][1]

View file

@ -143,7 +143,7 @@ async def test_notify_works(
) -> None:
"""Test notify works."""
assert hass.services.has_service("notify", "mobile_app_test") is True
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world"}, blocking=True
)
@ -191,7 +191,7 @@ async def test_notify_ws_works(
sub_result = await client.receive_json()
assert sub_result["success"]
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world"}, blocking=True
)
@ -212,7 +212,7 @@ async def test_notify_ws_works(
sub_result = await client.receive_json()
assert sub_result["success"]
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world 2"}, blocking=True
)
@ -271,7 +271,7 @@ async def test_notify_ws_confirming_works(
assert sub_result["success"]
# Sent a message that will be delivered locally
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world"}, blocking=True
)
@ -359,23 +359,24 @@ async def test_notify_ws_not_confirming(
sub_result = await client.receive_json()
assert sub_result["success"]
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world 1"}, blocking=True
)
with patch(
"homeassistant.components.mobile_app.push_notification.PUSH_CONFIRM_TIMEOUT", 0
):
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world 2"}, blocking=True
)
await hass.async_block_till_done()
await hass.async_block_till_done()
# When we fail, all unconfirmed ones and failed one are sent via cloud
assert len(aioclient_mock.mock_calls) == 2
# All future ones also go via cloud
assert await hass.services.async_call(
await hass.services.async_call(
"notify", "mobile_app_test", {"message": "Hello world 3"}, blocking=True
)
@ -389,7 +390,7 @@ async def test_local_push_only(
) -> None:
"""Test a local only push registration."""
with pytest.raises(HomeAssistantError) as e_info:
assert await hass.services.async_call(
await hass.services.async_call(
"notify",
"mobile_app_websocket_push_name",
{"message": "Not connected"},
@ -411,7 +412,7 @@ async def test_local_push_only(
sub_result = await client.receive_json()
assert sub_result["success"]
assert await hass.services.async_call(
await hass.services.async_call(
"notify",
"mobile_app_websocket_push_name",
{"message": "Hello world 1"},

View file

@ -637,7 +637,7 @@ async def test_switch_on(hass: HomeAssistant) -> None:
with patch(
"homeassistant.components.nextdns.NextDns.set_setting", return_value=True
) as mock_switch_on:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: "switch.fake_profile_block_page"},
@ -663,7 +663,7 @@ async def test_switch_off(hass: HomeAssistant) -> None:
with patch(
"homeassistant.components.nextdns.NextDns.set_setting", return_value=True
) as mock_switch_on:
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: "switch.fake_profile_web3"},

View file

@ -26,7 +26,7 @@ async def test_scan_clients_button_schedule(
dt_util.utcnow() + timedelta(seconds=DEBOUNCE_TIMEOUT),
)
assert await hass.services.async_call(
await hass.services.async_call(
BUTTON_DOMAIN,
SERVICE_PRESS,
{

View file

@ -30,7 +30,7 @@ async def test_media_lookups(
requests_mock.post("/playqueues", text=playqueue_created)
requests_mock.get("/player/playback/playMedia", status_code=200)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -43,7 +43,7 @@ async def test_media_lookups(
with pytest.raises(MediaNotFound) as excinfo, patch(
"plexapi.server.PlexServer.fetchItem", side_effect=NotFound
):
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -58,7 +58,7 @@ async def test_media_lookups(
# TV show searches
with pytest.raises(MediaNotFound) as excinfo:
payload = '{"library_name": "Not a Library", "show_name": "TV Show"}'
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -71,7 +71,7 @@ async def test_media_lookups(
assert "Library 'Not a Library' not found in" in str(excinfo.value)
with patch("plexapi.library.LibrarySection.search") as search:
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -83,7 +83,7 @@ async def test_media_lookups(
)
search.assert_called_with(**{"show.title": "TV Show", "libtype": "show"})
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -97,7 +97,7 @@ async def test_media_lookups(
**{"episode.title": "An Episode", "libtype": "episode"}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -111,7 +111,7 @@ async def test_media_lookups(
**{"show.title": "TV Show", "season.index": 1, "libtype": "season"}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -130,7 +130,7 @@ async def test_media_lookups(
}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -142,7 +142,7 @@ async def test_media_lookups(
)
search.assert_called_with(**{"artist.title": "Artist", "libtype": "artist"})
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -154,7 +154,7 @@ async def test_media_lookups(
)
search.assert_called_with(**{"album.title": "Album", "libtype": "album"})
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -168,7 +168,7 @@ async def test_media_lookups(
**{"artist.title": "Artist", "track.title": "Track 3", "libtype": "track"}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -182,7 +182,7 @@ async def test_media_lookups(
**{"artist.title": "Artist", "album.title": "Album", "libtype": "album"}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -201,7 +201,7 @@ async def test_media_lookups(
}
)
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -221,7 +221,7 @@ async def test_media_lookups(
)
# Movie searches
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -233,7 +233,7 @@ async def test_media_lookups(
)
search.assert_called_with(**{"movie.title": "Movie 1", "libtype": None})
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -247,7 +247,7 @@ async def test_media_lookups(
with pytest.raises(MediaNotFound) as excinfo:
payload = '{"title": "Movie 1"}'
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -262,7 +262,7 @@ async def test_media_lookups(
with pytest.raises(MediaNotFound) as excinfo:
payload = '{"library_name": "Movies", "title": "Not a Movie"}'
with patch("plexapi.library.LibrarySection.search", side_effect=BadRequest):
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -275,7 +275,7 @@ async def test_media_lookups(
assert "Problem in query" in str(excinfo.value)
# Playlist searches
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -288,7 +288,7 @@ async def test_media_lookups(
with pytest.raises(MediaNotFound) as excinfo:
payload = '{"playlist_name": "Not a Playlist"}'
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -302,7 +302,7 @@ async def test_media_lookups(
with pytest.raises(MediaNotFound) as excinfo:
payload = "{}"
assert await hass.services.async_call(
await hass.services.async_call(
MEDIA_PLAYER_DOMAIN,
SERVICE_PLAY_MEDIA,
{

View file

@ -67,7 +67,7 @@ async def test_media_player_playback(
with patch(
"plexapi.library.LibrarySection.search", return_value=None
), pytest.raises(HomeAssistantError) as excinfo:
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -87,7 +87,7 @@ async def test_media_player_playback(
# Test movie success
movies = [movie1]
with patch("plexapi.library.LibrarySection.search", return_value=movies):
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -102,7 +102,7 @@ async def test_media_player_playback(
# Test movie success with resume
playmedia_mock.reset()
with patch("plexapi.library.LibrarySection.search", return_value=movies):
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -117,7 +117,7 @@ async def test_media_player_playback(
# Test movie success with media browser URL
playmedia_mock.reset()
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -132,7 +132,7 @@ async def test_media_player_playback(
# Test movie success with media browser URL and resuming
playmedia_mock.reset()
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -148,7 +148,7 @@ async def test_media_player_playback(
# Test movie success with legacy media browser URL
playmedia_mock.reset()
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -164,7 +164,7 @@ async def test_media_player_playback(
playmedia_mock.reset()
movies = [movie1, movie2]
with patch("plexapi.library.LibrarySection.search", return_value=movies):
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -182,7 +182,7 @@ async def test_media_player_playback(
with pytest.raises(HomeAssistantError) as excinfo:
payload = '{"library_name": "Movies", "title": "Movie" }'
with patch("plexapi.library.LibrarySection.search", return_value=movies):
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -200,7 +200,7 @@ async def test_media_player_playback(
with patch("plexapi.library.LibrarySection.search", return_value=movies), patch(
"homeassistant.components.plex.server.PlexServer.create_playqueue"
) as mock_create_playqueue:
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -216,7 +216,7 @@ async def test_media_player_playback(
# Test radio station
playmedia_mock.reset()
radio_id = "/library/sections/3/stations/1"
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{

View file

@ -45,7 +45,7 @@ async def test_refresh_library(
# Test with non-existent server
with pytest.raises(HomeAssistantError):
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_REFRESH_LIBRARY,
{"server_name": "Not a Server", "library_name": "Movies"},
@ -54,7 +54,7 @@ async def test_refresh_library(
assert not refresh.called
# Test with non-existent library
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_REFRESH_LIBRARY,
{"library_name": "Not a Library"},
@ -63,7 +63,7 @@ async def test_refresh_library(
assert not refresh.called
# Test with valid library
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_REFRESH_LIBRARY,
{"library_name": "Movies"},
@ -96,7 +96,7 @@ async def test_refresh_library(
# Test multiple servers available but none specified
with pytest.raises(HomeAssistantError) as excinfo:
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_REFRESH_LIBRARY,
{"library_name": "Movies"},
@ -108,7 +108,7 @@ async def test_refresh_library(
async def test_scan_clients(hass: HomeAssistant, mock_plex_server) -> None:
"""Test scan_for_clients service call."""
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SCAN_CLIENTS,
blocking=True,

View file

@ -224,6 +224,8 @@ async def test_log_scheduled(
assert hass.services.has_service(DOMAIN, SERVICE_LOG_EVENT_LOOP_SCHEDULED)
hass.loop.call_later(0.1, lambda: None)
await hass.services.async_call(
DOMAIN, SERVICE_LOG_EVENT_LOOP_SCHEDULED, {}, blocking=True
)

View file

@ -1426,7 +1426,7 @@ def test_service_disable_events_not_recording(
"""Test that events are not recorded when recorder is disabled using service."""
hass = hass_recorder()
assert hass.services.call(
hass.services.call(
DOMAIN,
SERVICE_DISABLE,
{},
@ -1460,7 +1460,7 @@ def test_service_disable_events_not_recording(
)
assert len(db_events) == 0
assert hass.services.call(
hass.services.call(
DOMAIN,
SERVICE_ENABLE,
{},
@ -1510,7 +1510,7 @@ def test_service_disable_states_not_recording(
"""Test that state changes are not recorded when recorder is disabled using service."""
hass = hass_recorder()
assert hass.services.call(
hass.services.call(
DOMAIN,
SERVICE_DISABLE,
{},
@ -1523,7 +1523,7 @@ def test_service_disable_states_not_recording(
with session_scope(hass=hass, read_only=True) as session:
assert len(list(session.query(States))) == 0
assert hass.services.call(
hass.services.call(
DOMAIN,
SERVICE_ENABLE,
{},
@ -1563,7 +1563,7 @@ def test_service_disable_run_information_recorded(tmp_path: Path) -> None:
assert db_run_info[0].start is not None
assert db_run_info[0].end is None
assert hass.services.call(
hass.services.call(
DOMAIN,
SERVICE_DISABLE,
{},

View file

@ -262,7 +262,7 @@ async def test_turn_on_success(hass: HomeAssistant) -> None:
route = respx.post(RESOURCE) % HTTPStatus.OK
respx.get(RESOURCE).mock(side_effect=httpx.RequestError)
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: "switch.foo"},
@ -282,7 +282,7 @@ async def test_turn_on_status_not_ok(hass: HomeAssistant) -> None:
await _async_setup_test_switch(hass)
route = respx.post(RESOURCE) % HTTPStatus.INTERNAL_SERVER_ERROR
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: "switch.foo"},
@ -302,7 +302,7 @@ async def test_turn_on_timeout(hass: HomeAssistant) -> None:
await _async_setup_test_switch(hass)
respx.post(RESOURCE) % HTTPStatus.INTERNAL_SERVER_ERROR
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: "switch.foo"},
@ -320,7 +320,7 @@ async def test_turn_off_success(hass: HomeAssistant) -> None:
route = respx.post(RESOURCE) % HTTPStatus.OK
respx.get(RESOURCE).mock(side_effect=httpx.RequestError)
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: "switch.foo"},
@ -341,7 +341,7 @@ async def test_turn_off_status_not_ok(hass: HomeAssistant) -> None:
await _async_setup_test_switch(hass)
route = respx.post(RESOURCE) % HTTPStatus.INTERNAL_SERVER_ERROR
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: "switch.foo"},
@ -362,7 +362,7 @@ async def test_turn_off_timeout(hass: HomeAssistant) -> None:
await _async_setup_test_switch(hass)
respx.post(RESOURCE).mock(side_effect=asyncio.TimeoutError())
assert await hass.services.async_call(
await hass.services.async_call(
SWITCH_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: "switch.foo"},

View file

@ -4,6 +4,8 @@ Test setup of RFLink lights component/platform. State tracking and
control of RFLink switch devices.
"""
import asyncio
from homeassistant.components.light import ATTR_BRIGHTNESS
from homeassistant.components.rflink import EVENT_BUTTON_PRESSED
from homeassistant.const import (
@ -283,7 +285,8 @@ async def test_signal_repetitions_cancelling(hass: HomeAssistant, monkeypatch) -
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: f"{DOMAIN}.test"}
)
# Get background service time to start running
await asyncio.sleep(0)
await hass.services.async_call(
DOMAIN, SERVICE_TURN_ON, {ATTR_ENTITY_ID: f"{DOMAIN}.test"}, blocking=True
)

View file

@ -65,7 +65,7 @@ async def test_setup(hass: HomeAssistant) -> None:
)
# test host and port
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)

View file

@ -524,7 +524,7 @@ async def test_connection_closed_during_update_can_recover(
async def test_send_key(hass: HomeAssistant, remote: Mock) -> None:
"""Test for send key."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -540,7 +540,7 @@ async def test_send_key_broken_pipe(hass: HomeAssistant, remote: Mock) -> None:
"""Testing broken pipe Exception."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.control = Mock(side_effect=BrokenPipeError("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -555,7 +555,7 @@ async def test_send_key_connection_closed_retry_succeed(
remote.control = Mock(
side_effect=[exceptions.ConnectionClosed("Boom"), DEFAULT_MOCK, DEFAULT_MOCK]
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -574,7 +574,7 @@ async def test_send_key_unhandled_response(hass: HomeAssistant, remote: Mock) ->
"""Testing unhandled response exception."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.control = Mock(side_effect=exceptions.UnhandledResponse("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -586,7 +586,7 @@ async def test_send_key_websocketexception(hass: HomeAssistant, remotews: Mock)
"""Testing unhandled response exception."""
await setup_samsungtv_entry(hass, MOCK_CONFIGWS)
remotews.send_commands = Mock(side_effect=WebSocketException("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -600,7 +600,7 @@ async def test_send_key_websocketexception_encrypted(
"""Testing unhandled response exception."""
await setup_samsungtv_entry(hass, MOCK_ENTRYDATA_ENCRYPTED_WS)
remoteencws.send_commands = Mock(side_effect=WebSocketException("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -612,7 +612,7 @@ async def test_send_key_os_error_ws(hass: HomeAssistant, remotews: Mock) -> None
"""Testing unhandled response exception."""
await setup_samsungtv_entry(hass, MOCK_CONFIGWS)
remotews.send_commands = Mock(side_effect=OSError("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -626,7 +626,7 @@ async def test_send_key_os_error_ws_encrypted(
"""Testing unhandled response exception."""
await setup_samsungtv_entry(hass, MOCK_ENTRYDATA_ENCRYPTED_WS)
remoteencws.send_commands = Mock(side_effect=OSError("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -637,7 +637,7 @@ async def test_send_key_os_error(hass: HomeAssistant, remote: Mock) -> None:
"""Testing broken pipe Exception."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.control = Mock(side_effect=OSError("Boom"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -656,12 +656,12 @@ async def test_name(hass: HomeAssistant) -> None:
async def test_state(hass: HomeAssistant) -> None:
"""Test for state property."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
assert state.state == STATE_ON
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
state = hass.states.get(ENTITY_ID)
@ -711,7 +711,7 @@ async def test_turn_off_websocket(
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key called
@ -723,11 +723,11 @@ async def test_turn_off_websocket(
# commands not sent : power off in progress
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert "TV is powering off, not sending keys: ['KEY_VOLUP']" in caplog.text
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SELECT_SOURCE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_INPUT_SOURCE: "Deezer"},
@ -750,7 +750,7 @@ async def test_turn_off_websocket_frame(
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key called
@ -778,7 +778,7 @@ async def test_turn_off_encrypted_websocket(
remoteencws.send_commands.reset_mock()
caplog.clear()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key called
@ -793,7 +793,7 @@ async def test_turn_off_encrypted_websocket(
# commands not sent : power off in progress
remoteencws.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert "TV is powering off, not sending keys: ['KEY_VOLUP']" in caplog.text
@ -819,7 +819,7 @@ async def test_turn_off_encrypted_websocket_key_type(
remoteencws.send_commands.reset_mock()
caplog.clear()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key called
@ -834,7 +834,7 @@ async def test_turn_off_encrypted_websocket_key_type(
async def test_turn_off_legacy(hass: HomeAssistant, remote: Mock) -> None:
"""Test for turn_off."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key called
@ -849,7 +849,7 @@ async def test_turn_off_os_error(
caplog.set_level(logging.DEBUG)
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.close = Mock(side_effect=OSError("BOOM"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert "Could not establish connection" in caplog.text
@ -863,7 +863,7 @@ async def test_turn_off_ws_os_error(
caplog.set_level(logging.DEBUG)
await setup_samsungtv_entry(hass, MOCK_CONFIGWS)
remotews.close = Mock(side_effect=OSError("BOOM"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert "Error closing connection" in caplog.text
@ -877,7 +877,7 @@ async def test_turn_off_encryptedws_os_error(
caplog.set_level(logging.DEBUG)
await setup_samsungtv_entry(hass, MOCK_ENTRYDATA_ENCRYPTED_WS)
remoteencws.close = Mock(side_effect=OSError("BOOM"))
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
assert "Error closing connection" in caplog.text
@ -886,7 +886,7 @@ async def test_turn_off_encryptedws_os_error(
async def test_volume_up(hass: HomeAssistant, remote: Mock) -> None:
"""Test for volume_up."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_UP, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -899,7 +899,7 @@ async def test_volume_up(hass: HomeAssistant, remote: Mock) -> None:
async def test_volume_down(hass: HomeAssistant, remote: Mock) -> None:
"""Test for volume_down."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_VOLUME_DOWN, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -912,7 +912,7 @@ async def test_volume_down(hass: HomeAssistant, remote: Mock) -> None:
async def test_mute_volume(hass: HomeAssistant, remote: Mock) -> None:
"""Test for mute_volume."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_VOLUME_MUTE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_MEDIA_VOLUME_MUTED: True},
@ -928,7 +928,7 @@ async def test_mute_volume(hass: HomeAssistant, remote: Mock) -> None:
async def test_media_play(hass: HomeAssistant, remote: Mock) -> None:
"""Test for media_play."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_PLAY, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -937,7 +937,7 @@ async def test_media_play(hass: HomeAssistant, remote: Mock) -> None:
assert remote.close.call_count == 1
assert remote.close.call_args_list == [call()]
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -950,7 +950,7 @@ async def test_media_play(hass: HomeAssistant, remote: Mock) -> None:
async def test_media_pause(hass: HomeAssistant, remote: Mock) -> None:
"""Test for media_pause."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_PAUSE, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -959,7 +959,7 @@ async def test_media_pause(hass: HomeAssistant, remote: Mock) -> None:
assert remote.close.call_count == 1
assert remote.close.call_args_list == [call()]
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -972,7 +972,7 @@ async def test_media_pause(hass: HomeAssistant, remote: Mock) -> None:
async def test_media_next_track(hass: HomeAssistant, remote: Mock) -> None:
"""Test for media_next_track."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_NEXT_TRACK, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -985,7 +985,7 @@ async def test_media_next_track(hass: HomeAssistant, remote: Mock) -> None:
async def test_media_previous_track(hass: HomeAssistant, remote: Mock) -> None:
"""Test for media_previous_track."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_MEDIA_PREVIOUS_TRACK, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
# key and update called
@ -1009,7 +1009,7 @@ async def test_turn_on_wol(hass: HomeAssistant) -> None:
with patch(
"homeassistant.components.samsungtv.media_player.send_magic_packet"
) as mock_send_magic_packet:
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_ON, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
await hass.async_block_till_done()
@ -1031,7 +1031,7 @@ async def test_play_media(hass: HomeAssistant, remote: Mock) -> None:
"""Test for play_media."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
with patch("homeassistant.components.samsungtv.bridge.asyncio.sleep") as sleep:
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -1060,7 +1060,7 @@ async def test_play_media_invalid_type(hass: HomeAssistant) -> None:
url = "https://example.com"
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -1082,7 +1082,7 @@ async def test_play_media_channel_as_string(hass: HomeAssistant) -> None:
url = "https://example.com"
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -1103,7 +1103,7 @@ async def test_play_media_channel_as_non_positive(hass: HomeAssistant) -> None:
with patch("homeassistant.components.samsungtv.bridge.Remote") as remote:
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -1122,7 +1122,7 @@ async def test_play_media_channel_as_non_positive(hass: HomeAssistant) -> None:
async def test_select_source(hass: HomeAssistant, remote: Mock) -> None:
"""Test for select_source."""
await setup_samsungtv_entry(hass, MOCK_CONFIG)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SELECT_SOURCE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_INPUT_SOURCE: "HDMI"},
@ -1140,7 +1140,7 @@ async def test_select_source_invalid_source(hass: HomeAssistant) -> None:
with patch("homeassistant.components.samsungtv.bridge.Remote") as remote:
await setup_samsungtv_entry(hass, MOCK_CONFIG)
remote.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SELECT_SOURCE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_INPUT_SOURCE: "INVALID"},
@ -1158,7 +1158,7 @@ async def test_play_media_app(hass: HomeAssistant, remotews: Mock) -> None:
await setup_samsungtv_entry(hass, MOCK_CONFIGWS)
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -1182,7 +1182,7 @@ async def test_select_source_app(hass: HomeAssistant, remotews: Mock) -> None:
await setup_samsungtv_entry(hass, MOCK_CONFIGWS)
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_SELECT_SOURCE,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_INPUT_SOURCE: "Deezer"},
@ -1207,7 +1207,7 @@ async def test_websocket_unsupported_remote_control(
remotews.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN, SERVICE_TURN_OFF, {ATTR_ENTITY_ID: ENTITY_ID}, True
)
remotews.raise_mock_ws_event_callback(
@ -1256,7 +1256,7 @@ async def test_volume_control_upnp(
assert state.attributes[ATTR_MEDIA_VOLUME_MUTED] is False
# Upnp action succeeds
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_VOLUME_SET,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_MEDIA_VOLUME_LEVEL: 0.5},
@ -1270,7 +1270,7 @@ async def test_volume_control_upnp(
dmr_device.async_set_volume_level.side_effect = UpnpActionResponseError(
status=500, error_code=501, error_desc="Action Failed"
)
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_VOLUME_SET,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_MEDIA_VOLUME_LEVEL: 0.6},
@ -1289,7 +1289,7 @@ async def test_upnp_not_available(
assert "Unable to create Upnp DMR device" in caplog.text
# Upnp action fails
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_VOLUME_SET,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_MEDIA_VOLUME_LEVEL: 0.6},
@ -1307,7 +1307,7 @@ async def test_upnp_missing_service(
assert "Unable to create Upnp DMR device" in caplog.text
# Upnp action fails
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
SERVICE_VOLUME_SET,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_MEDIA_VOLUME_LEVEL: 0.6},

View file

@ -46,7 +46,7 @@ async def test_main_services(
remoteencws.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
REMOTE_DOMAIN,
SERVICE_TURN_OFF,
{ATTR_ENTITY_ID: ENTITY_ID},
@ -64,7 +64,7 @@ async def test_main_services(
# commands not sent : power off in progress
remoteencws.send_commands.reset_mock()
assert await hass.services.async_call(
await hass.services.async_call(
REMOTE_DOMAIN,
SERVICE_SEND_COMMAND,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_COMMAND: ["dash"]},
@ -79,7 +79,7 @@ async def test_send_command_service(hass: HomeAssistant, remoteencws: Mock) -> N
"""Test the send command."""
await setup_samsungtv_entry(hass, MOCK_ENTRYDATA_ENCRYPTED_WS)
assert await hass.services.async_call(
await hass.services.async_call(
REMOTE_DOMAIN,
SERVICE_SEND_COMMAND,
{ATTR_ENTITY_ID: ENTITY_ID, ATTR_COMMAND: ["dash"]},

View file

@ -34,7 +34,7 @@ async def test_plex_play_media(hass: HomeAssistant, async_autosetup_sonos) -> No
"homeassistant.components.sonos.media_player.SonosMediaPlayerEntity.set_shuffle"
) as mock_shuffle:
# Test successful Plex service call
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -59,7 +59,7 @@ async def test_plex_play_media(hass: HomeAssistant, async_autosetup_sonos) -> No
'"album_name": "Album", "shuffle": 1}'
)
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{
@ -107,7 +107,7 @@ async def test_plex_play_media(hass: HomeAssistant, async_autosetup_sonos) -> No
"homeassistant.components.plex.services.get_plex_server",
return_value=mock_plex_server,
):
assert await hass.services.async_call(
await hass.services.async_call(
MP_DOMAIN,
SERVICE_PLAY_MEDIA,
{

View file

@ -156,7 +156,6 @@ async def test_get_trace(
}
sun_action = {
"limit": 10,
"params": {
"domain": "test",
"service": "automation",
@ -1594,7 +1593,6 @@ async def test_trace_blueprint_automation(
},
}
sun_action = {
"limit": 10,
"params": {
"domain": "test",
"service": "automation",

View file

@ -90,7 +90,7 @@ async def test_services_with_parameters(
await setup_webostv(hass)
data = {ATTR_ENTITY_ID: ENTITY_ID, **attr_data}
assert await hass.services.async_call(MP_DOMAIN, service, data, True)
await hass.services.async_call(MP_DOMAIN, service, data, True)
getattr(client, client_call[0]).assert_called_once_with(client_call[1])
@ -111,7 +111,7 @@ async def test_services(hass: HomeAssistant, client, service, client_call) -> No
await setup_webostv(hass)
data = {ATTR_ENTITY_ID: ENTITY_ID}
assert await hass.services.async_call(MP_DOMAIN, service, data, True)
await hass.services.async_call(MP_DOMAIN, service, data, True)
getattr(client, client_call).assert_called_once()
@ -123,17 +123,13 @@ async def test_media_play_pause(hass: HomeAssistant, client) -> None:
data = {ATTR_ENTITY_ID: ENTITY_ID}
# After init state is playing - check pause call
assert await hass.services.async_call(
MP_DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, data, True
)
await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, data, True)
client.pause.assert_called_once()
client.play.assert_not_called()
# After pause state is paused - check play call
assert await hass.services.async_call(
MP_DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, data, True
)
await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY_PAUSE, data, True)
client.play.assert_called_once()
client.pause.assert_called_once()
@ -154,7 +150,7 @@ async def test_media_next_previous_track(
# check channel up/down for live TV channels
data = {ATTR_ENTITY_ID: ENTITY_ID}
assert await hass.services.async_call(MP_DOMAIN, service, data, True)
await hass.services.async_call(MP_DOMAIN, service, data, True)
getattr(client, client_call[0]).assert_not_called()
getattr(client, client_call[1]).assert_called_once()
@ -162,7 +158,7 @@ async def test_media_next_previous_track(
# check next/previous for not Live TV channels
monkeypatch.setattr(client, "current_app_id", "in1")
data = {ATTR_ENTITY_ID: ENTITY_ID}
assert await hass.services.async_call(MP_DOMAIN, service, data, True)
await hass.services.async_call(MP_DOMAIN, service, data, True)
getattr(client, client_call[0]).assert_called_once()
getattr(client, client_call[1]).assert_called_once()
@ -179,7 +175,7 @@ async def test_select_source_with_empty_source_list(
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_INPUT_SOURCE: "nonexistent",
}
assert await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
client.launch_app.assert_not_called()
client.set_input.assert_not_called()
@ -195,7 +191,7 @@ async def test_select_app_source(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_INPUT_SOURCE: "Live TV",
}
assert await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
client.launch_app.assert_called_once_with(LIVE_TV_APP_ID)
client.set_input.assert_not_called()
@ -210,7 +206,7 @@ async def test_select_input_source(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_INPUT_SOURCE: "Input01",
}
assert await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_SELECT_SOURCE, data, True)
client.launch_app.assert_not_called()
client.set_input.assert_called_once_with("in1")
@ -224,8 +220,8 @@ async def test_button(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_BUTTON: "test",
}
assert await hass.services.async_call(DOMAIN, SERVICE_BUTTON, data, True)
await hass.services.async_call(DOMAIN, SERVICE_BUTTON, data, True)
await hass.async_block_till_done()
client.button.assert_called_once()
client.button.assert_called_with("test")
@ -238,8 +234,8 @@ async def test_command(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_COMMAND: "test",
}
assert await hass.services.async_call(DOMAIN, SERVICE_COMMAND, data, True)
await hass.services.async_call(DOMAIN, SERVICE_COMMAND, data, True)
await hass.async_block_till_done()
client.request.assert_called_with("test", payload=None)
@ -252,8 +248,8 @@ async def test_command_with_optional_arg(hass: HomeAssistant, client) -> None:
ATTR_COMMAND: "test",
ATTR_PAYLOAD: {"target": "https://www.google.com"},
}
assert await hass.services.async_call(DOMAIN, SERVICE_COMMAND, data, True)
await hass.services.async_call(DOMAIN, SERVICE_COMMAND, data, True)
await hass.async_block_till_done()
client.request.assert_called_with(
"test", payload={"target": "https://www.google.com"}
)
@ -267,10 +263,8 @@ async def test_select_sound_output(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_ID,
ATTR_SOUND_OUTPUT: "external_speaker",
}
assert await hass.services.async_call(
DOMAIN, SERVICE_SELECT_SOUND_OUTPUT, data, True
)
await hass.services.async_call(DOMAIN, SERVICE_SELECT_SOUND_OUTPUT, data, True)
await hass.async_block_till_done()
client.change_sound_output.assert_called_once_with("external_speaker")
@ -359,9 +353,7 @@ async def test_service_entity_id_none(hass: HomeAssistant, client) -> None:
ATTR_ENTITY_ID: ENTITY_MATCH_NONE,
ATTR_SOUND_OUTPUT: "external_speaker",
}
assert await hass.services.async_call(
DOMAIN, SERVICE_SELECT_SOUND_OUTPUT, data, True
)
await hass.services.async_call(DOMAIN, SERVICE_SELECT_SOUND_OUTPUT, data, True)
client.change_sound_output.assert_not_called()
@ -384,7 +376,7 @@ async def test_play_media(hass: HomeAssistant, client, media_id, ch_id) -> None:
ATTR_MEDIA_CONTENT_TYPE: MediaType.CHANNEL,
ATTR_MEDIA_CONTENT_ID: media_id,
}
assert await hass.services.async_call(MP_DOMAIN, SERVICE_PLAY_MEDIA, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_PLAY_MEDIA, data, True)
client.set_channel.assert_called_once_with(ch_id)
@ -493,7 +485,7 @@ async def test_control_error_handling(
# Device on, raise HomeAssistantError
with pytest.raises(HomeAssistantError) as exc:
assert await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY, data, True)
assert (
str(exc.value)
@ -505,7 +497,7 @@ async def test_control_error_handling(
monkeypatch.setattr(client, "is_on", False)
monkeypatch.setattr(client, "play", Mock(side_effect=asyncio.TimeoutError))
await client.mock_state_update()
assert await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY, data, True)
await hass.services.async_call(MP_DOMAIN, SERVICE_MEDIA_PLAY, data, True)
assert client.play.call_count == 1
assert (

View file

@ -106,7 +106,7 @@ async def test_fan_reset_filter_service(
hass: HomeAssistant, pywemo_device, wemo_entity
) -> None:
"""Verify that SERVICE_RESET_FILTER_LIFE is registered and works."""
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
fan.SERVICE_RESET_FILTER_LIFE,
{ATTR_ENTITY_ID: wemo_entity.entity_id},
@ -130,7 +130,7 @@ async def test_fan_set_humidity_service(
hass: HomeAssistant, pywemo_device, wemo_entity, test_input, expected
) -> None:
"""Verify that SERVICE_SET_HUMIDITY is registered and works."""
assert await hass.services.async_call(
await hass.services.async_call(
DOMAIN,
fan.SERVICE_SET_HUMIDITY,
{
@ -157,7 +157,7 @@ async def test_fan_set_percentage(
hass: HomeAssistant, pywemo_device, wemo_entity, percentage, expected_fan_mode
) -> None:
"""Verify set_percentage works properly through the entire range of FanModes."""
assert await hass.services.async_call(
await hass.services.async_call(
FAN_DOMAIN,
SERVICE_SET_PERCENTAGE,
{ATTR_ENTITY_ID: [wemo_entity.entity_id], ATTR_PERCENTAGE: percentage},
@ -170,7 +170,7 @@ async def test_fan_mode_high_initially(hass: HomeAssistant, pywemo_device) -> No
"""Verify the FanMode is set to High when turned on."""
pywemo_device.fan_mode = FanMode.Off
wemo_entity = await async_create_wemo_entity(hass, pywemo_device, "")
assert await hass.services.async_call(
await hass.services.async_call(
FAN_DOMAIN,
SERVICE_TURN_ON,
{ATTR_ENTITY_ID: [wemo_entity.entity_id]},

View file

@ -28,7 +28,7 @@ async def test_ping_entity(
},
blocking=True,
)
await hass.async_block_till_done()
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.ping"
@ -47,7 +47,7 @@ async def test_ping_entity(
},
blocking=True,
)
await hass.async_block_till_done()
assert "There is no value to refresh for this entity" in caplog.text
# Assert a node ping button entity is not created for the controller

View file

@ -297,7 +297,7 @@ async def test_thermostat_v2(
},
blocking=True,
)
await hass.async_block_till_done()
assert "Error while refreshing value" in caplog.text

View file

@ -368,7 +368,7 @@ async def test_node_status_sensor_not_ready(
},
blocking=True,
)
await hass.async_block_till_done()
assert "There is no value to refresh for this entity" in caplog.text
@ -755,7 +755,7 @@ async def test_statistics_sensors(
{ATTR_ENTITY_ID: entity_id},
blocking=True,
)
await hass.async_block_till_done()
assert caplog.text.count("There is no value to refresh for this entity") == len(
[
*CONTROLLER_STATISTICS_SUFFIXES,

View file

@ -678,6 +678,7 @@ async def test_refresh_value(
{ATTR_ENTITY_ID: CLIMATE_RADIO_THERMOSTAT_ENTITY},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "node.poll_value"
@ -701,6 +702,7 @@ async def test_refresh_value(
},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 8
client.async_send_command.reset_mock()
@ -716,6 +718,7 @@ async def test_refresh_value(
},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 8
client.async_send_command.reset_mock()
@ -733,6 +736,7 @@ async def test_refresh_value(
},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 8
client.async_send_command.reset_mock()
@ -1593,6 +1597,7 @@ async def test_invoke_cc_api(
},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "endpoint.invoke_cc_api"
@ -1645,6 +1650,7 @@ async def test_invoke_cc_api(
},
blocking=True,
)
await hass.async_block_till_done()
assert len(client.async_send_command.call_args_list) == 1
args = client.async_send_command.call_args[0][0]
assert args["command"] == "endpoint.invoke_cc_api"

View file

@ -127,7 +127,7 @@ async def test_update_entity_states(
},
blocking=True,
)
await hass.async_block_till_done()
assert "There is no value to refresh for this entity" in caplog.text
client.async_send_command.return_value = {"updates": []}

View file

@ -1,4 +1,5 @@
"""Tests for the intent helpers."""
import asyncio
from unittest.mock import MagicMock, patch
import pytest
@ -246,3 +247,41 @@ def test_async_remove_no_existing(hass: HomeAssistant) -> None:
# simply shouldn't cause an exception
assert intent.DATA_KEY not in hass.data
async def test_validate_then_run_in_background(hass: HomeAssistant) -> None:
"""Test we don't execute a service in foreground forever."""
hass.states.async_set("light.kitchen", "off")
call_done = asyncio.Event()
calls = []
# Register a service that takes 0.1 seconds to execute
async def mock_service(call):
"""Mock service."""
await asyncio.sleep(0.1)
call_done.set()
calls.append(call)
hass.services.async_register("light", "turn_on", mock_service)
# Create intent handler with a service timeout of 0.05 seconds
handler = intent.ServiceIntentHandler(
"TestType", "light", "turn_on", "Turned {} on"
)
handler.service_timeout = 0.05
intent.async_register(hass, handler)
result = await intent.async_handle(
hass,
"test",
"TestType",
slots={"name": {"value": "kitchen"}},
)
assert result.response_type == intent.IntentResponseType.ACTION_DONE
assert not call_done.is_set()
await call_done.wait()
assert len(calls) == 1
assert calls[0].data == {"entity_id": "light.kitchen"}

View file

@ -23,7 +23,6 @@ from homeassistant.const import (
SERVICE_TURN_ON,
)
from homeassistant.core import (
SERVICE_CALL_LIMIT,
Context,
CoreState,
HomeAssistant,
@ -264,7 +263,6 @@ async def test_calling_service_basic(
"0": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -317,7 +315,6 @@ async def test_calling_service_template(hass: HomeAssistant) -> None:
"0": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -356,7 +353,6 @@ async def test_data_template_with_templated_key(hass: HomeAssistant) -> None:
"0": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -3338,7 +3334,6 @@ async def test_parallel_error(
{
"error_type": ServiceNotFound,
"result": {
"limit": 10,
"params": {
"domain": "epic",
"service": "failure",
@ -3387,7 +3382,6 @@ async def test_propagate_error_service_not_found(hass: HomeAssistant) -> None:
{
"error_type": ServiceNotFound,
"result": {
"limit": 10,
"params": {
"domain": "test",
"service": "script",
@ -3424,7 +3418,6 @@ async def test_propagate_error_invalid_service_data(hass: HomeAssistant) -> None
{
"error_type": vol.MultipleInvalid,
"result": {
"limit": 10,
"params": {
"domain": "test",
"service": "script",
@ -3465,7 +3458,6 @@ async def test_propagate_error_service_exception(hass: HomeAssistant) -> None:
{
"error_type": ValueError,
"result": {
"limit": 10,
"params": {
"domain": "test",
"service": "script",
@ -4343,7 +4335,6 @@ async def test_set_variable(
"1": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -4386,7 +4377,6 @@ async def test_set_redefines_variable(
"1": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -4402,7 +4392,6 @@ async def test_set_redefines_variable(
"3": [
{
"result": {
"limit": SERVICE_CALL_LIMIT,
"params": {
"domain": "test",
"service": "script",
@ -4936,7 +4925,6 @@ async def test_continue_on_error(hass: HomeAssistant) -> None:
"1": [
{
"result": {
"limit": 10,
"params": {
"domain": "broken",
"service": "service",
@ -4952,7 +4940,6 @@ async def test_continue_on_error(hass: HomeAssistant) -> None:
{
"error_type": HomeAssistantError,
"result": {
"limit": 10,
"params": {
"domain": "broken",
"service": "service",
@ -5011,7 +4998,6 @@ async def test_continue_on_error_automation_issue(hass: HomeAssistant) -> None:
{
"error_type": ServiceNotFound,
"result": {
"limit": 10,
"params": {
"domain": "service",
"service": "not_found",
@ -5059,7 +5045,6 @@ async def test_continue_on_error_unknown_error(hass: HomeAssistant) -> None:
{
"error_type": MyLibraryError,
"result": {
"limit": 10,
"params": {
"domain": "some",
"service": "service",

View file

@ -957,9 +957,7 @@ async def test_serviceregistry_call_with_blocking_done_in_time(
assert registered_events[0].data["domain"] == "test_domain"
assert registered_events[0].data["service"] == "register_calls"
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
assert len(calls) == 1
@ -981,9 +979,7 @@ async def test_serviceregistry_async_service(hass: HomeAssistant) -> None:
hass.services.async_register("test_domain", "register_calls", service_handler)
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
assert len(calls) == 1
@ -1000,9 +996,7 @@ async def test_serviceregistry_async_service_partial(hass: HomeAssistant) -> Non
)
await hass.async_block_till_done()
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
assert len(calls) == 1
@ -1017,9 +1011,7 @@ async def test_serviceregistry_callback_service(hass: HomeAssistant) -> None:
hass.services.async_register("test_domain", "register_calls", service_handler)
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
assert len(calls) == 1
@ -1063,12 +1055,10 @@ async def test_serviceregistry_async_service_raise_exception(
hass.services.async_register("test_domain", "register_calls", service_handler)
with pytest.raises(ValueError):
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
# Non-blocking service call never throw exception
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=False)
hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=False)
await hass.async_block_till_done()
@ -1085,12 +1075,10 @@ async def test_serviceregistry_callback_service_raise_exception(
hass.services.async_register("test_domain", "register_calls", service_handler)
with pytest.raises(ValueError):
assert await hass.services.async_call(
"test_domain", "REGISTER_CALLS", blocking=True
)
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=True)
# Non-blocking service call never throw exception
await hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=False)
hass.services.async_call("test_domain", "REGISTER_CALLS", blocking=False)
await hass.async_block_till_done()
@ -1359,42 +1347,6 @@ async def test_async_functions_with_callback(hass: HomeAssistant) -> None:
assert len(runs) == 3
@pytest.mark.parametrize("cancel_call", [True, False])
async def test_cancel_service_task(hass: HomeAssistant, cancel_call) -> None:
"""Test cancellation."""
service_called = asyncio.Event()
service_cancelled = False
async def service_handler(call):
nonlocal service_cancelled
service_called.set()
try:
await asyncio.sleep(10)
except asyncio.CancelledError:
service_cancelled = True
raise
hass.services.async_register("test_domain", "test_service", service_handler)
call_task = hass.async_create_task(
hass.services.async_call("test_domain", "test_service", blocking=True)
)
tasks_1 = asyncio.all_tasks()
await asyncio.wait_for(service_called.wait(), timeout=1)
tasks_2 = asyncio.all_tasks() - tasks_1
assert len(tasks_2) == 1
service_task = tasks_2.pop()
if cancel_call:
call_task.cancel()
else:
service_task.cancel()
with pytest.raises(asyncio.CancelledError):
await call_task
assert service_cancelled
def test_valid_entity_id() -> None:
"""Test valid entity ID."""
for invalid in [