diff --git a/homeassistant/components/aemet/const.py b/homeassistant/components/aemet/const.py index 4be90011f5a..645c1ad0ea2 100644 --- a/homeassistant/components/aemet/const.py +++ b/homeassistant/components/aemet/const.py @@ -17,14 +17,6 @@ from homeassistant.components.weather import ( ATTR_CONDITION_RAINY, ATTR_CONDITION_SNOWY, ATTR_CONDITION_SUNNY, - ATTR_FORECAST_CONDITION, - ATTR_FORECAST_PRECIPITATION, - ATTR_FORECAST_PRECIPITATION_PROBABILITY, - ATTR_FORECAST_TEMP, - ATTR_FORECAST_TEMP_LOW, - ATTR_FORECAST_TIME, - ATTR_FORECAST_WIND_BEARING, - ATTR_FORECAST_WIND_SPEED, ) from homeassistant.const import ( DEGREE, @@ -45,8 +37,16 @@ ENTRY_NAME = "name" ENTRY_WEATHER_COORDINATOR = "weather_coordinator" ATTR_API_CONDITION = "condition" +ATTR_API_FORECAST_CONDITION = "condition" ATTR_API_FORECAST_DAILY = "forecast-daily" ATTR_API_FORECAST_HOURLY = "forecast-hourly" +ATTR_API_FORECAST_PRECIPITATION = "precipitation" +ATTR_API_FORECAST_PRECIPITATION_PROBABILITY = "precipitation_probability" +ATTR_API_FORECAST_TEMP = "temperature" +ATTR_API_FORECAST_TEMP_LOW = "templow" +ATTR_API_FORECAST_TIME = "datetime" +ATTR_API_FORECAST_WIND_BEARING = "wind_bearing" +ATTR_API_FORECAST_WIND_SPEED = "wind_speed" ATTR_API_HUMIDITY = "humidity" ATTR_API_PRESSURE = "pressure" ATTR_API_RAIN = "rain" @@ -158,14 +158,14 @@ CONDITIONS_MAP = { } FORECAST_MONITORED_CONDITIONS = [ - ATTR_FORECAST_CONDITION, - ATTR_FORECAST_PRECIPITATION, - ATTR_FORECAST_PRECIPITATION_PROBABILITY, - ATTR_FORECAST_TEMP, - ATTR_FORECAST_TEMP_LOW, - ATTR_FORECAST_TIME, - ATTR_FORECAST_WIND_BEARING, - ATTR_FORECAST_WIND_SPEED, + ATTR_API_FORECAST_CONDITION, + ATTR_API_FORECAST_PRECIPITATION, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_API_FORECAST_TEMP, + ATTR_API_FORECAST_TEMP_LOW, + ATTR_API_FORECAST_TIME, + ATTR_API_FORECAST_WIND_BEARING, + ATTR_API_FORECAST_WIND_SPEED, ] MONITORED_CONDITIONS = [ ATTR_API_CONDITION, @@ -202,43 +202,43 @@ FORECAST_MODE_ATTR_API = { FORECAST_SENSOR_TYPES: tuple[SensorEntityDescription, ...] = ( SensorEntityDescription( - key=ATTR_FORECAST_CONDITION, + key=ATTR_API_FORECAST_CONDITION, name="Condition", ), SensorEntityDescription( - key=ATTR_FORECAST_PRECIPITATION, + key=ATTR_API_FORECAST_PRECIPITATION, name="Precipitation", native_unit_of_measurement=PRECIPITATION_MILLIMETERS_PER_HOUR, ), SensorEntityDescription( - key=ATTR_FORECAST_PRECIPITATION_PROBABILITY, + key=ATTR_API_FORECAST_PRECIPITATION_PROBABILITY, name="Precipitation probability", native_unit_of_measurement=PERCENTAGE, ), SensorEntityDescription( - key=ATTR_FORECAST_TEMP, + key=ATTR_API_FORECAST_TEMP, name="Temperature", native_unit_of_measurement=TEMP_CELSIUS, device_class=SensorDeviceClass.TEMPERATURE, ), SensorEntityDescription( - key=ATTR_FORECAST_TEMP_LOW, + key=ATTR_API_FORECAST_TEMP_LOW, name="Temperature Low", native_unit_of_measurement=TEMP_CELSIUS, device_class=SensorDeviceClass.TEMPERATURE, ), SensorEntityDescription( - key=ATTR_FORECAST_TIME, + key=ATTR_API_FORECAST_TIME, name="Time", device_class=SensorDeviceClass.TIMESTAMP, ), SensorEntityDescription( - key=ATTR_FORECAST_WIND_BEARING, + key=ATTR_API_FORECAST_WIND_BEARING, name="Wind bearing", native_unit_of_measurement=DEGREE, ), SensorEntityDescription( - key=ATTR_FORECAST_WIND_SPEED, + key=ATTR_API_FORECAST_WIND_SPEED, name="Wind speed", native_unit_of_measurement=SPEED_KILOMETERS_PER_HOUR, ), diff --git a/homeassistant/components/aemet/sensor.py b/homeassistant/components/aemet/sensor.py index f98e3fff49e..e34583148e1 100644 --- a/homeassistant/components/aemet/sensor.py +++ b/homeassistant/components/aemet/sensor.py @@ -10,7 +10,7 @@ from homeassistant.helpers.update_coordinator import CoordinatorEntity from homeassistant.util import dt as dt_util from .const import ( - ATTR_FORECAST_TIME, + ATTR_API_FORECAST_TIME, ATTRIBUTION, DOMAIN, ENTRY_NAME, @@ -45,17 +45,13 @@ async def async_setup_entry( entities.extend( [ AemetForecastSensor( - name_prefix, - unique_id_prefix, + f"{domain_data[ENTRY_NAME]} {mode} Forecast", + f"{unique_id}-forecast-{mode}", weather_coordinator, mode, description, ) for mode in FORECAST_MODES - if ( - (name_prefix := f"{domain_data[ENTRY_NAME]} {mode} Forecast") - and (unique_id_prefix := f"{unique_id}-forecast-{mode}") - ) for description in FORECAST_SENSOR_TYPES if description.key in FORECAST_MONITORED_CONDITIONS ] @@ -89,14 +85,14 @@ class AemetSensor(AbstractAemetSensor): def __init__( self, name, - unique_id, + unique_id_prefix, weather_coordinator: WeatherUpdateCoordinator, description: SensorEntityDescription, ): """Initialize the sensor.""" super().__init__( name=name, - unique_id=f"{unique_id}-{description.key}", + unique_id=f"{unique_id_prefix}-{description.key}", coordinator=weather_coordinator, description=description, ) @@ -113,7 +109,7 @@ class AemetForecastSensor(AbstractAemetSensor): def __init__( self, name, - unique_id, + unique_id_prefix, weather_coordinator: WeatherUpdateCoordinator, forecast_mode, description: SensorEntityDescription, @@ -121,7 +117,7 @@ class AemetForecastSensor(AbstractAemetSensor): """Initialize the sensor.""" super().__init__( name=name, - unique_id=f"{unique_id}-{description.key}", + unique_id=f"{unique_id_prefix}-{description.key}", coordinator=weather_coordinator, description=description, ) @@ -139,6 +135,6 @@ class AemetForecastSensor(AbstractAemetSensor): ) if forecasts: forecast = forecasts[0].get(self.entity_description.key) - if self.entity_description.key == ATTR_FORECAST_TIME: + if self.entity_description.key == ATTR_API_FORECAST_TIME: forecast = dt_util.parse_datetime(forecast) return forecast diff --git a/homeassistant/components/aemet/weather.py b/homeassistant/components/aemet/weather.py index d05442b621e..a7ff3630e78 100644 --- a/homeassistant/components/aemet/weather.py +++ b/homeassistant/components/aemet/weather.py @@ -1,13 +1,36 @@ """Support for the AEMET OpenData service.""" -from homeassistant.components.weather import WeatherEntity +from homeassistant.components.weather import ( + ATTR_FORECAST_CONDITION, + ATTR_FORECAST_NATIVE_PRECIPITATION, + ATTR_FORECAST_NATIVE_TEMP, + ATTR_FORECAST_NATIVE_TEMP_LOW, + ATTR_FORECAST_NATIVE_WIND_SPEED, + ATTR_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_FORECAST_TIME, + ATTR_FORECAST_WIND_BEARING, + WeatherEntity, +) from homeassistant.config_entries import ConfigEntry -from homeassistant.const import PRESSURE_HPA, SPEED_KILOMETERS_PER_HOUR, TEMP_CELSIUS +from homeassistant.const import ( + LENGTH_MILLIMETERS, + PRESSURE_HPA, + SPEED_KILOMETERS_PER_HOUR, + TEMP_CELSIUS, +) from homeassistant.core import HomeAssistant from homeassistant.helpers.entity_platform import AddEntitiesCallback from homeassistant.helpers.update_coordinator import CoordinatorEntity from .const import ( ATTR_API_CONDITION, + ATTR_API_FORECAST_CONDITION, + ATTR_API_FORECAST_PRECIPITATION, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_API_FORECAST_TEMP, + ATTR_API_FORECAST_TEMP_LOW, + ATTR_API_FORECAST_TIME, + ATTR_API_FORECAST_WIND_BEARING, + ATTR_API_FORECAST_WIND_SPEED, ATTR_API_HUMIDITY, ATTR_API_PRESSURE, ATTR_API_TEMPERATURE, @@ -19,10 +42,32 @@ from .const import ( ENTRY_WEATHER_COORDINATOR, FORECAST_MODE_ATTR_API, FORECAST_MODE_DAILY, + FORECAST_MODE_HOURLY, FORECAST_MODES, ) from .weather_update_coordinator import WeatherUpdateCoordinator +FORECAST_MAP = { + FORECAST_MODE_DAILY: { + ATTR_API_FORECAST_CONDITION: ATTR_FORECAST_CONDITION, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY: ATTR_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_API_FORECAST_TEMP_LOW: ATTR_FORECAST_NATIVE_TEMP_LOW, + ATTR_API_FORECAST_TEMP: ATTR_FORECAST_NATIVE_TEMP, + ATTR_API_FORECAST_TIME: ATTR_FORECAST_TIME, + ATTR_API_FORECAST_WIND_BEARING: ATTR_FORECAST_WIND_BEARING, + ATTR_API_FORECAST_WIND_SPEED: ATTR_FORECAST_NATIVE_WIND_SPEED, + }, + FORECAST_MODE_HOURLY: { + ATTR_API_FORECAST_CONDITION: ATTR_FORECAST_CONDITION, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY: ATTR_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_API_FORECAST_PRECIPITATION: ATTR_FORECAST_NATIVE_PRECIPITATION, + ATTR_API_FORECAST_TEMP: ATTR_FORECAST_NATIVE_TEMP, + ATTR_API_FORECAST_TIME: ATTR_FORECAST_TIME, + ATTR_API_FORECAST_WIND_BEARING: ATTR_FORECAST_WIND_BEARING, + ATTR_API_FORECAST_WIND_SPEED: ATTR_FORECAST_NATIVE_WIND_SPEED, + }, +} + async def async_setup_entry( hass: HomeAssistant, @@ -47,9 +92,10 @@ class AemetWeather(CoordinatorEntity[WeatherUpdateCoordinator], WeatherEntity): """Implementation of an AEMET OpenData sensor.""" _attr_attribution = ATTRIBUTION - _attr_temperature_unit = TEMP_CELSIUS - _attr_pressure_unit = PRESSURE_HPA - _attr_wind_speed_unit = SPEED_KILOMETERS_PER_HOUR + _attr_native_precipitation_unit = LENGTH_MILLIMETERS + _attr_native_pressure_unit = PRESSURE_HPA + _attr_native_temperature_unit = TEMP_CELSIUS + _attr_native_wind_speed_unit = SPEED_KILOMETERS_PER_HOUR def __init__( self, @@ -75,7 +121,12 @@ class AemetWeather(CoordinatorEntity[WeatherUpdateCoordinator], WeatherEntity): @property def forecast(self): """Return the forecast array.""" - return self.coordinator.data[FORECAST_MODE_ATTR_API[self._forecast_mode]] + forecasts = self.coordinator.data[FORECAST_MODE_ATTR_API[self._forecast_mode]] + forecast_map = FORECAST_MAP[self._forecast_mode] + return [ + {ha_key: forecast[api_key] for api_key, ha_key in forecast_map.items()} + for forecast in forecasts + ] @property def humidity(self): @@ -83,12 +134,12 @@ class AemetWeather(CoordinatorEntity[WeatherUpdateCoordinator], WeatherEntity): return self.coordinator.data[ATTR_API_HUMIDITY] @property - def pressure(self): + def native_pressure(self): """Return the pressure.""" return self.coordinator.data[ATTR_API_PRESSURE] @property - def temperature(self): + def native_temperature(self): """Return the temperature.""" return self.coordinator.data[ATTR_API_TEMPERATURE] @@ -98,6 +149,6 @@ class AemetWeather(CoordinatorEntity[WeatherUpdateCoordinator], WeatherEntity): return self.coordinator.data[ATTR_API_WIND_BEARING] @property - def wind_speed(self): + def native_wind_speed(self): """Return the wind speed.""" return self.coordinator.data[ATTR_API_WIND_SPEED] diff --git a/homeassistant/components/aemet/weather_update_coordinator.py b/homeassistant/components/aemet/weather_update_coordinator.py index c86465ea8f1..1c64206891c 100644 --- a/homeassistant/components/aemet/weather_update_coordinator.py +++ b/homeassistant/components/aemet/weather_update_coordinator.py @@ -42,23 +42,21 @@ from aemet_opendata.helpers import ( ) import async_timeout -from homeassistant.components.weather import ( - ATTR_FORECAST_CONDITION, - ATTR_FORECAST_PRECIPITATION, - ATTR_FORECAST_PRECIPITATION_PROBABILITY, - ATTR_FORECAST_TEMP, - ATTR_FORECAST_TEMP_LOW, - ATTR_FORECAST_TIME, - ATTR_FORECAST_WIND_BEARING, - ATTR_FORECAST_WIND_SPEED, -) from homeassistant.helpers.update_coordinator import DataUpdateCoordinator, UpdateFailed from homeassistant.util import dt as dt_util from .const import ( ATTR_API_CONDITION, + ATTR_API_FORECAST_CONDITION, ATTR_API_FORECAST_DAILY, ATTR_API_FORECAST_HOURLY, + ATTR_API_FORECAST_PRECIPITATION, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY, + ATTR_API_FORECAST_TEMP, + ATTR_API_FORECAST_TEMP_LOW, + ATTR_API_FORECAST_TIME, + ATTR_API_FORECAST_WIND_BEARING, + ATTR_API_FORECAST_WIND_SPEED, ATTR_API_HUMIDITY, ATTR_API_PRESSURE, ATTR_API_RAIN, @@ -402,15 +400,15 @@ class WeatherUpdateCoordinator(DataUpdateCoordinator): return None return { - ATTR_FORECAST_CONDITION: condition, - ATTR_FORECAST_PRECIPITATION_PROBABILITY: self._get_precipitation_prob_day( + ATTR_API_FORECAST_CONDITION: condition, + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY: self._get_precipitation_prob_day( day ), - ATTR_FORECAST_TEMP: self._get_temperature_day(day), - ATTR_FORECAST_TEMP_LOW: self._get_temperature_low_day(day), - ATTR_FORECAST_TIME: dt_util.as_utc(date).isoformat(), - ATTR_FORECAST_WIND_SPEED: self._get_wind_speed_day(day), - ATTR_FORECAST_WIND_BEARING: self._get_wind_bearing_day(day), + ATTR_API_FORECAST_TEMP: self._get_temperature_day(day), + ATTR_API_FORECAST_TEMP_LOW: self._get_temperature_low_day(day), + ATTR_API_FORECAST_TIME: dt_util.as_utc(date).isoformat(), + ATTR_API_FORECAST_WIND_SPEED: self._get_wind_speed_day(day), + ATTR_API_FORECAST_WIND_BEARING: self._get_wind_bearing_day(day), } def _convert_forecast_hour(self, date, day, hour): @@ -420,15 +418,15 @@ class WeatherUpdateCoordinator(DataUpdateCoordinator): forecast_dt = date.replace(hour=hour, minute=0, second=0) return { - ATTR_FORECAST_CONDITION: condition, - ATTR_FORECAST_PRECIPITATION: self._calc_precipitation(day, hour), - ATTR_FORECAST_PRECIPITATION_PROBABILITY: self._calc_precipitation_prob( + ATTR_API_FORECAST_CONDITION: condition, + ATTR_API_FORECAST_PRECIPITATION: self._calc_precipitation(day, hour), + ATTR_API_FORECAST_PRECIPITATION_PROBABILITY: self._calc_precipitation_prob( day, hour ), - ATTR_FORECAST_TEMP: self._get_temperature(day, hour), - ATTR_FORECAST_TIME: dt_util.as_utc(forecast_dt).isoformat(), - ATTR_FORECAST_WIND_SPEED: self._get_wind_speed(day, hour), - ATTR_FORECAST_WIND_BEARING: self._get_wind_bearing(day, hour), + ATTR_API_FORECAST_TEMP: self._get_temperature(day, hour), + ATTR_API_FORECAST_TIME: dt_util.as_utc(forecast_dt).isoformat(), + ATTR_API_FORECAST_WIND_SPEED: self._get_wind_speed(day, hour), + ATTR_API_FORECAST_WIND_BEARING: self._get_wind_bearing(day, hour), } def _calc_precipitation(self, day, hour):