Add test to ensure bootstrap continues if an integraton raises CancelledError (#112472)

This commit is contained in:
J. Nick Koston 2024-03-05 19:34:16 -10:00 committed by GitHub
parent eef661c917
commit 87739bc072
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194
6 changed files with 103 additions and 0 deletions

View File

@ -1067,3 +1067,48 @@ async def test_bootstrap_does_not_preload_stage_1_integrations() -> None:
# as a side effect of importing the pre-imports
for integration in bootstrap.STAGE_1_INTEGRATIONS:
assert f"homeassistant.components.{integration}" not in decoded_stdout
@pytest.mark.parametrize("load_registries", [False])
async def test_cancellation_does_not_leak_upward_from_async_setup(
hass: HomeAssistant,
caplog: pytest.LogCaptureFixture,
enable_custom_integrations: None,
) -> None:
"""Test setting up an integration that raises asyncio.CancelledError."""
await bootstrap.async_setup_multi_components(
hass, {"test_package_raises_cancelled_error"}, {}
)
await hass.async_block_till_done()
assert (
"Error during setup of component test_package_raises_cancelled_error"
in caplog.text
)
@pytest.mark.parametrize("load_registries", [False])
async def test_cancellation_does_not_leak_upward_from_async_setup_entry(
hass: HomeAssistant,
caplog: pytest.LogCaptureFixture,
enable_custom_integrations: None,
) -> None:
"""Test setting up an integration that raises asyncio.CancelledError."""
entry = MockConfigEntry(
domain="test_package_raises_cancelled_error_config_entry", data={}
)
entry.add_to_hass(hass)
await bootstrap.async_setup_multi_components(
hass, {"test_package_raises_cancelled_error_config_entry"}, {}
)
await hass.async_block_till_done()
await bootstrap.async_setup_multi_components(hass, {"test_package"}, {})
await hass.async_block_till_done()
assert (
"Error setting up entry Mock Title for test_package_raises_cancelled_error_config_entry"
in caplog.text
)
assert "test_package" in hass.config.components
assert "test_package_raises_cancelled_error_config_entry" in hass.config.components

View File

@ -0,0 +1,8 @@
"""Provide a mock package component."""
import asyncio
async def async_setup(hass, config):
"""Mock a successful setup."""
asyncio.current_task().cancel()
await asyncio.sleep(0)

View File

@ -0,0 +1,10 @@
{
"domain": "test_package_raises_cancelled_error",
"name": "Test Package that raises asyncio.CancelledError",
"documentation": "http://test-package.io",
"requirements": [],
"dependencies": [],
"codeowners": [],
"config_flow": false,
"version": "1.2.3"
}

View File

@ -0,0 +1,13 @@
"""Provide a mock package component."""
import asyncio
async def async_setup(hass, config):
"""Mock a successful setup."""
return True
async def async_setup_entry(hass, entry):
"""Mock an unsuccessful entry setup."""
asyncio.current_task().cancel()
await asyncio.sleep(0)

View File

@ -0,0 +1,17 @@
"""Config flow."""
from homeassistant.config_entries import ConfigFlow
from homeassistant.core import HomeAssistant
class MockConfigFlow(
ConfigFlow, domain="test_package_raises_cancelled_error_config_entry"
):
"""Mock config flow."""
pass
async def _async_has_devices(hass: HomeAssistant) -> bool:
"""Return if there are devices that can be discovered."""
return True

View File

@ -0,0 +1,10 @@
{
"domain": "test_package_raises_cancelled_error_config_entry",
"name": "Test Package that raises asyncio.CancelledError in async_setup_entry",
"documentation": "http://test-package.io",
"requirements": [],
"dependencies": [],
"codeowners": [],
"config_flow": true,
"version": "1.2.3"
}