From 2a348e68c88a045718437e236702553592cd4fcf Mon Sep 17 00:00:00 2001 From: Elad Bar Date: Sun, 12 Dec 2021 18:23:02 +0200 Subject: [PATCH] Added support for long term statistics --- CHANGELOG.md | 4 + custom_components/edgeos/helpers/const.py | 7 +- .../edgeos/managers/entity_manager.py | 74 ++++++++++++++----- custom_components/edgeos/manifest.json | 2 +- .../edgeos/models/entity_data.py | 5 +- custom_components/edgeos/sensor.py | 5 ++ 6 files changed, 74 insertions(+), 23 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 6b5f6e8..66428d6 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,5 +1,9 @@ # Changelog +## 1.1.7 + +- Added support for long term statistics +- ## 1.1.6 - Upgraded code to support breaking changes of HA v2012.12.0 diff --git a/custom_components/edgeos/helpers/const.py b/custom_components/edgeos/helpers/const.py index b686034..ab85185 100644 --- a/custom_components/edgeos/helpers/const.py +++ b/custom_components/edgeos/helpers/const.py @@ -8,7 +8,11 @@ BinarySensorDeviceClass, ) from homeassistant.components.device_tracker import DOMAIN as DOMAIN_DEVICE_TRACKER -from homeassistant.components.sensor import DOMAIN as DOMAIN_SENSOR, SensorDeviceClass +from homeassistant.components.sensor import ( + DOMAIN as DOMAIN_SENSOR, + SensorDeviceClass, + SensorStateClass, +) from homeassistant.const import ( ATTR_NAME, ATTR_UNIT_OF_MEASUREMENT, @@ -242,6 +246,7 @@ ENTITY_DISABLED = "disabled" ENTITY_BINARY_SENSOR_DEVICE_CLASS = "binary-sensor-device-class" ENTITY_SENSOR_DEVICE_CLASS = "sensor-device-class" +ENTITY_SENSOR_STATE_CLASS = "sensor-state-class" ENTITY_STATUS = "entity-status" ENTITY_STATUS_EMPTY = None diff --git a/custom_components/edgeos/managers/entity_manager.py b/custom_components/edgeos/managers/entity_manager.py index d64c03e..fa3d2da 100644 --- a/custom_components/edgeos/managers/entity_manager.py +++ b/custom_components/edgeos/managers/entity_manager.py @@ -316,8 +316,8 @@ def create_binary_sensor( icon = ICONS[sensor_type] - self.create_entity( - DOMAIN_BINARY_SENSOR, entity_name, is_on, attributes, BinarySensorDeviceClass.CONNECTIVITY, icon + self.create_binary_sensor_entity( + entity_name, is_on, attributes, BinarySensorDeviceClass.CONNECTIVITY, icon ) except Exception as ex: @@ -341,8 +341,8 @@ def create_unknown_devices_sensor(self): ATTR_UNKNOWN_DEVICES: unknown_devices, } - self.create_entity( - DOMAIN_SENSOR, entity_name, state, attributes, None, "mdi:help-rhombus" + self.create_sensor_entity( + entity_name, state, attributes, None, SensorStateClass.MEASUREMENT, "mdi:help-rhombus" ) except Exception as ex: self.log_exception( @@ -372,8 +372,8 @@ def create_uptime_sensor( if key != UPTIME: attributes[key] = system_state[key] - self.create_entity( - DOMAIN_SENSOR, entity_name, state, attributes, None, "mdi:timer-sand" + self.create_sensor_entity( + entity_name, state, attributes, None, SensorStateClass.TOTAL_INCREASING, "mdi:timer-sand" ) except Exception as ex: self.log_exception(ex, "Failed to create system sensor") @@ -404,8 +404,8 @@ def create_system_status_binary_sensor( icon = CONNECTED_ICONS[is_alive] - self.create_entity( - DOMAIN_BINARY_SENSOR, entity_name, is_alive, attributes, BinarySensorDeviceClass.CONNECTIVITY, icon + self.create_binary_sensor_entity( + entity_name, is_alive, attributes, BinarySensorDeviceClass.CONNECTIVITY, icon ) except Exception as ex: self.log_exception(ex, "Failed to create system status binary sensor") @@ -430,8 +430,8 @@ def create_device_tracker(self, host, data): if ATTR_UNIT_OF_MEASUREMENT not in attr: attributes[name] = value - self.create_entity( - DOMAIN_DEVICE_TRACKER, entity_name, state, attributes + self.create_device_tracker_entity( + entity_name, state, attributes ) except Exception as ex: @@ -440,13 +440,12 @@ def create_device_tracker(self, host, data): f"Failed to create {host} device tracker with the following data: {data}", ) - def create_entity( - self, - domain: str, + @staticmethod + def get_basic_entity( name: str, + domain: str, state: int, attributes: dict, - device_class: Optional[str] = None, icon: Optional[str] = None, ): entity = EntityData() @@ -457,15 +456,50 @@ def create_entity( entity.device_name = DEFAULT_NAME entity.unique_id = f"{DEFAULT_NAME}-{domain}-{name}" - if domain == DOMAIN_BINARY_SENSOR: - entity.binary_sensor_device_class = device_class - elif domain == DOMAIN_SENSOR: - entity.sensor_device_class = device_class - if icon is not None: entity.icon = icon - self.set_entity(domain, name, entity) + return entity + + def create_device_tracker_entity( + self, + name: str, + state: int, + attributes: dict + ): + entity = self.get_basic_entity(name, DOMAIN_DEVICE_TRACKER, state, attributes) + + self.set_entity(DOMAIN_DEVICE_TRACKER, name, entity) + + def create_binary_sensor_entity( + self, + name: str, + state: int, + attributes: dict, + device_class: Optional[BinarySensorDeviceClass] = None, + icon: Optional[str] = None, + ): + entity = self.get_basic_entity(name, DOMAIN_BINARY_SENSOR, state, attributes, icon) + + entity.binary_sensor_device_class = device_class + + self.set_entity(DOMAIN_BINARY_SENSOR, name, entity) + + def create_sensor_entity( + self, + name: str, + state: int, + attributes: dict, + device_class: Optional[SensorDeviceClass] = None, + state_class: Optional[SensorStateClass] = None, + icon: Optional[str] = None, + ): + entity = self.get_basic_entity(name, DOMAIN_BINARY_SENSOR, state, attributes, icon) + + entity.sensor_device_class = device_class + entity.sensor_state_class = state_class + + self.set_entity(DOMAIN_SENSOR, name, entity) @staticmethod def get_device_attributes(key): diff --git a/custom_components/edgeos/manifest.json b/custom_components/edgeos/manifest.json index 81debba..c4be943 100644 --- a/custom_components/edgeos/manifest.json +++ b/custom_components/edgeos/manifest.json @@ -6,6 +6,6 @@ "codeowners": ["@elad-bar"], "requirements": ["aiohttp"], "config_flow": true, - "version": "1.1.6", + "version": "1.1.7", "iot_class": "local_polling" } diff --git a/custom_components/edgeos/models/entity_data.py b/custom_components/edgeos/models/entity_data.py index db2b398..242edab 100644 --- a/custom_components/edgeos/models/entity_data.py +++ b/custom_components/edgeos/models/entity_data.py @@ -14,6 +14,7 @@ class EntityData: disabled: bool binary_sensor_device_class: Optional[BinarySensorDeviceClass] sensor_device_class: Optional[SensorDeviceClass] + sensor_state_class: Optional[SensorStateClass] def __init__(self): self.unique_id = "" @@ -26,6 +27,7 @@ def __init__(self): self.disabled = False self.binary_sensor_device_class = None self.sensor_device_class = None + self.sensor_state_class = None def __repr__(self): obj = { @@ -38,7 +40,8 @@ def __repr__(self): ENTITY_UNIQUE_ID: self.unique_id, ENTITY_DISABLED: self.disabled, ENTITY_BINARY_SENSOR_DEVICE_CLASS: self.binary_sensor_device_class, - ENTITY_SENSOR_DEVICE_CLASS: self.sensor_device_class + ENTITY_SENSOR_DEVICE_CLASS: self.sensor_device_class, + ENTITY_SENSOR_STATE_CLASS: self.sensor_state_class } to_string = f"{obj}" diff --git a/custom_components/edgeos/sensor.py b/custom_components/edgeos/sensor.py index 340a00d..fe18d48 100644 --- a/custom_components/edgeos/sensor.py +++ b/custom_components/edgeos/sensor.py @@ -57,6 +57,11 @@ def device_class(self) -> SensorDeviceClass | str | None: """Return the class of this sensor.""" return self.entity.sensor_device_class + @property + def state_class(self) -> SensorDeviceClass | str | None: + """Return the class of this sensor.""" + return self.entity.sensor_state_class + def _immediate_update(self, previous_state: bool): if previous_state != self.entity.state: _LOGGER.debug(