From 63f3c2396876d301e7fbdfdf4020603535b3fa02 Mon Sep 17 00:00:00 2001 From: "J. Nick Koston" Date: Sat, 23 Dec 2023 14:28:08 -1000 Subject: [PATCH] Add support for attribute caching to the weather platform (#106334) --- homeassistant/components/weather/__init__.py | 67 ++++++++++++++------ 1 file changed, 48 insertions(+), 19 deletions(-) diff --git a/homeassistant/components/weather/__init__.py b/homeassistant/components/weather/__init__.py index 993c5e9503b..fa832ca8c32 100644 --- a/homeassistant/components/weather/__init__.py +++ b/homeassistant/components/weather/__init__.py @@ -9,6 +9,7 @@ from datetime import timedelta from functools import partial import logging from typing import ( + TYPE_CHECKING, Any, Final, Generic, @@ -84,6 +85,12 @@ from .const import ( # noqa: F401 ) from .websocket_api import async_setup as async_setup_ws_api +if TYPE_CHECKING: + from functools import cached_property +else: + from homeassistant.backports.functools import cached_property + + _LOGGER = logging.getLogger(__name__) ATTR_CONDITION_CLASS = "condition_class" @@ -272,7 +279,29 @@ class PostInit(metaclass=PostInitMeta): """Finish initializing.""" -class WeatherEntity(Entity, PostInit): +CACHED_PROPERTIES_WITH_ATTR_ = { + "native_apparent_temperature", + "native_temperature", + "native_temperature_unit", + "native_dew_point", + "native_pressure", + "native_pressure_unit", + "humidity", + "native_wind_gust_speed", + "native_wind_speed", + "native_wind_speed_unit", + "wind_bearing", + "ozone", + "cloud_coverage", + "uv_index", + "native_visibility", + "native_visibility_unit", + "native_precipitation_unit", + "condition", +} + + +class WeatherEntity(Entity, PostInit, cached_properties=CACHED_PROPERTIES_WITH_ATTR_): """ABC for weather data.""" _entity_component_unrecorded_attributes = frozenset({ATTR_FORECAST}) @@ -398,22 +427,22 @@ class WeatherEntity(Entity, PostInit): return self.async_registry_entry_updated() - @property + @cached_property def native_apparent_temperature(self) -> float | None: """Return the apparent temperature in native units.""" return self._attr_native_temperature - @property + @cached_property def native_temperature(self) -> float | None: """Return the temperature in native units.""" return self._attr_native_temperature - @property + @cached_property def native_temperature_unit(self) -> str | None: """Return the native unit of measurement for temperature.""" return self._attr_native_temperature_unit - @property + @cached_property def native_dew_point(self) -> float | None: """Return the dew point temperature in native units.""" return self._attr_native_dew_point @@ -441,12 +470,12 @@ class WeatherEntity(Entity, PostInit): return self._default_temperature_unit - @property + @cached_property def native_pressure(self) -> float | None: """Return the pressure in native units.""" return self._attr_native_pressure - @property + @cached_property def native_pressure_unit(self) -> str | None: """Return the native unit of measurement for pressure.""" return self._attr_native_pressure_unit @@ -476,22 +505,22 @@ class WeatherEntity(Entity, PostInit): return self._default_pressure_unit - @property + @cached_property def humidity(self) -> float | None: """Return the humidity in native units.""" return self._attr_humidity - @property + @cached_property def native_wind_gust_speed(self) -> float | None: """Return the wind gust speed in native units.""" return self._attr_native_wind_gust_speed - @property + @cached_property def native_wind_speed(self) -> float | None: """Return the wind speed in native units.""" return self._attr_native_wind_speed - @property + @cached_property def native_wind_speed_unit(self) -> str | None: """Return the native unit of measurement for wind speed.""" return self._attr_native_wind_speed_unit @@ -521,32 +550,32 @@ class WeatherEntity(Entity, PostInit): return self._default_wind_speed_unit - @property + @cached_property def wind_bearing(self) -> float | str | None: """Return the wind bearing.""" return self._attr_wind_bearing - @property + @cached_property def ozone(self) -> float | None: """Return the ozone level.""" return self._attr_ozone - @property + @cached_property def cloud_coverage(self) -> float | None: """Return the Cloud coverage in %.""" return self._attr_cloud_coverage - @property + @cached_property def uv_index(self) -> float | None: """Return the UV index.""" return self._attr_uv_index - @property + @cached_property def native_visibility(self) -> float | None: """Return the visibility in native units.""" return self._attr_native_visibility - @property + @cached_property def native_visibility_unit(self) -> str | None: """Return the native unit of measurement for visibility.""" return self._attr_native_visibility_unit @@ -603,7 +632,7 @@ class WeatherEntity(Entity, PostInit): """Return the hourly forecast in native units.""" raise NotImplementedError - @property + @cached_property def native_precipitation_unit(self) -> str | None: """Return the native unit of measurement for accumulated precipitation.""" return self._attr_native_precipitation_unit @@ -970,7 +999,7 @@ class WeatherEntity(Entity, PostInit): """Return the current state.""" return self.condition - @property + @cached_property def condition(self) -> str | None: """Return the current condition.""" return self._attr_condition