Reload ZHA only a single time when the connection is lost multiple times (#107963)
* Reload only a single time when the connection is lost multiple times * Ignore when reset task finishes, allow only one reset per `ZHAGateway`
This commit is contained in:
parent
20b88e30f5
commit
8a3eb149b7
2 changed files with 43 additions and 2 deletions
|
@ -142,7 +142,9 @@ class ZHAGateway:
|
|||
self._log_relay_handler = LogRelayHandler(hass, self)
|
||||
self.config_entry = config_entry
|
||||
self._unsubs: list[Callable[[], None]] = []
|
||||
|
||||
self.shutting_down = False
|
||||
self._reload_task: asyncio.Task | None = None
|
||||
|
||||
def get_application_controller_data(self) -> tuple[ControllerApplication, dict]:
|
||||
"""Get an uninitialized instance of a zigpy `ControllerApplication`."""
|
||||
|
@ -231,12 +233,17 @@ class ZHAGateway:
|
|||
|
||||
def connection_lost(self, exc: Exception) -> None:
|
||||
"""Handle connection lost event."""
|
||||
_LOGGER.debug("Connection to the radio was lost: %r", exc)
|
||||
|
||||
if self.shutting_down:
|
||||
return
|
||||
|
||||
_LOGGER.debug("Connection to the radio was lost: %r", exc)
|
||||
# Ensure we do not queue up multiple resets
|
||||
if self._reload_task is not None:
|
||||
_LOGGER.debug("Ignoring reset, one is already running")
|
||||
return
|
||||
|
||||
self.hass.async_create_task(
|
||||
self._reload_task = self.hass.async_create_task(
|
||||
self.hass.config_entries.async_reload(self.config_entry.entry_id)
|
||||
)
|
||||
|
||||
|
@ -760,6 +767,10 @@ class ZHAGateway:
|
|||
|
||||
async def shutdown(self) -> None:
|
||||
"""Stop ZHA Controller Application."""
|
||||
if self.shutting_down:
|
||||
_LOGGER.debug("Ignoring duplicate shutdown event")
|
||||
return
|
||||
|
||||
_LOGGER.debug("Shutting down ZHA ControllerApplication")
|
||||
self.shutting_down = True
|
||||
|
||||
|
|
|
@ -291,3 +291,33 @@ async def test_gateway_force_multi_pan_channel(
|
|||
|
||||
_, config = zha_gateway.get_application_controller_data()
|
||||
assert config["network"]["channel"] == expected_channel
|
||||
|
||||
|
||||
async def test_single_reload_on_multiple_connection_loss(
|
||||
hass: HomeAssistant,
|
||||
zigpy_app_controller: ControllerApplication,
|
||||
config_entry: MockConfigEntry,
|
||||
):
|
||||
"""Test that we only reload once when we lose the connection multiple times."""
|
||||
config_entry.add_to_hass(hass)
|
||||
|
||||
zha_gateway = ZHAGateway(hass, {}, config_entry)
|
||||
|
||||
with patch(
|
||||
"bellows.zigbee.application.ControllerApplication.new",
|
||||
return_value=zigpy_app_controller,
|
||||
):
|
||||
await zha_gateway.async_initialize()
|
||||
|
||||
with patch.object(
|
||||
hass.config_entries, "async_reload", wraps=hass.config_entries.async_reload
|
||||
) as mock_reload:
|
||||
zha_gateway.connection_lost(RuntimeError())
|
||||
zha_gateway.connection_lost(RuntimeError())
|
||||
zha_gateway.connection_lost(RuntimeError())
|
||||
zha_gateway.connection_lost(RuntimeError())
|
||||
zha_gateway.connection_lost(RuntimeError())
|
||||
|
||||
assert len(mock_reload.mock_calls) == 1
|
||||
|
||||
await hass.async_block_till_done()
|
||||
|
|
Loading…
Add table
Reference in a new issue