DSMR: Remove Gas derivative sensor (#52147)

This commit is contained in:
Franck Nijhof 2021-06-24 14:25:38 +02:00 committed by GitHub
parent 0e5040d917
commit afa00b7626
No known key found for this signature in database
GPG key ID: 4AEE18F83AFDEB23
2 changed files with 4 additions and 125 deletions

View file

@ -15,12 +15,7 @@ import voluptuous as vol
from homeassistant.components.sensor import PLATFORM_SCHEMA, SensorEntity
from homeassistant.config_entries import SOURCE_IMPORT, ConfigEntry
from homeassistant.const import (
CONF_HOST,
CONF_PORT,
EVENT_HOMEASSISTANT_STOP,
TIME_HOURS,
)
from homeassistant.const import CONF_HOST, CONF_PORT, EVENT_HOMEASSISTANT_STOP
from homeassistant.core import CoreState, HomeAssistant, callback
from homeassistant.helpers import config_validation as cv
from homeassistant.util import Throttle
@ -172,7 +167,7 @@ async def async_setup_entry(
else:
gas_obis = obis_ref.GAS_METER_READING
# Add gas meter reading and derivative for usage
# Add gas meter reading
devices += [
DSMREntity(
"Gas Consumption",
@ -181,15 +176,7 @@ async def async_setup_entry(
gas_obis,
config,
True,
),
DerivativeDSMREntity(
"Hourly Gas Consumption",
DEVICE_NAME_GAS,
config[CONF_SERIAL_ID_GAS],
gas_obis,
config,
False,
),
)
]
async_add_entities(devices)
@ -374,66 +361,3 @@ class DSMREntity(SensorEntity):
return "low"
return None
class DerivativeDSMREntity(DSMREntity):
"""Calculated derivative for values where the DSMR doesn't offer one.
Gas readings are only reported per hour and don't offer a rate only
the current meter reading. This entity converts subsequents readings
into a hourly rate.
"""
_previous_reading = None
_previous_timestamp = None
_state = None
@property
def state(self):
"""Return the calculated current hourly rate."""
return self._state
@property
def force_update(self):
"""Disable force update."""
return False
@property
def should_poll(self):
"""Enable polling."""
return True
async def async_update(self):
"""Recalculate hourly rate if timestamp has changed.
DSMR updates gas meter reading every hour. Along with the new
value a timestamp is provided for the reading. Test if the last
known timestamp differs from the current one then calculate a
new rate for the previous hour.
"""
# check if the timestamp for the object differs from the previous one
timestamp = self.get_dsmr_object_attr("datetime")
if timestamp and timestamp != self._previous_timestamp:
current_reading = self.get_dsmr_object_attr("value")
if self._previous_reading is None:
# Can't calculate rate without previous datapoint
# just store current point
pass
else:
# Recalculate the rate
diff = current_reading - self._previous_reading
timediff = timestamp - self._previous_timestamp
total_seconds = timediff.total_seconds()
self._state = round(float(diff) / total_seconds * 3600, 3)
self._previous_reading = current_reading
self._previous_timestamp = timestamp
@property
def unit_of_measurement(self):
"""Return the unit of measurement of this entity, per hour, if any."""
unit = self.get_dsmr_object_attr("unit")
if unit:
return f"{unit}/{TIME_HOURS}"

View file

@ -13,13 +13,8 @@ from unittest.mock import DEFAULT, MagicMock
from homeassistant import config_entries
from homeassistant.components.dsmr.const import DOMAIN
from homeassistant.components.dsmr.sensor import DerivativeDSMREntity
from homeassistant.components.sensor import DOMAIN as SENSOR_DOMAIN
from homeassistant.const import (
ENERGY_KILO_WATT_HOUR,
VOLUME_CUBIC_METERS,
VOLUME_FLOW_RATE_CUBIC_METERS_PER_HOUR,
)
from homeassistant.const import ENERGY_KILO_WATT_HOUR, VOLUME_CUBIC_METERS
from homeassistant.helpers import entity_registry as er
from homeassistant.setup import async_setup_component
@ -179,46 +174,6 @@ async def test_setup_only_energy(hass, dsmr_connection_fixture):
assert not entry
async def test_derivative():
"""Test calculation of derivative value."""
from dsmr_parser.objects import MBusObject
config = {"platform": "dsmr"}
entity = DerivativeDSMREntity("test", "test_device", "5678", "1.0.0", config, False)
await entity.async_update()
assert entity.state is None, "initial state not unknown"
entity.telegram = {
"1.0.0": MBusObject(
[
{"value": datetime.datetime.fromtimestamp(1551642213)},
{"value": Decimal(745.695), "unit": VOLUME_CUBIC_METERS},
]
)
}
await entity.async_update()
assert entity.state is None, "state after first update should still be unknown"
entity.telegram = {
"1.0.0": MBusObject(
[
{"value": datetime.datetime.fromtimestamp(1551642543)},
{"value": Decimal(745.698), "unit": VOLUME_CUBIC_METERS},
]
)
}
await entity.async_update()
assert (
abs(entity.state - 0.033) < 0.00001
), "state should be hourly usage calculated from first and second update"
assert entity.unit_of_measurement == VOLUME_FLOW_RATE_CUBIC_METERS_PER_HOUR
async def test_v4_meter(hass, dsmr_connection_fixture):
"""Test if v4 meter is correctly parsed."""
(connection_factory, transport, protocol) = dsmr_connection_fixture