mirror of
https://github.com/home-assistant/core.git
synced 2025-04-24 09:17:53 +00:00
Fixed Canary temperature sensor and remapped air quality value (#11355)
* Fixed Canary temperature sensor and remapped air quality value * Addressed review comment * - Fixed canary tests and added more tests - Removed py-canary requirements from tests * Noop to trigger a build again * - Removed py-canary requirements from tests * Addressed PR comment * - Updated tests - Removed py-canary from gen_requirements_all.py * - Fixed hound violation * Added back py-canary to gen_requirements_all.py as it's still need in tests * Added back py-canary to test requirements as it's still need in tests * Address PR comment
This commit is contained in:
parent
c7efe5b7dd
commit
b3bf6c4be2
@ -111,6 +111,13 @@ class CanaryData(object):
|
||||
"""Return a list of readings based on device_id."""
|
||||
return self._readings_by_device_id.get(device_id, [])
|
||||
|
||||
def get_reading(self, device_id, sensor_type):
|
||||
"""Return reading for device_id and sensor type."""
|
||||
readings = self._readings_by_device_id.get(device_id, [])
|
||||
return next((
|
||||
reading.value for reading in readings
|
||||
if reading.sensor_type == sensor_type), None)
|
||||
|
||||
def set_location_mode(self, location_id, mode_name, is_private=False):
|
||||
"""Set location mode."""
|
||||
self._api.set_location_mode(location_id, mode_name, is_private)
|
||||
|
@ -4,13 +4,27 @@ Support for Canary sensors.
|
||||
For more details about this platform, please refer to the documentation at
|
||||
https://home-assistant.io/components/sensor.canary/
|
||||
"""
|
||||
|
||||
from homeassistant.components.canary import DATA_CANARY
|
||||
from homeassistant.const import TEMP_FAHRENHEIT, TEMP_CELSIUS
|
||||
from homeassistant.const import TEMP_CELSIUS
|
||||
from homeassistant.helpers.entity import Entity
|
||||
|
||||
DEPENDENCIES = ['canary']
|
||||
|
||||
SENSOR_VALUE_PRECISION = 1
|
||||
SENSOR_VALUE_PRECISION = 2
|
||||
ATTR_AIR_QUALITY = "air_quality"
|
||||
|
||||
# Sensor types are defined like so:
|
||||
# sensor type name, unit_of_measurement, icon
|
||||
SENSOR_TYPES = [
|
||||
["temperature", TEMP_CELSIUS, "mdi:thermometer"],
|
||||
["humidity", "%", "mdi:water-percent"],
|
||||
["air_quality", None, "mdi:weather-windy"],
|
||||
]
|
||||
|
||||
STATE_AIR_QUALITY_NORMAL = "normal"
|
||||
STATE_AIR_QUALITY_ABNORMAL = "abnormal"
|
||||
STATE_AIR_QUALITY_VERY_ABNORMAL = "very_abnormal"
|
||||
|
||||
|
||||
def setup_platform(hass, config, add_devices, discovery_info=None):
|
||||
@ -18,11 +32,10 @@ def setup_platform(hass, config, add_devices, discovery_info=None):
|
||||
data = hass.data[DATA_CANARY]
|
||||
devices = []
|
||||
|
||||
from canary.api import SensorType
|
||||
for location in data.locations:
|
||||
for device in location.devices:
|
||||
if device.is_online:
|
||||
for sensor_type in SensorType:
|
||||
for sensor_type in SENSOR_TYPES:
|
||||
devices.append(CanarySensor(data, sensor_type, location,
|
||||
device))
|
||||
|
||||
@ -37,10 +50,9 @@ class CanarySensor(Entity):
|
||||
self._data = data
|
||||
self._sensor_type = sensor_type
|
||||
self._device_id = device.device_id
|
||||
self._is_celsius = location.is_celsius
|
||||
self._sensor_value = None
|
||||
|
||||
sensor_type_name = sensor_type.value.replace("_", " ").title()
|
||||
sensor_type_name = sensor_type[0].replace("_", " ").title()
|
||||
self._name = '{} {} {}'.format(location.name,
|
||||
device.name,
|
||||
sensor_type_name)
|
||||
@ -59,27 +71,51 @@ class CanarySensor(Entity):
|
||||
def unique_id(self):
|
||||
"""Return the unique ID of this sensor."""
|
||||
return "sensor_canary_{}_{}".format(self._device_id,
|
||||
self._sensor_type.value)
|
||||
self._sensor_type[0])
|
||||
|
||||
@property
|
||||
def unit_of_measurement(self):
|
||||
"""Return the unit of measurement this sensor expresses itself in."""
|
||||
from canary.api import SensorType
|
||||
if self._sensor_type == SensorType.TEMPERATURE:
|
||||
return TEMP_CELSIUS if self._is_celsius else TEMP_FAHRENHEIT
|
||||
elif self._sensor_type == SensorType.HUMIDITY:
|
||||
return "%"
|
||||
elif self._sensor_type == SensorType.AIR_QUALITY:
|
||||
return ""
|
||||
"""Return the unit of measurement."""
|
||||
return self._sensor_type[1]
|
||||
|
||||
@property
|
||||
def icon(self):
|
||||
"""Icon for the sensor."""
|
||||
return self._sensor_type[2]
|
||||
|
||||
@property
|
||||
def device_state_attributes(self):
|
||||
"""Return the state attributes."""
|
||||
if self._sensor_type[0] == "air_quality" \
|
||||
and self._sensor_value is not None:
|
||||
air_quality = None
|
||||
if self._sensor_value <= .4:
|
||||
air_quality = STATE_AIR_QUALITY_VERY_ABNORMAL
|
||||
elif self._sensor_value <= .59:
|
||||
air_quality = STATE_AIR_QUALITY_ABNORMAL
|
||||
elif self._sensor_value <= 1.0:
|
||||
air_quality = STATE_AIR_QUALITY_NORMAL
|
||||
|
||||
return {
|
||||
ATTR_AIR_QUALITY: air_quality
|
||||
}
|
||||
|
||||
return None
|
||||
|
||||
def update(self):
|
||||
"""Get the latest state of the sensor."""
|
||||
self._data.update()
|
||||
|
||||
readings = self._data.get_readings(self._device_id)
|
||||
value = next((
|
||||
reading.value for reading in readings
|
||||
if reading.sensor_type == self._sensor_type), None)
|
||||
from canary.api import SensorType
|
||||
canary_sensor_type = None
|
||||
if self._sensor_type[0] == "air_quality":
|
||||
canary_sensor_type = SensorType.AIR_QUALITY
|
||||
elif self._sensor_type[0] == "temperature":
|
||||
canary_sensor_type = SensorType.TEMPERATURE
|
||||
elif self._sensor_type[0] == "humidity":
|
||||
canary_sensor_type = SensorType.HUMIDITY
|
||||
|
||||
value = self._data.get_reading(self._device_id, canary_sensor_type)
|
||||
|
||||
if value is not None:
|
||||
self._sensor_value = round(float(value), SENSOR_VALUE_PRECISION)
|
||||
|
@ -3,13 +3,13 @@ import copy
|
||||
import unittest
|
||||
from unittest.mock import Mock
|
||||
|
||||
from canary.api import SensorType
|
||||
from homeassistant.components.canary import DATA_CANARY
|
||||
from homeassistant.components.sensor import canary
|
||||
from homeassistant.components.sensor.canary import CanarySensor
|
||||
from homeassistant.components.sensor.canary import CanarySensor, \
|
||||
SENSOR_TYPES, ATTR_AIR_QUALITY, STATE_AIR_QUALITY_NORMAL, \
|
||||
STATE_AIR_QUALITY_ABNORMAL, STATE_AIR_QUALITY_VERY_ABNORMAL
|
||||
from tests.common import (get_test_home_assistant)
|
||||
from tests.components.test_canary import mock_device, mock_reading, \
|
||||
mock_location
|
||||
from tests.components.test_canary import mock_device, mock_location
|
||||
|
||||
VALID_CONFIG = {
|
||||
"canary": {
|
||||
@ -55,38 +55,33 @@ class TestCanarySensorSetup(unittest.TestCase):
|
||||
|
||||
self.assertEqual(6, len(self.DEVICES))
|
||||
|
||||
def test_celsius_temperature_sensor(self):
|
||||
"""Test temperature sensor with celsius."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home", True)
|
||||
|
||||
data = Mock()
|
||||
data.get_readings.return_value = [
|
||||
mock_reading(SensorType.TEMPERATURE, 21.1234)]
|
||||
|
||||
sensor = CanarySensor(data, SensorType.TEMPERATURE, location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Temperature", sensor.name)
|
||||
self.assertEqual("sensor_canary_10_temperature", sensor.unique_id)
|
||||
self.assertEqual("°C", sensor.unit_of_measurement)
|
||||
self.assertEqual(21.1, sensor.state)
|
||||
|
||||
def test_fahrenheit_temperature_sensor(self):
|
||||
def test_temperature_sensor(self):
|
||||
"""Test temperature sensor with fahrenheit."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home", False)
|
||||
|
||||
data = Mock()
|
||||
data.get_readings.return_value = [
|
||||
mock_reading(SensorType.TEMPERATURE, 21.1567)]
|
||||
data.get_reading.return_value = 21.1234
|
||||
|
||||
sensor = CanarySensor(data, SensorType.TEMPERATURE, location, device)
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[0], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Temperature", sensor.name)
|
||||
self.assertEqual("°F", sensor.unit_of_measurement)
|
||||
self.assertEqual(21.2, sensor.state)
|
||||
self.assertEqual("°C", sensor.unit_of_measurement)
|
||||
self.assertEqual(21.12, sensor.state)
|
||||
|
||||
def test_temperature_sensor_with_none_sensor_value(self):
|
||||
"""Test temperature sensor with fahrenheit."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home", False)
|
||||
|
||||
data = Mock()
|
||||
data.get_reading.return_value = None
|
||||
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[0], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual(None, sensor.state)
|
||||
|
||||
def test_humidity_sensor(self):
|
||||
"""Test humidity sensor."""
|
||||
@ -94,28 +89,79 @@ class TestCanarySensorSetup(unittest.TestCase):
|
||||
location = mock_location("Home")
|
||||
|
||||
data = Mock()
|
||||
data.get_readings.return_value = [
|
||||
mock_reading(SensorType.HUMIDITY, 50.4567)]
|
||||
data.get_reading.return_value = 50.4567
|
||||
|
||||
sensor = CanarySensor(data, SensorType.HUMIDITY, location, device)
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[1], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Humidity", sensor.name)
|
||||
self.assertEqual("%", sensor.unit_of_measurement)
|
||||
self.assertEqual(50.5, sensor.state)
|
||||
self.assertEqual(50.46, sensor.state)
|
||||
|
||||
def test_air_quality_sensor(self):
|
||||
def test_air_quality_sensor_with_very_abnormal_reading(self):
|
||||
"""Test air quality sensor."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home")
|
||||
|
||||
data = Mock()
|
||||
data.get_readings.return_value = [
|
||||
mock_reading(SensorType.AIR_QUALITY, 50.4567)]
|
||||
data.get_reading.return_value = 0.4
|
||||
|
||||
sensor = CanarySensor(data, SensorType.AIR_QUALITY, location, device)
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[2], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Air Quality", sensor.name)
|
||||
self.assertEqual("", sensor.unit_of_measurement)
|
||||
self.assertEqual(50.5, sensor.state)
|
||||
self.assertEqual(None, sensor.unit_of_measurement)
|
||||
self.assertEqual(0.4, sensor.state)
|
||||
|
||||
air_quality = sensor.device_state_attributes[ATTR_AIR_QUALITY]
|
||||
self.assertEqual(STATE_AIR_QUALITY_VERY_ABNORMAL, air_quality)
|
||||
|
||||
def test_air_quality_sensor_with_abnormal_reading(self):
|
||||
"""Test air quality sensor."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home")
|
||||
|
||||
data = Mock()
|
||||
data.get_reading.return_value = 0.59
|
||||
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[2], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Air Quality", sensor.name)
|
||||
self.assertEqual(None, sensor.unit_of_measurement)
|
||||
self.assertEqual(0.59, sensor.state)
|
||||
|
||||
air_quality = sensor.device_state_attributes[ATTR_AIR_QUALITY]
|
||||
self.assertEqual(STATE_AIR_QUALITY_ABNORMAL, air_quality)
|
||||
|
||||
def test_air_quality_sensor_with_normal_reading(self):
|
||||
"""Test air quality sensor."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home")
|
||||
|
||||
data = Mock()
|
||||
data.get_reading.return_value = 1.0
|
||||
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[2], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual("Home Family Room Air Quality", sensor.name)
|
||||
self.assertEqual(None, sensor.unit_of_measurement)
|
||||
self.assertEqual(1.0, sensor.state)
|
||||
|
||||
air_quality = sensor.device_state_attributes[ATTR_AIR_QUALITY]
|
||||
self.assertEqual(STATE_AIR_QUALITY_NORMAL, air_quality)
|
||||
|
||||
def test_air_quality_sensor_with_none_sensor_value(self):
|
||||
"""Test air quality sensor."""
|
||||
device = mock_device(10, "Family Room")
|
||||
location = mock_location("Home")
|
||||
|
||||
data = Mock()
|
||||
data.get_reading.return_value = None
|
||||
|
||||
sensor = CanarySensor(data, SENSOR_TYPES[2], location, device)
|
||||
sensor.update()
|
||||
|
||||
self.assertEqual(None, sensor.state)
|
||||
self.assertEqual(None, sensor.device_state_attributes)
|
||||
|
Loading…
x
Reference in New Issue
Block a user