diff --git a/custom_components/bmw_connected_drive/__init__.py b/custom_components/bmw_connected_drive/__init__.py index 595eba7..77e5dbf 100644 --- a/custom_components/bmw_connected_drive/__init__.py +++ b/custom_components/bmw_connected_drive/__init__.py @@ -98,9 +98,6 @@ async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: ) ) - # Add event listener for option flow changes - entry.async_on_unload(entry.add_update_listener(async_update_options)) - return True @@ -116,11 +113,6 @@ async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool: return unload_ok -async def async_update_options(hass: HomeAssistant, config_entry: ConfigEntry) -> None: - """Handle options update.""" - await hass.config_entries.async_reload(config_entry.entry_id) - - class BMWBaseEntity(CoordinatorEntity[BMWDataUpdateCoordinator]): """Common base for BMW entities.""" diff --git a/custom_components/bmw_connected_drive/config_flow.py b/custom_components/bmw_connected_drive/config_flow.py index 37ceb23..c07be4c 100644 --- a/custom_components/bmw_connected_drive/config_flow.py +++ b/custom_components/bmw_connected_drive/config_flow.py @@ -104,6 +104,16 @@ async def async_step_account_options( ) -> FlowResult: """Handle the initial step.""" if user_input is not None: + # Manually update & reload the config entry after options change. + # Required as each successful login will store the latest refresh_token + # using async_update_entry, which would otherwise trigger a full reload + # if the options would be refreshed using a listener. + changed = self.hass.config_entries.async_update_entry( + self.config_entry, + options=user_input, + ) + if changed: + await self.hass.config_entries.async_reload(self.config_entry.entry_id) return self.async_create_entry(title="", data=user_input) return self.async_show_form( step_id="account_options", diff --git a/custom_components/bmw_connected_drive/coordinator.py b/custom_components/bmw_connected_drive/coordinator.py index 3733544..401ec76 100644 --- a/custom_components/bmw_connected_drive/coordinator.py +++ b/custom_components/bmw_connected_drive/coordinator.py @@ -3,7 +3,6 @@ from datetime import timedelta import logging -from types import MappingProxyType import async_timeout from bimmer_connected.account import MyBMWAccount @@ -61,6 +60,11 @@ async def _async_update_data(self) -> None: if self.account.refresh_token != old_refresh_token: self._update_config_entry_refresh_token(self.account.refresh_token) + _LOGGER.debug( + "bimmer_connected: refresh token %s > %s", + old_refresh_token, + self.account.refresh_token, + ) def _update_config_entry_refresh_token(self, refresh_token: str | None) -> None: """Update or delete the refresh_token in the Config Entry.""" @@ -70,8 +74,7 @@ def _update_config_entry_refresh_token(self, refresh_token: str | None) -> None: } if not refresh_token: data.pop(CONF_REFRESH_TOKEN) - self._entry.data = MappingProxyType(data) - self.hass.config_entries._async_schedule_save() # pylint: disable=protected-access + self.hass.config_entries.async_update_entry(self._entry, data=data) def notify_listeners(self) -> None: """Notify all listeners to refresh HA state machine."""