From 012291a1f3d9478be4c6d7c149ac59e472154e0e Mon Sep 17 00:00:00 2001 From: Jan Bouwhuis Date: Tue, 12 Mar 2024 09:07:20 +0100 Subject: [PATCH] Fix google_asssistant sensor state reporting (#112838) * Fix post google_assistant sensor values as float not string * Fix aqi reporting and improve tests * Fix _air_quality_description_for_aqi and test --- .../components/google_assistant/trait.py | 15 ++++--- .../components/google_assistant/test_trait.py | 40 ++++++++++++------- 2 files changed, 35 insertions(+), 20 deletions(-) diff --git a/homeassistant/components/google_assistant/trait.py b/homeassistant/components/google_assistant/trait.py index bf68ebd758c..dd1e0cb3409 100644 --- a/homeassistant/components/google_assistant/trait.py +++ b/homeassistant/components/google_assistant/trait.py @@ -2707,10 +2707,9 @@ class SensorStateTrait(_Trait): name = TRAIT_SENSOR_STATE commands: list[str] = [] - def _air_quality_description_for_aqi(self, aqi): - if aqi is None or aqi.isnumeric() is False: + def _air_quality_description_for_aqi(self, aqi: float | None) -> str: + if aqi is None or aqi < 0: return "unknown" - aqi = int(aqi) if aqi <= 50: return "healthy" if aqi <= 100: @@ -2765,11 +2764,17 @@ class SensorStateTrait(_Trait): if device_class is None or data is None: return {} - sensor_data = {"name": data[0], "rawValue": self.state.state} + try: + value = float(self.state.state) + except ValueError: + value = None + if self.state.state == STATE_UNKNOWN: + value = None + sensor_data = {"name": data[0], "rawValue": value} if device_class == sensor.SensorDeviceClass.AQI: sensor_data["currentSensorState"] = self._air_quality_description_for_aqi( - self.state.state + value ) return {"currentSensorStateData": [sensor_data]} diff --git a/tests/components/google_assistant/test_trait.py b/tests/components/google_assistant/test_trait.py index b9a68b90a26..a285febe5b3 100644 --- a/tests/components/google_assistant/test_trait.py +++ b/tests/components/google_assistant/test_trait.py @@ -1,6 +1,7 @@ """Tests for the Google Assistant traits.""" from datetime import datetime, timedelta +from typing import Any from unittest.mock import ANY, patch from freezegun.api import FrozenDateTimeFactory @@ -3926,16 +3927,15 @@ async def test_air_quality_description_for_aqi(hass: HomeAssistant) -> None: BASIC_CONFIG, ) - assert trt._air_quality_description_for_aqi("0") == "healthy" - assert trt._air_quality_description_for_aqi("75") == "moderate" + assert trt._air_quality_description_for_aqi(0) == "healthy" + assert trt._air_quality_description_for_aqi(75) == "moderate" assert ( - trt._air_quality_description_for_aqi("125") == "unhealthy for sensitive groups" + trt._air_quality_description_for_aqi(125.0) == "unhealthy for sensitive groups" ) - assert trt._air_quality_description_for_aqi("175") == "unhealthy" - assert trt._air_quality_description_for_aqi("250") == "very unhealthy" - assert trt._air_quality_description_for_aqi("350") == "hazardous" - assert trt._air_quality_description_for_aqi("-1") == "unknown" - assert trt._air_quality_description_for_aqi("non-numeric") == "unknown" + assert trt._air_quality_description_for_aqi(175) == "unhealthy" + assert trt._air_quality_description_for_aqi(250) == "very unhealthy" + assert trt._air_quality_description_for_aqi(350) == "hazardous" + assert trt._air_quality_description_for_aqi(-1) == "unknown" async def test_null_device_class(hass: HomeAssistant) -> None: @@ -3956,7 +3956,19 @@ async def test_null_device_class(hass: HomeAssistant) -> None: assert trt.query_attributes() == {} -async def test_sensorstate(hass: HomeAssistant) -> None: +@pytest.mark.parametrize( + ("value", "published", "aqi"), + [ + (100.0, 100.0, "moderate"), + (10.0, 10.0, "healthy"), + (0, 0.0, "healthy"), + ("", None, "unknown"), + ("unknown", None, "unknown"), + ], +) +async def test_sensorstate( + hass: HomeAssistant, value: Any, published: Any, aqi: Any +) -> None: """Test SensorState trait support for sensor domain.""" sensor_types = { sensor.SensorDeviceClass.AQI: ("AirQuality", "AQI"), @@ -3978,7 +3990,7 @@ async def test_sensorstate(hass: HomeAssistant) -> None: hass, State( "sensor.test", - 100.0, + value, { "device_class": sensor_type, }, @@ -4024,16 +4036,14 @@ async def test_sensorstate(hass: HomeAssistant) -> None: "currentSensorStateData": [ { "name": name, - "currentSensorState": trt._air_quality_description_for_aqi( - trt.state.state - ), - "rawValue": trt.state.state, + "currentSensorState": aqi, + "rawValue": published, }, ] } else: assert trt.query_attributes() == { - "currentSensorStateData": [{"name": name, "rawValue": trt.state.state}] + "currentSensorStateData": [{"name": name, "rawValue": published}] } assert helpers.get_google_type(sensor.DOMAIN, None) is not None