diff --git a/homeassistant/package_constraints.txt b/homeassistant/package_constraints.txt index 532bd23428c..dbd749d7ca7 100644 --- a/homeassistant/package_constraints.txt +++ b/homeassistant/package_constraints.txt @@ -98,9 +98,6 @@ hyperframe>=5.2.0 # Ensure we run compatible with musllinux build env numpy==1.23.2 -# pytest_asyncio breaks our test suite. We rely on pytest-aiohttp instead -pytest_asyncio==1000000000.0.0 - # Prevent dependency conflicts between sisyphus-control and aioambient # until upper bounds for sisyphus-control have been updated # https://github.com/jkeljo/sisyphus-control/issues/6 diff --git a/pyproject.toml b/pyproject.toml index a5b6c205c89..710b025bee3 100644 --- a/pyproject.toml +++ b/pyproject.toml @@ -227,3 +227,4 @@ norecursedirs = [ ] log_format = "%(asctime)s.%(msecs)03d %(levelname)-8s %(threadName)s %(name)s:%(filename)s:%(lineno)s %(message)s" log_date_format = "%Y-%m-%d %H:%M:%S" +asyncio_mode = "auto" diff --git a/requirements_test.txt b/requirements_test.txt index 38ea4aa37ab..7db57fb5bcf 100644 --- a/requirements_test.txt +++ b/requirements_test.txt @@ -16,7 +16,8 @@ mypy==0.991 pre-commit==2.20.0 pylint==2.15.6 pipdeptree==2.3.1 -pytest-aiohttp==0.3.0 +pytest-asyncio==0.20.2 +pytest-aiohttp==1.0.4 pytest-cov==3.0.0 pytest-freezegun==0.4.2 pytest-socket==0.5.1 diff --git a/script/gen_requirements_all.py b/script/gen_requirements_all.py index 6d547ab9fed..355caa6cb62 100755 --- a/script/gen_requirements_all.py +++ b/script/gen_requirements_all.py @@ -110,9 +110,6 @@ hyperframe>=5.2.0 # Ensure we run compatible with musllinux build env numpy==1.23.2 -# pytest_asyncio breaks our test suite. We rely on pytest-aiohttp instead -pytest_asyncio==1000000000.0.0 - # Prevent dependency conflicts between sisyphus-control and aioambient # until upper bounds for sisyphus-control have been updated # https://github.com/jkeljo/sisyphus-control/issues/6 diff --git a/tests/auth/test_init.py b/tests/auth/test_init.py index 49c2c776684..f8ba8108f59 100644 --- a/tests/auth/test_init.py +++ b/tests/auth/test_init.py @@ -28,7 +28,7 @@ from tests.common import ( @pytest.fixture -def mock_hass(loop): +def mock_hass(event_loop): """Home Assistant mock with minimum amount of data set to make it work with auth.""" hass = Mock() hass.config.skip_pip = True diff --git a/tests/common.py b/tests/common.py index b7a26cb5f6d..f32dbd11081 100644 --- a/tests/common.py +++ b/tests/common.py @@ -160,7 +160,7 @@ def get_test_home_assistant(): # pylint: disable=protected-access -async def async_test_home_assistant(loop, load_registries=True): +async def async_test_home_assistant(event_loop, load_registries=True): """Return a Home Assistant object pointing at test config dir.""" hass = ha.HomeAssistant() store = auth_store.AuthStore(hass) diff --git a/tests/components/alexa/test_flash_briefings.py b/tests/components/alexa/test_flash_briefings.py index 8b9c91e28b5..499848f01db 100644 --- a/tests/components/alexa/test_flash_briefings.py +++ b/tests/components/alexa/test_flash_briefings.py @@ -21,8 +21,9 @@ NPR_NEWS_MP3_URL = "https://pd.npr.org/anon.npr-mp3/npr/news/newscast.mp3" @pytest.fixture -def alexa_client(loop, hass, hass_client): +def alexa_client(event_loop, hass, hass_client): """Initialize a Home Assistant server for testing this module.""" + loop = event_loop @callback def mock_service(call): diff --git a/tests/components/alexa/test_intent.py b/tests/components/alexa/test_intent.py index 9c71bc32e4d..54708e9d0f0 100644 --- a/tests/components/alexa/test_intent.py +++ b/tests/components/alexa/test_intent.py @@ -27,8 +27,9 @@ NPR_NEWS_MP3_URL = "https://pd.npr.org/anon.npr-mp3/npr/news/newscast.mp3" @pytest.fixture -def alexa_client(loop, hass, hass_client): +def alexa_client(event_loop, hass, hass_client): """Initialize a Home Assistant server for testing this module.""" + loop = event_loop @callback def mock_service(call): diff --git a/tests/components/auth/conftest.py b/tests/components/auth/conftest.py index 867f44d9f15..b7e69a44a0d 100644 --- a/tests/components/auth/conftest.py +++ b/tests/components/auth/conftest.py @@ -3,6 +3,6 @@ import pytest @pytest.fixture -def aiohttp_client(loop, aiohttp_client, socket_enabled): +def aiohttp_client(event_loop, aiohttp_client, socket_enabled): """Return aiohttp_client and allow opening sockets.""" return aiohttp_client diff --git a/tests/components/config/test_init.py b/tests/components/config/test_init.py index 2d5610cadfb..9a54c55ff9e 100644 --- a/tests/components/config/test_init.py +++ b/tests/components/config/test_init.py @@ -2,7 +2,7 @@ from homeassistant.setup import async_setup_component -async def test_config_setup(hass, loop): +async def test_config_setup(hass, event_loop): """Test it sets up hassbian.""" await async_setup_component(hass, "config", {}) assert "config" in hass.config.components diff --git a/tests/components/emulated_hue/test_upnp.py b/tests/components/emulated_hue/test_upnp.py index ce7f013963c..770f636098c 100644 --- a/tests/components/emulated_hue/test_upnp.py +++ b/tests/components/emulated_hue/test_upnp.py @@ -31,7 +31,7 @@ class MockTransport: @pytest.fixture -def aiohttp_client(loop, aiohttp_client, socket_enabled): +def aiohttp_client(event_loop, aiohttp_client, socket_enabled): """Return aiohttp_client and allow opening sockets.""" return aiohttp_client diff --git a/tests/components/emulated_roku/test_binding.py b/tests/components/emulated_roku/test_binding.py index 5afee6f6cc3..8adf1a18f19 100644 --- a/tests/components/emulated_roku/test_binding.py +++ b/tests/components/emulated_roku/test_binding.py @@ -25,7 +25,7 @@ async def test_events_fired_properly(hass): roku_event_handler = None def instantiate( - loop, + event_loop, handler, roku_usn, host_ip, diff --git a/tests/components/energy/test_sensor.py b/tests/components/energy/test_sensor.py index 0108dd1de76..636eb74e4d3 100644 --- a/tests/components/energy/test_sensor.py +++ b/tests/components/energy/test_sensor.py @@ -3,6 +3,7 @@ import copy from datetime import timedelta from unittest.mock import patch +from freezegun import freeze_time import pytest from homeassistant.components.energy import data @@ -41,6 +42,13 @@ async def setup_integration(recorder_mock): return setup_integration +@pytest.fixture(autouse=True) +@freeze_time("2022-04-19 07:53:05") +def frozen_time(): + """Freeze clock for tests.""" + yield + + def get_statistics_for_entity(statistics_results, entity_id): """Get statistics for a certain entity, or None if there is none.""" for statistics_result in statistics_results: diff --git a/tests/components/fido/test_sensor.py b/tests/components/fido/test_sensor.py index 0ab1de94117..13d8515f8f2 100644 --- a/tests/components/fido/test_sensor.py +++ b/tests/components/fido/test_sensor.py @@ -38,7 +38,7 @@ class FidoClientMockError(FidoClientMock): raise PyFidoError("Fake Error") -async def test_fido_sensor(loop, hass): +async def test_fido_sensor(event_loop, hass): """Test the Fido number sensor.""" with patch("homeassistant.components.fido.sensor.FidoClient", new=FidoClientMock): config = { diff --git a/tests/components/frontend/test_init.py b/tests/components/frontend/test_init.py index 661b3ace38a..6bff327d397 100644 --- a/tests/components/frontend/test_init.py +++ b/tests/components/frontend/test_init.py @@ -80,7 +80,7 @@ async def frontend_themes(hass): @pytest.fixture -def aiohttp_client(loop, aiohttp_client, socket_enabled): +def aiohttp_client(event_loop, aiohttp_client, socket_enabled): """Return aiohttp_client and allow opening sockets.""" return aiohttp_client diff --git a/tests/components/geofency/test_init.py b/tests/components/geofency/test_init.py index 9959023e8a6..9aaa356085b 100644 --- a/tests/components/geofency/test_init.py +++ b/tests/components/geofency/test_init.py @@ -117,7 +117,7 @@ def mock_dev_track(mock_device_tracker_conf): @pytest.fixture -async def geofency_client(loop, hass, hass_client_no_auth): +async def geofency_client(event_loop, hass, hass_client_no_auth): """Geofency mock client (unauthenticated).""" assert await async_setup_component( @@ -130,7 +130,7 @@ async def geofency_client(loop, hass, hass_client_no_auth): @pytest.fixture(autouse=True) -async def setup_zones(loop, hass): +async def setup_zones(event_loop, hass): """Set up Zone config in HA.""" assert await async_setup_component( hass, diff --git a/tests/components/google_assistant/test_google_assistant.py b/tests/components/google_assistant/test_google_assistant.py index 3fd35846d7e..97484f31341 100644 --- a/tests/components/google_assistant/test_google_assistant.py +++ b/tests/components/google_assistant/test_google_assistant.py @@ -42,8 +42,9 @@ def auth_header(hass_access_token): @pytest.fixture -def assistant_client(loop, hass, hass_client_no_auth): +def assistant_client(event_loop, hass, hass_client_no_auth): """Create web client for the Google Assistant API.""" + loop = event_loop loop.run_until_complete( setup.async_setup_component( hass, @@ -66,8 +67,10 @@ def assistant_client(loop, hass, hass_client_no_auth): @pytest.fixture -def hass_fixture(loop, hass): +def hass_fixture(event_loop, hass): """Set up a Home Assistant instance for these tests.""" + loop = event_loop + # We need to do this to get access to homeassistant/turn_(on,off) loop.run_until_complete(setup.async_setup_component(hass, core.DOMAIN, {})) diff --git a/tests/components/gpslogger/test_init.py b/tests/components/gpslogger/test_init.py index 4d246cff589..77357065a1a 100644 --- a/tests/components/gpslogger/test_init.py +++ b/tests/components/gpslogger/test_init.py @@ -26,7 +26,7 @@ def mock_dev_track(mock_device_tracker_conf): @pytest.fixture -async def gpslogger_client(loop, hass, hass_client_no_auth): +async def gpslogger_client(event_loop, hass, hass_client_no_auth): """Mock client for GPSLogger (unauthenticated).""" assert await async_setup_component(hass, DOMAIN, {DOMAIN: {}}) @@ -38,7 +38,7 @@ async def gpslogger_client(loop, hass, hass_client_no_auth): @pytest.fixture(autouse=True) -async def setup_zones(loop, hass): +async def setup_zones(event_loop, hass): """Set up Zone config in HA.""" assert await async_setup_component( hass, diff --git a/tests/components/homekit/conftest.py b/tests/components/homekit/conftest.py index b0422a40f72..2800dfb9be7 100644 --- a/tests/components/homekit/conftest.py +++ b/tests/components/homekit/conftest.py @@ -21,7 +21,7 @@ def iid_storage(hass): @pytest.fixture() -def run_driver(hass, loop, iid_storage): +def run_driver(hass, event_loop, iid_storage): """Return a custom AccessoryDriver instance for HomeKit accessory init. This mock does not mock async_stop, so the driver will not be stopped @@ -41,12 +41,12 @@ def run_driver(hass, loop, iid_storage): bridge_name=BRIDGE_NAME, iid_storage=iid_storage, address="127.0.0.1", - loop=loop, + loop=event_loop, ) @pytest.fixture -def hk_driver(hass, loop, iid_storage): +def hk_driver(hass, event_loop, iid_storage): """Return a custom AccessoryDriver instance for HomeKit accessory init.""" with patch("pyhap.accessory_driver.AsyncZeroconf"), patch( "pyhap.accessory_driver.AccessoryEncoder" @@ -65,12 +65,12 @@ def hk_driver(hass, loop, iid_storage): bridge_name=BRIDGE_NAME, iid_storage=iid_storage, address="127.0.0.1", - loop=loop, + loop=event_loop, ) @pytest.fixture -def mock_hap(hass, loop, iid_storage, mock_zeroconf): +def mock_hap(hass, event_loop, iid_storage, mock_zeroconf): """Return a custom AccessoryDriver instance for HomeKit accessory init.""" with patch("pyhap.accessory_driver.AsyncZeroconf"), patch( "pyhap.accessory_driver.AccessoryEncoder" @@ -93,7 +93,7 @@ def mock_hap(hass, loop, iid_storage, mock_zeroconf): bridge_name=BRIDGE_NAME, iid_storage=iid_storage, address="127.0.0.1", - loop=loop, + loop=event_loop, ) diff --git a/tests/components/http/conftest.py b/tests/components/http/conftest.py index c796ec50b51..ed2c78bafd7 100644 --- a/tests/components/http/conftest.py +++ b/tests/components/http/conftest.py @@ -3,6 +3,6 @@ import pytest @pytest.fixture -def aiohttp_client(loop, aiohttp_client, socket_enabled): +def aiohttp_client(event_loop, aiohttp_client, socket_enabled): """Return aiohttp_client and allow opening sockets.""" return aiohttp_client diff --git a/tests/components/http/test_cors.py b/tests/components/http/test_cors.py index 599df194195..8de081c840a 100644 --- a/tests/components/http/test_cors.py +++ b/tests/components/http/test_cors.py @@ -49,12 +49,12 @@ async def mock_handler(request): @pytest.fixture -def client(loop, aiohttp_client): +def client(event_loop, aiohttp_client): """Fixture to set up a web.Application.""" app = web.Application() setup_cors(app, [TRUSTED_ORIGIN]) app["allow_configured_cors"](app.router.add_get("/", mock_handler)) - return loop.run_until_complete(aiohttp_client(app)) + return event_loop.run_until_complete(aiohttp_client(app)) async def test_cors_requests(client): diff --git a/tests/components/image_processing/test_init.py b/tests/components/image_processing/test_init.py index 9953df041ae..37f84fb971f 100644 --- a/tests/components/image_processing/test_init.py +++ b/tests/components/image_processing/test_init.py @@ -15,7 +15,7 @@ from tests.common import assert_setup_component, async_capture_events @pytest.fixture -def aiohttp_unused_port(loop, aiohttp_unused_port, socket_enabled): +def aiohttp_unused_port(event_loop, aiohttp_unused_port, socket_enabled): """Return aiohttp_unused_port and allow opening sockets.""" return aiohttp_unused_port diff --git a/tests/components/litejet/test_trigger.py b/tests/components/litejet/test_trigger.py index 152d11b0c23..86713b51489 100644 --- a/tests/components/litejet/test_trigger.py +++ b/tests/components/litejet/test_trigger.py @@ -113,12 +113,12 @@ async def test_held_more_than_short(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "200"}, + "held_more_than": {"milliseconds": "2000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) - await simulate_time(hass, mock_litejet, timedelta(seconds=0.1)) + await simulate_time(hass, mock_litejet, timedelta(seconds=1)) await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 @@ -130,13 +130,13 @@ async def test_held_more_than_long(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "200"}, + "held_more_than": {"milliseconds": "2000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=0.3)) + await simulate_time(hass, mock_litejet, timedelta(seconds=3)) assert len(calls) == 1 assert calls[0].data["id"] == 0 await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) @@ -150,12 +150,12 @@ async def test_held_less_than_short(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_less_than": {"milliseconds": "200"}, + "held_less_than": {"milliseconds": "2000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) - await simulate_time(hass, mock_litejet, timedelta(seconds=0.1)) + await simulate_time(hass, mock_litejet, timedelta(seconds=1)) assert len(calls) == 0 await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 1 @@ -169,13 +169,13 @@ async def test_held_less_than_long(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_less_than": {"milliseconds": "200"}, + "held_less_than": {"milliseconds": "2000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=0.3)) + await simulate_time(hass, mock_litejet, timedelta(seconds=3)) assert len(calls) == 0 await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 @@ -188,13 +188,13 @@ async def test_held_in_range_short(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "100"}, - "held_less_than": {"milliseconds": "300"}, + "held_more_than": {"milliseconds": "1000"}, + "held_less_than": {"milliseconds": "3000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) - await simulate_time(hass, mock_litejet, timedelta(seconds=0.05)) + await simulate_time(hass, mock_litejet, timedelta(seconds=0.5)) await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 @@ -206,14 +206,14 @@ async def test_held_in_range_just_right(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "100"}, - "held_less_than": {"milliseconds": "300"}, + "held_more_than": {"milliseconds": "1000"}, + "held_less_than": {"milliseconds": "3000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=0.2)) + await simulate_time(hass, mock_litejet, timedelta(seconds=2)) assert len(calls) == 0 await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 1 @@ -227,14 +227,14 @@ async def test_held_in_range_long(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "100"}, - "held_less_than": {"milliseconds": "300"}, + "held_more_than": {"milliseconds": "1000"}, + "held_less_than": {"milliseconds": "3000"}, }, ) await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=0.4)) + await simulate_time(hass, mock_litejet, timedelta(seconds=4)) assert len(calls) == 0 await simulate_release(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 @@ -247,8 +247,8 @@ async def test_reload(hass, calls, mock_litejet): { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "100"}, - "held_less_than": {"milliseconds": "300"}, + "held_more_than": {"milliseconds": "1000"}, + "held_less_than": {"milliseconds": "3000"}, }, ) @@ -260,7 +260,7 @@ async def test_reload(hass, calls, mock_litejet): "trigger": { "platform": "litejet", "number": ENTITY_OTHER_SWITCH_NUMBER, - "held_more_than": {"milliseconds": "1000"}, + "held_more_than": {"milliseconds": "10000"}, }, "action": {"service": "test.automation"}, } @@ -275,7 +275,7 @@ async def test_reload(hass, calls, mock_litejet): await simulate_press(hass, mock_litejet, ENTITY_OTHER_SWITCH_NUMBER) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=0.5)) + await simulate_time(hass, mock_litejet, timedelta(seconds=5)) assert len(calls) == 0 - await simulate_time(hass, mock_litejet, timedelta(seconds=1.25)) + await simulate_time(hass, mock_litejet, timedelta(seconds=12.5)) assert len(calls) == 1 diff --git a/tests/components/locative/test_init.py b/tests/components/locative/test_init.py index 5f608803e4a..a0af04145b0 100644 --- a/tests/components/locative/test_init.py +++ b/tests/components/locative/test_init.py @@ -21,7 +21,7 @@ def mock_dev_track(mock_device_tracker_conf): @pytest.fixture -async def locative_client(loop, hass, hass_client): +async def locative_client(event_loop, hass, hass_client): """Locative mock client.""" assert await async_setup_component(hass, DOMAIN, {DOMAIN: {}}) await hass.async_block_till_done() diff --git a/tests/components/meraki/test_device_tracker.py b/tests/components/meraki/test_device_tracker.py index 47265444105..e95241cbbc7 100644 --- a/tests/components/meraki/test_device_tracker.py +++ b/tests/components/meraki/test_device_tracker.py @@ -15,8 +15,9 @@ from homeassistant.setup import async_setup_component @pytest.fixture -def meraki_client(loop, hass, hass_client): +def meraki_client(event_loop, hass, hass_client): """Meraki mock client.""" + loop = event_loop assert loop.run_until_complete( async_setup_component( hass, diff --git a/tests/components/modbus/test_init.py b/tests/components/modbus/test_init.py index 73b1f9743c2..3b704eff161 100644 --- a/tests/components/modbus/test_init.py +++ b/tests/components/modbus/test_init.py @@ -16,6 +16,7 @@ from datetime import timedelta import logging from unittest import mock +from freezegun.api import FrozenDateTimeFactory from pymodbus.exceptions import ModbusException from pymodbus.pdu import ExceptionResponse, IllegalFunctionRequest import pytest @@ -542,6 +543,7 @@ async def mock_modbus_read_pymodbus_fixture( do_exception, caplog, mock_pymodbus, + freezer: FrozenDateTimeFactory, ): """Load integration modbus using mocked pymodbus.""" caplog.clear() @@ -573,16 +575,13 @@ async def mock_modbus_read_pymodbus_fixture( } ], } - now = dt_util.utcnow() - with mock.patch("homeassistant.helpers.event.dt_util.utcnow", return_value=now): - assert await async_setup_component(hass, DOMAIN, config) is True - await hass.async_block_till_done() + assert await async_setup_component(hass, DOMAIN, config) is True + await hass.async_block_till_done() assert DOMAIN in hass.config.components assert caplog.text == "" - now = now + timedelta(seconds=DEFAULT_SCAN_INTERVAL + 60) - with mock.patch("homeassistant.helpers.event.dt_util.utcnow", return_value=now): - async_fire_time_changed(hass, now) - await hass.async_block_till_done() + freezer.tick(timedelta(seconds=DEFAULT_SCAN_INTERVAL + 60)) + async_fire_time_changed(hass) + await hass.async_block_till_done() yield mock_pymodbus @@ -690,7 +689,7 @@ async def test_pymodbus_connect_fail(hass, caplog, mock_pymodbus): assert ExceptionMessage in caplog.text -async def test_delay(hass, mock_pymodbus): +async def test_delay(hass, mock_pymodbus, freezer: FrozenDateTimeFactory): """Run test for startup delay.""" # the purpose of this test is to test startup delay @@ -720,11 +719,8 @@ async def test_delay(hass, mock_pymodbus): } mock_pymodbus.read_coils.return_value = ReadResult([0x01]) start_time = dt_util.utcnow() - with mock.patch( - "homeassistant.helpers.event.dt_util.utcnow", return_value=start_time - ): - assert await async_setup_component(hass, DOMAIN, config) is True - await hass.async_block_till_done() + assert await async_setup_component(hass, DOMAIN, config) is True + await hass.async_block_till_done() assert hass.states.get(entity_id).state == STATE_UNKNOWN time_sensor_active = start_time + timedelta(seconds=2) @@ -736,19 +732,15 @@ async def test_delay(hass, mock_pymodbus): # This test assumed listeners are always fired at 0 # microseconds which is impossible in production so # we use 999999 microseconds to simulate the real world. - now += timedelta(seconds=1, microseconds=999999) - with mock.patch( - "homeassistant.helpers.event.dt_util.utcnow", - return_value=now, - autospec=True, - ): - async_fire_time_changed(hass, now) - await hass.async_block_till_done() - if now > time_sensor_active: - if now <= time_after_delay: - assert hass.states.get(entity_id).state == STATE_UNAVAILABLE - elif now > time_after_scan: - assert hass.states.get(entity_id).state == STATE_ON + freezer.tick(timedelta(seconds=1, microseconds=999999)) + now = dt_util.utcnow() + async_fire_time_changed(hass, now) + await hass.async_block_till_done() + if now > time_sensor_active: + if now <= time_after_delay: + assert hass.states.get(entity_id).state == STATE_UNAVAILABLE + elif now > time_after_scan: + assert hass.states.get(entity_id).state == STATE_ON @pytest.mark.parametrize( @@ -853,19 +845,20 @@ async def test_write_no_client(hass, mock_modbus): @pytest.mark.parametrize("do_config", [{}]) -async def test_integration_reload(hass, caplog, mock_modbus): +async def test_integration_reload( + hass, caplog, mock_modbus, freezer: FrozenDateTimeFactory +): """Run test for integration reload.""" caplog.set_level(logging.INFO) caplog.clear() yaml_path = get_fixture_path("configuration.yaml", "modbus") - now = dt_util.utcnow() with mock.patch.object(hass_config, "YAML_CONFIG_FILE", yaml_path): await hass.services.async_call(DOMAIN, SERVICE_RELOAD, blocking=True) await hass.async_block_till_done() for i in range(4): - now = now + timedelta(seconds=1) - async_fire_time_changed(hass, now) + freezer.tick(timedelta(seconds=1)) + async_fire_time_changed(hass) await hass.async_block_till_done() assert "Modbus reloading" in caplog.text diff --git a/tests/components/motioneye/test_camera.py b/tests/components/motioneye/test_camera.py index 3e2db3bf897..d70405cd297 100644 --- a/tests/components/motioneye/test_camera.py +++ b/tests/components/motioneye/test_camera.py @@ -62,7 +62,7 @@ from tests.common import async_fire_time_changed @pytest.fixture -def aiohttp_server(loop, aiohttp_server, socket_enabled): +def aiohttp_server(event_loop, aiohttp_server, socket_enabled): """Return aiohttp_server and allow opening sockets.""" return aiohttp_server @@ -218,7 +218,7 @@ async def test_get_still_image_from_camera( ) -> None: """Test getting a still image.""" - image_handler = Mock(return_value="") + image_handler = AsyncMock(return_value="") app = web.Application() app.add_routes( @@ -258,7 +258,7 @@ async def test_get_still_image_from_camera( async def test_get_stream_from_camera(aiohttp_server: Any, hass: HomeAssistant) -> None: """Test getting a stream.""" - stream_handler = Mock(return_value="") + stream_handler = AsyncMock(return_value="") app = web.Application() app.add_routes([web.get("/", stream_handler)]) stream_server = await aiohttp_server(app) @@ -341,7 +341,7 @@ async def test_camera_option_stream_url_template( """Verify camera with a stream URL template option.""" client = create_mock_motioneye_client() - stream_handler = Mock(return_value="") + stream_handler = AsyncMock(return_value="") app = web.Application() app.add_routes([web.get(f"/{TEST_CAMERA_NAME}/{TEST_CAMERA_ID}", stream_handler)]) stream_server = await aiohttp_server(app) @@ -371,7 +371,7 @@ async def test_camera_option_stream_url_template( # the expected exception, then verify the right handler was called. with pytest.raises(HTTPBadGateway): await async_get_mjpeg_stream(hass, Mock(), TEST_CAMERA_ENTITY_ID) - assert stream_handler.called + assert AsyncMock.called assert not client.get_camera_stream_url.called diff --git a/tests/components/nest/conftest.py b/tests/components/nest/conftest.py index 458685cde70..db89063553f 100644 --- a/tests/components/nest/conftest.py +++ b/tests/components/nest/conftest.py @@ -82,7 +82,7 @@ class FakeAuth(AbstractAuth): @pytest.fixture -def aiohttp_client(loop, aiohttp_client, socket_enabled): +def aiohttp_client(event_loop, aiohttp_client, socket_enabled): """Return aiohttp_client and allow opening sockets.""" return aiohttp_client diff --git a/tests/components/nest/test_api.py b/tests/components/nest/test_api.py index 7d88ba1d329..a998a08d0c4 100644 --- a/tests/components/nest/test_api.py +++ b/tests/components/nest/test_api.py @@ -53,7 +53,9 @@ async def test_auth(hass, aioclient_mock): # Prepare to capture credentials for Subscriber captured_creds = None - async def async_new_subscriber(creds, subscription_name, loop, async_callback): + async def async_new_subscriber( + creds, subscription_name, event_loop, async_callback + ): """Capture credentials for tests.""" nonlocal captured_creds captured_creds = creds @@ -112,7 +114,9 @@ async def test_auth_expired_token(hass, aioclient_mock): # Prepare to capture credentials for Subscriber captured_creds = None - async def async_new_subscriber(creds, subscription_name, loop, async_callback): + async def async_new_subscriber( + creds, subscription_name, event_loop, async_callback + ): """Capture credentials for tests.""" nonlocal captured_creds captured_creds = creds diff --git a/tests/components/recorder/test_util.py b/tests/components/recorder/test_util.py index 54f9bb9b9f2..ecdd729a163 100644 --- a/tests/components/recorder/test_util.py +++ b/tests/components/recorder/test_util.py @@ -110,7 +110,7 @@ def test_validate_or_move_away_sqlite_database(hass, tmpdir, caplog): async def test_last_run_was_recently_clean( - loop, async_setup_recorder_instance: SetupRecorderInstanceT, tmp_path + event_loop, async_setup_recorder_instance: SetupRecorderInstanceT, tmp_path ): """Test we can check if the last recorder run was recently clean.""" config = { diff --git a/tests/components/rss_feed_template/test_init.py b/tests/components/rss_feed_template/test_init.py index ffdb4e5ba9a..0ed22ac84fa 100644 --- a/tests/components/rss_feed_template/test_init.py +++ b/tests/components/rss_feed_template/test_init.py @@ -8,8 +8,9 @@ from homeassistant.setup import async_setup_component @pytest.fixture -def mock_http_client(loop, hass, hass_client): +def mock_http_client(event_loop, hass, hass_client): """Set up test fixture.""" + loop = event_loop config = { "rss_feed_template": { "testfeed": { diff --git a/tests/components/skybell/__init__.py b/tests/components/skybell/__init__.py index dd162ed5d80..fc049adcc3d 100644 --- a/tests/components/skybell/__init__.py +++ b/tests/components/skybell/__init__.py @@ -1,7 +1,5 @@ """Tests for the SkyBell integration.""" -from unittest.mock import AsyncMock, patch - from homeassistant.const import CONF_EMAIL, CONF_PASSWORD USERNAME = "user" @@ -12,19 +10,3 @@ CONF_CONFIG_FLOW = { CONF_EMAIL: USERNAME, CONF_PASSWORD: PASSWORD, } - - -def _patch_skybell_devices() -> None: - mocked_skybell = AsyncMock() - mocked_skybell.user_id = USER_ID - return patch( - "homeassistant.components.skybell.config_flow.Skybell.async_get_devices", - return_value=[mocked_skybell], - ) - - -def _patch_skybell() -> None: - return patch( - "homeassistant.components.skybell.config_flow.Skybell.async_send_request", - return_value={"id": USER_ID}, - ) diff --git a/tests/components/skybell/conftest.py b/tests/components/skybell/conftest.py new file mode 100644 index 00000000000..46337f612e1 --- /dev/null +++ b/tests/components/skybell/conftest.py @@ -0,0 +1,25 @@ +"""Test setup for the SkyBell integration.""" + +from unittest.mock import AsyncMock, patch + +from aioskybell import Skybell, SkybellDevice +from pytest import fixture + +from . import USER_ID + + +@fixture(autouse=True) +def skybell_mock(): + """Fixture for our skybell tests.""" + mocked_skybell_device = AsyncMock(spec=SkybellDevice) + + mocked_skybell = AsyncMock(spec=Skybell) + mocked_skybell.async_get_devices.return_value = [mocked_skybell_device] + mocked_skybell.async_send_request.return_value = {"id": USER_ID} + mocked_skybell.user_id = USER_ID + + with patch( + "homeassistant.components.skybell.config_flow.Skybell", + return_value=mocked_skybell, + ), patch("homeassistant.components.skybell.Skybell", return_value=mocked_skybell): + yield mocked_skybell diff --git a/tests/components/skybell/test_config_flow.py b/tests/components/skybell/test_config_flow.py index 9b7afd12c93..318819246a3 100644 --- a/tests/components/skybell/test_config_flow.py +++ b/tests/components/skybell/test_config_flow.py @@ -2,6 +2,7 @@ from unittest.mock import patch from aioskybell import exceptions +from pytest import fixture from homeassistant import config_entries from homeassistant.components.skybell.const import DOMAIN @@ -10,43 +11,39 @@ from homeassistant.const import CONF_PASSWORD, CONF_SOURCE from homeassistant.core import HomeAssistant from homeassistant.data_entry_flow import FlowResultType -from . import ( - CONF_CONFIG_FLOW, - PASSWORD, - USER_ID, - _patch_skybell, - _patch_skybell_devices, -) +from . import CONF_CONFIG_FLOW, PASSWORD, USER_ID from tests.common import MockConfigEntry -def _patch_setup_entry() -> None: - return patch( +@fixture(autouse=True) +def setup_entry() -> None: + """Make sure component doesn't initialize.""" + with patch( "homeassistant.components.skybell.async_setup_entry", return_value=True, - ) + ): + yield async def test_flow_user(hass: HomeAssistant) -> None: """Test that the user step works.""" - with _patch_skybell(), _patch_skybell_devices(), _patch_setup_entry(): - result = await hass.config_entries.flow.async_init( - DOMAIN, context={"source": SOURCE_USER} - ) + result = await hass.config_entries.flow.async_init( + DOMAIN, context={"source": SOURCE_USER} + ) - assert result["type"] == FlowResultType.FORM - assert result["step_id"] == "user" + assert result["type"] == FlowResultType.FORM + assert result["step_id"] == "user" - result = await hass.config_entries.flow.async_configure( - result["flow_id"], - user_input=CONF_CONFIG_FLOW, - ) + result = await hass.config_entries.flow.async_configure( + result["flow_id"], + user_input=CONF_CONFIG_FLOW, + ) - assert result["type"] == FlowResultType.CREATE_ENTRY - assert result["title"] == "user" - assert result["data"] == CONF_CONFIG_FLOW - assert result["result"].unique_id == USER_ID + assert result["type"] == FlowResultType.CREATE_ENTRY + assert result["title"] == "user" + assert result["data"] == CONF_CONFIG_FLOW + assert result["result"].unique_id == USER_ID async def test_flow_user_already_configured(hass: HomeAssistant) -> None: @@ -57,50 +54,48 @@ async def test_flow_user_already_configured(hass: HomeAssistant) -> None: ) entry.add_to_hass(hass) - with _patch_skybell(), _patch_skybell_devices(): - result = await hass.config_entries.flow.async_init( - DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW - ) + result = await hass.config_entries.flow.async_init( + DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW + ) assert result["type"] == FlowResultType.ABORT assert result["reason"] == "already_configured" -async def test_flow_user_cannot_connect(hass: HomeAssistant) -> None: +async def test_flow_user_cannot_connect(hass: HomeAssistant, skybell_mock) -> None: """Test user initialized flow with unreachable server.""" - with _patch_skybell() as skybell_mock: - skybell_mock.side_effect = exceptions.SkybellException(hass) - result = await hass.config_entries.flow.async_init( - DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW - ) - assert result["type"] == FlowResultType.FORM - assert result["step_id"] == "user" - assert result["errors"] == {"base": "cannot_connect"} + skybell_mock.async_initialize.side_effect = exceptions.SkybellException(hass) + result = await hass.config_entries.flow.async_init( + DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW + ) + assert result["type"] == FlowResultType.FORM + assert result["step_id"] == "user" + assert result["errors"] == {"base": "cannot_connect"} -async def test_invalid_credentials(hass: HomeAssistant) -> None: +async def test_invalid_credentials(hass: HomeAssistant, skybell_mock) -> None: """Test that invalid credentials throws an error.""" - with patch("homeassistant.components.skybell.Skybell.async_login") as skybell_mock: - skybell_mock.side_effect = exceptions.SkybellAuthenticationException(hass) - result = await hass.config_entries.flow.async_init( - DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW - ) + skybell_mock.async_initialize.side_effect = ( + exceptions.SkybellAuthenticationException(hass) + ) + result = await hass.config_entries.flow.async_init( + DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW + ) - assert result["type"] == FlowResultType.FORM - assert result["step_id"] == "user" - assert result["errors"] == {"base": "invalid_auth"} + assert result["type"] == FlowResultType.FORM + assert result["step_id"] == "user" + assert result["errors"] == {"base": "invalid_auth"} -async def test_flow_user_unknown_error(hass: HomeAssistant) -> None: +async def test_flow_user_unknown_error(hass: HomeAssistant, skybell_mock) -> None: """Test user initialized flow with unreachable server.""" - with _patch_skybell_devices() as skybell_mock: - skybell_mock.side_effect = Exception - result = await hass.config_entries.flow.async_init( - DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW - ) - assert result["type"] == FlowResultType.FORM - assert result["step_id"] == "user" - assert result["errors"] == {"base": "unknown"} + skybell_mock.async_initialize.side_effect = Exception + result = await hass.config_entries.flow.async_init( + DOMAIN, context={"source": SOURCE_USER}, data=CONF_CONFIG_FLOW + ) + assert result["type"] == FlowResultType.FORM + assert result["step_id"] == "user" + assert result["errors"] == {"base": "unknown"} async def test_step_reauth(hass: HomeAssistant) -> None: @@ -121,17 +116,15 @@ async def test_step_reauth(hass: HomeAssistant) -> None: assert result["type"] == FlowResultType.FORM assert result["step_id"] == "reauth_confirm" - with _patch_skybell(), _patch_skybell_devices(), _patch_setup_entry(): - - result = await hass.config_entries.flow.async_configure( - result["flow_id"], - user_input={CONF_PASSWORD: PASSWORD}, - ) - assert result["type"] == FlowResultType.ABORT - assert result["reason"] == "reauth_successful" + result = await hass.config_entries.flow.async_configure( + result["flow_id"], + user_input={CONF_PASSWORD: PASSWORD}, + ) + assert result["type"] == FlowResultType.ABORT + assert result["reason"] == "reauth_successful" -async def test_step_reauth_failed(hass: HomeAssistant) -> None: +async def test_step_reauth_failed(hass: HomeAssistant, skybell_mock) -> None: """Test the reauth flow fails and recovers.""" entry = MockConfigEntry(domain=DOMAIN, unique_id=USER_ID, data=CONF_CONFIG_FLOW) entry.add_to_hass(hass) @@ -149,21 +142,22 @@ async def test_step_reauth_failed(hass: HomeAssistant) -> None: assert result["type"] == FlowResultType.FORM assert result["step_id"] == "reauth_confirm" - with patch("homeassistant.components.skybell.Skybell.async_login") as skybell_mock: - skybell_mock.side_effect = exceptions.SkybellAuthenticationException(hass) - result = await hass.config_entries.flow.async_configure( - result["flow_id"], - user_input={CONF_PASSWORD: PASSWORD}, - ) + skybell_mock.async_initialize.side_effect = ( + exceptions.SkybellAuthenticationException(hass) + ) + result = await hass.config_entries.flow.async_configure( + result["flow_id"], + user_input={CONF_PASSWORD: PASSWORD}, + ) - assert result["type"] == FlowResultType.FORM - assert result["errors"] == {"base": "invalid_auth"} + assert result["type"] == FlowResultType.FORM + assert result["errors"] == {"base": "invalid_auth"} - with _patch_skybell(), _patch_skybell_devices(), _patch_setup_entry(): + skybell_mock.async_initialize.side_effect = None - result = await hass.config_entries.flow.async_configure( - result["flow_id"], - user_input={CONF_PASSWORD: PASSWORD}, - ) - assert result["type"] == FlowResultType.ABORT - assert result["reason"] == "reauth_successful" + result = await hass.config_entries.flow.async_configure( + result["flow_id"], + user_input={CONF_PASSWORD: PASSWORD}, + ) + assert result["type"] == FlowResultType.ABORT + assert result["reason"] == "reauth_successful" diff --git a/tests/components/traccar/test_init.py b/tests/components/traccar/test_init.py index 830670efc11..4c6c235a3aa 100644 --- a/tests/components/traccar/test_init.py +++ b/tests/components/traccar/test_init.py @@ -24,7 +24,7 @@ def mock_dev_track(mock_device_tracker_conf): @pytest.fixture(name="client") -async def traccar_client(loop, hass, hass_client_no_auth): +async def traccar_client(event_loop, hass, hass_client_no_auth): """Mock client for Traccar (unauthenticated).""" assert await async_setup_component(hass, DOMAIN, {DOMAIN: {}}) @@ -36,7 +36,7 @@ async def traccar_client(loop, hass, hass_client_no_auth): @pytest.fixture(autouse=True) -async def setup_zones(loop, hass): +async def setup_zones(event_loop, hass): """Set up Zone config in HA.""" assert await async_setup_component( hass, diff --git a/tests/conftest.py b/tests/conftest.py index b6638968182..4dc988db8fc 100644 --- a/tests/conftest.py +++ b/tests/conftest.py @@ -5,6 +5,7 @@ import asyncio from collections.abc import AsyncGenerator, Callable, Generator from contextlib import asynccontextmanager import functools +import gc import itertools from json import JSONDecoder, loads import logging @@ -13,6 +14,7 @@ import ssl import threading from typing import Any from unittest.mock import AsyncMock, MagicMock, Mock, patch +import warnings from aiohttp import client from aiohttp.pytest_plugin import AiohttpClient @@ -188,12 +190,14 @@ util.get_local_ip = lambda: "127.0.0.1" @pytest.fixture(autouse=True) -def verify_cleanup(): +def verify_cleanup(event_loop: asyncio.AbstractEventLoop): """Verify that the test has cleaned up resources correctly.""" threads_before = frozenset(threading.enumerate()) - + tasks_before = asyncio.all_tasks(event_loop) yield + event_loop.run_until_complete(event_loop.shutdown_default_executor()) + if len(INSTANCES) >= 2: count = len(INSTANCES) for inst in INSTANCES: @@ -204,6 +208,26 @@ def verify_cleanup(): for thread in threads: assert isinstance(thread, threading._DummyThread) + # Warn and clean-up lingering tasks and timers + # before moving on to the next test. + tasks = asyncio.all_tasks(event_loop) - tasks_before + for task in tasks: + warnings.warn(f"Linger task after test {task}") + task.cancel() + if tasks: + event_loop.run_until_complete(asyncio.wait(tasks)) + + for handle in event_loop._scheduled: # pylint: disable=protected-access + if not handle.cancelled(): + warnings.warn(f"Lingering timer after test {handle}") + handle.cancel() + + # Make sure garbage collect run in same test as allocation + # this is to mimic the behavior of pytest-aiohttp, and is + # required to avoid warnings from spilling over into next + # test case. + gc.collect() + @pytest.fixture(autouse=True) def bcrypt_cost(): @@ -278,7 +302,7 @@ def aiohttp_client_cls(): @pytest.fixture def aiohttp_client( - loop: asyncio.AbstractEventLoop, + event_loop: asyncio.AbstractEventLoop, ) -> Generator[AiohttpClient, None, None]: """Override the default aiohttp_client since 3.x does not support aiohttp_client_cls. @@ -289,6 +313,7 @@ def aiohttp_client( aiohttp_client(server, **kwargs) aiohttp_client(raw_server, **kwargs) """ + loop = event_loop clients = [] async def go( @@ -335,9 +360,10 @@ def hass_fixture_setup(): @pytest.fixture -def hass(hass_fixture_setup, loop, load_registries, hass_storage, request): +def hass(hass_fixture_setup, event_loop, load_registries, hass_storage, request): """Fixture to provide a test instance of Home Assistant.""" + loop = event_loop hass_fixture_setup.append(True) orig_tz = dt_util.DEFAULT_TIME_ZONE @@ -382,7 +408,7 @@ def hass(hass_fixture_setup, loop, load_registries, hass_storage, request): @pytest.fixture -async def stop_hass(): +async def stop_hass(event_loop): """Make sure all hass are stopped.""" orig_hass = ha.HomeAssistant @@ -403,6 +429,7 @@ async def stop_hass(): with patch.object(hass_inst.loop, "stop"): await hass_inst.async_block_till_done() await hass_inst.async_stop(force=True) + await event_loop.shutdown_default_executor() @pytest.fixture diff --git a/tests/helpers/test_script.py b/tests/helpers/test_script.py index 519498f2e08..a5f3cc0cc91 100644 --- a/tests/helpers/test_script.py +++ b/tests/helpers/test_script.py @@ -8,7 +8,7 @@ import logging import operator from types import MappingProxyType from unittest import mock -from unittest.mock import AsyncMock, patch +from unittest.mock import AsyncMock, MagicMock, patch from async_timeout import timeout import pytest @@ -1734,6 +1734,7 @@ async def test_condition_created_once(async_from_config, hass): ) async_from_config.reset_mock() + async_from_config.return_value = MagicMock() hass.states.async_set("test.entity", "hello") await script_obj.async_run(context=Context()) diff --git a/tests/scripts/test_auth.py b/tests/scripts/test_auth.py index 3ab19450879..a5478d149ec 100644 --- a/tests/scripts/test_auth.py +++ b/tests/scripts/test_auth.py @@ -108,7 +108,7 @@ async def test_change_password_invalid_user(hass, provider, capsys, hass_storage data.validate_login("invalid-user", "new-pass") -def test_parsing_args(loop): +def test_parsing_args(event_loop): """Test we parse args correctly.""" called = False diff --git a/tests/scripts/test_check_config.py b/tests/scripts/test_check_config.py index 05ebb8fb0e5..fc35b28f7c9 100644 --- a/tests/scripts/test_check_config.py +++ b/tests/scripts/test_check_config.py @@ -43,7 +43,7 @@ def normalize_yaml_files(check_dict): return [key.replace(root, "...") for key in sorted(check_dict["yaml_files"].keys())] -def test_bad_core_config(mock_is_file, loop): +def test_bad_core_config(mock_is_file, event_loop): """Test a bad core config setup.""" files = {YAML_CONFIG_FILE: BAD_CORE_CONFIG} with patch_yaml_files(files): @@ -52,7 +52,7 @@ def test_bad_core_config(mock_is_file, loop): assert res["except"]["homeassistant"][1] == {"unit_system": "bad"} -def test_config_platform_valid(mock_is_file, loop): +def test_config_platform_valid(mock_is_file, event_loop): """Test a valid platform setup.""" files = {YAML_CONFIG_FILE: BASE_CONFIG + "light:\n platform: demo"} with patch_yaml_files(files): @@ -65,7 +65,7 @@ def test_config_platform_valid(mock_is_file, loop): assert len(res["yaml_files"]) == 1 -def test_component_platform_not_found(mock_is_file, loop): +def test_component_platform_not_found(mock_is_file, event_loop): """Test errors if component or platform not found.""" # Make sure they don't exist files = {YAML_CONFIG_FILE: BASE_CONFIG + "beer:"} @@ -96,7 +96,7 @@ def test_component_platform_not_found(mock_is_file, loop): assert len(res["yaml_files"]) == 1 -def test_secrets(mock_is_file, loop): +def test_secrets(mock_is_file, event_loop): """Test secrets config checking method.""" secrets_path = get_test_config_dir("secrets.yaml") @@ -127,7 +127,7 @@ def test_secrets(mock_is_file, loop): ] -def test_package_invalid(mock_is_file, loop): +def test_package_invalid(mock_is_file, event_loop): """Test an invalid package.""" files = { YAML_CONFIG_FILE: BASE_CONFIG + (" packages:\n p1:\n" ' group: ["a"]') @@ -145,7 +145,7 @@ def test_package_invalid(mock_is_file, loop): assert len(res["yaml_files"]) == 1 -def test_bootstrap_error(loop): +def test_bootstrap_error(event_loop): """Test a valid platform setup.""" files = {YAML_CONFIG_FILE: BASE_CONFIG + "automation: !include no.yaml"} with patch_yaml_files(files): diff --git a/tests/test_bootstrap.py b/tests/test_bootstrap.py index e51f4d315ee..c8365c86a9a 100644 --- a/tests/test_bootstrap.py +++ b/tests/test_bootstrap.py @@ -460,7 +460,7 @@ async def test_setup_hass( mock_ensure_config_exists, mock_process_ha_config_upgrade, caplog, - loop, + event_loop, ): """Test it works.""" verbose = Mock() @@ -511,7 +511,7 @@ async def test_setup_hass_takes_longer_than_log_slow_startup( mock_ensure_config_exists, mock_process_ha_config_upgrade, caplog, - loop, + event_loop, ): """Test it works.""" verbose = Mock() @@ -553,7 +553,7 @@ async def test_setup_hass_invalid_yaml( mock_mount_local_lib_path, mock_ensure_config_exists, mock_process_ha_config_upgrade, - loop, + event_loop, ): """Test it works.""" with patch( @@ -581,7 +581,7 @@ async def test_setup_hass_config_dir_nonexistent( mock_mount_local_lib_path, mock_ensure_config_exists, mock_process_ha_config_upgrade, - loop, + event_loop, ): """Test it works.""" mock_ensure_config_exists.return_value = False @@ -608,7 +608,7 @@ async def test_setup_hass_safe_mode( mock_mount_local_lib_path, mock_ensure_config_exists, mock_process_ha_config_upgrade, - loop, + event_loop, ): """Test it works.""" with patch("homeassistant.components.browser.setup") as browser_setup, patch( @@ -641,7 +641,7 @@ async def test_setup_hass_invalid_core_config( mock_mount_local_lib_path, mock_ensure_config_exists, mock_process_ha_config_upgrade, - loop, + event_loop, ): """Test it works.""" with patch( @@ -669,7 +669,7 @@ async def test_setup_safe_mode_if_no_frontend( mock_mount_local_lib_path, mock_ensure_config_exists, mock_process_ha_config_upgrade, - loop, + event_loop, ): """Test we setup safe mode if frontend didn't load.""" verbose = Mock() diff --git a/tests/test_core.py b/tests/test_core.py index 80f7c18d254..c5f153ad3bd 100644 --- a/tests/test_core.py +++ b/tests/test_core.py @@ -87,9 +87,9 @@ def test_async_add_hass_job_schedule_partial_callback(): assert len(hass.add_job.mock_calls) == 0 -def test_async_add_hass_job_schedule_coroutinefunction(loop): +def test_async_add_hass_job_schedule_coroutinefunction(event_loop): """Test that we schedule coroutines and add jobs to the job pool.""" - hass = MagicMock(loop=MagicMock(wraps=loop)) + hass = MagicMock(loop=MagicMock(wraps=event_loop)) async def job(): pass @@ -100,9 +100,9 @@ def test_async_add_hass_job_schedule_coroutinefunction(loop): assert len(hass.add_job.mock_calls) == 0 -def test_async_add_hass_job_schedule_partial_coroutinefunction(loop): +def test_async_add_hass_job_schedule_partial_coroutinefunction(event_loop): """Test that we schedule partial coros and add jobs to the job pool.""" - hass = MagicMock(loop=MagicMock(wraps=loop)) + hass = MagicMock(loop=MagicMock(wraps=event_loop)) async def job(): pass @@ -128,9 +128,9 @@ def test_async_add_job_add_hass_threaded_job_to_pool(): assert len(hass.loop.run_in_executor.mock_calls) == 1 -def test_async_create_task_schedule_coroutine(loop): +def test_async_create_task_schedule_coroutine(event_loop): """Test that we schedule coroutines and add jobs to the job pool.""" - hass = MagicMock(loop=MagicMock(wraps=loop)) + hass = MagicMock(loop=MagicMock(wraps=event_loop)) async def job(): pass @@ -1079,7 +1079,7 @@ async def test_bad_timezone_raises_value_error(hass): await hass.config.async_update(time_zone="not_a_timezone") -async def test_start_taking_too_long(loop, caplog): +async def test_start_taking_too_long(event_loop, caplog): """Test when async_start takes too long.""" hass = ha.HomeAssistant() caplog.set_level(logging.WARNING) @@ -1098,7 +1098,7 @@ async def test_start_taking_too_long(loop, caplog): assert hass.state == ha.CoreState.stopped -async def test_track_task_functions(loop): +async def test_track_task_functions(event_loop): """Test function to start/stop track task and initial state.""" hass = ha.HomeAssistant() try: diff --git a/tests/util/test_location.py b/tests/util/test_location.py index d8d86965733..51cd8d4388f 100644 --- a/tests/util/test_location.py +++ b/tests/util/test_location.py @@ -32,7 +32,7 @@ async def session(hass): @pytest.fixture -async def raising_session(loop): +async def raising_session(event_loop): """Return an aioclient session that only fails.""" return Mock(get=Mock(side_effect=aiohttp.ClientError))