core/homeassistant/components/homewizard/sensor.py

199 lines
6.5 KiB
Python

"""Creates Homewizard sensor entities."""
from __future__ import annotations
import logging
from typing import Final
from homeassistant.components.sensor import (
STATE_CLASS_MEASUREMENT,
STATE_CLASS_TOTAL_INCREASING,
SensorEntity,
SensorEntityDescription,
)
from homeassistant.config_entries import ConfigEntry
from homeassistant.const import (
DEVICE_CLASS_ENERGY,
DEVICE_CLASS_GAS,
DEVICE_CLASS_POWER,
ENERGY_KILO_WATT_HOUR,
PERCENTAGE,
POWER_WATT,
VOLUME_CUBIC_METERS,
)
from homeassistant.core import HomeAssistant
from homeassistant.helpers.entity import DeviceInfo, EntityCategory
from homeassistant.helpers.entity_platform import AddEntitiesCallback
from homeassistant.helpers.typing import StateType
from homeassistant.helpers.update_coordinator import CoordinatorEntity
from .const import DOMAIN, DeviceResponseEntry
from .coordinator import HWEnergyDeviceUpdateCoordinator
_LOGGER = logging.getLogger(__name__)
SENSORS: Final[tuple[SensorEntityDescription, ...]] = (
SensorEntityDescription(
key="smr_version",
name="DSMR Version",
icon="mdi:counter",
entity_category=EntityCategory.DIAGNOSTIC,
),
SensorEntityDescription(
key="meter_model",
name="Smart Meter Model",
icon="mdi:gauge",
entity_category=EntityCategory.DIAGNOSTIC,
),
SensorEntityDescription(
key="wifi_ssid",
name="Wifi SSID",
icon="mdi:wifi",
entity_category=EntityCategory.DIAGNOSTIC,
),
SensorEntityDescription(
key="wifi_strength",
name="Wifi Strength",
icon="mdi:wifi",
native_unit_of_measurement=PERCENTAGE,
state_class=STATE_CLASS_MEASUREMENT,
entity_category=EntityCategory.DIAGNOSTIC,
entity_registry_enabled_default=False,
),
SensorEntityDescription(
key="total_power_import_t1_kwh",
name="Total Power Import T1",
native_unit_of_measurement=ENERGY_KILO_WATT_HOUR,
device_class=DEVICE_CLASS_ENERGY,
state_class=STATE_CLASS_TOTAL_INCREASING,
),
SensorEntityDescription(
key="total_power_import_t2_kwh",
name="Total Power Import T2",
native_unit_of_measurement=ENERGY_KILO_WATT_HOUR,
device_class=DEVICE_CLASS_ENERGY,
state_class=STATE_CLASS_TOTAL_INCREASING,
),
SensorEntityDescription(
key="total_power_export_t1_kwh",
name="Total Power Export T1",
native_unit_of_measurement=ENERGY_KILO_WATT_HOUR,
device_class=DEVICE_CLASS_ENERGY,
state_class=STATE_CLASS_TOTAL_INCREASING,
),
SensorEntityDescription(
key="total_power_export_t2_kwh",
name="Total Power Export T2",
native_unit_of_measurement=ENERGY_KILO_WATT_HOUR,
device_class=DEVICE_CLASS_ENERGY,
state_class=STATE_CLASS_TOTAL_INCREASING,
),
SensorEntityDescription(
key="active_power_w",
name="Active Power",
native_unit_of_measurement=POWER_WATT,
device_class=DEVICE_CLASS_POWER,
state_class=STATE_CLASS_MEASUREMENT,
),
SensorEntityDescription(
key="active_power_l1_w",
name="Active Power L1",
native_unit_of_measurement=POWER_WATT,
device_class=DEVICE_CLASS_POWER,
state_class=STATE_CLASS_MEASUREMENT,
),
SensorEntityDescription(
key="active_power_l2_w",
name="Active Power L2",
native_unit_of_measurement=POWER_WATT,
device_class=DEVICE_CLASS_POWER,
state_class=STATE_CLASS_MEASUREMENT,
),
SensorEntityDescription(
key="active_power_l3_w",
name="Active Power L3",
native_unit_of_measurement=POWER_WATT,
device_class=DEVICE_CLASS_POWER,
state_class=STATE_CLASS_MEASUREMENT,
),
SensorEntityDescription(
key="total_gas_m3",
name="Total Gas",
native_unit_of_measurement=VOLUME_CUBIC_METERS,
device_class=DEVICE_CLASS_GAS,
state_class=STATE_CLASS_TOTAL_INCREASING,
),
)
async def async_setup_entry(
hass: HomeAssistant, entry: ConfigEntry, async_add_entities: AddEntitiesCallback
) -> None:
"""Initialize sensors."""
coordinator: HWEnergyDeviceUpdateCoordinator = hass.data[DOMAIN][entry.entry_id]
entities = []
if coordinator.api.data is not None:
for description in SENSORS:
if (
description.key in coordinator.api.data.available_datapoints
and getattr(coordinator.api.data, description.key) is not None
):
entities.append(HWEnergySensor(coordinator, entry, description))
async_add_entities(entities)
class HWEnergySensor(CoordinatorEntity[DeviceResponseEntry], SensorEntity):
"""Representation of a HomeWizard Sensor."""
def __init__(
self,
coordinator: HWEnergyDeviceUpdateCoordinator,
entry: ConfigEntry,
description: SensorEntityDescription,
) -> None:
"""Initialize Sensor Domain."""
super().__init__(coordinator)
self.entity_description = description
self.entry = entry
# Config attributes.
self._attr_name = f"{entry.title} {description.name}"
self.data_type = description.key
self._attr_unique_id = f"{entry.unique_id}_{description.key}"
# Special case for export, not everyone has solarpanels
# The chance that 'export' is non-zero when you have solar panels is nil
if self.data_type in [
"total_power_export_t1_kwh",
"total_power_export_t2_kwh",
]:
if self.data["data"][self.data_type] == 0:
self._attr_entity_registry_enabled_default = False
@property
def device_info(self) -> DeviceInfo:
"""Return device information."""
return {
"name": self.entry.title,
"manufacturer": "HomeWizard",
"sw_version": self.data["device"].firmware_version,
"model": self.data["device"].product_type,
"identifiers": {(DOMAIN, self.data["device"].serial)},
}
@property
def data(self) -> DeviceResponseEntry:
"""Return data object from DataUpdateCoordinator."""
return self.coordinator.data
@property
def native_value(self) -> StateType:
"""Return state of meter."""
return self.data["data"][self.data_type]
@property
def available(self) -> bool:
"""Return availability of meter."""
return super().available and self.data_type in self.data["data"]