diff --git a/packages/control/bat.py b/packages/control/bat.py index dfe643c042..2052de16f7 100644 --- a/packages/control/bat.py +++ b/packages/control/bat.py @@ -8,6 +8,15 @@ log = logging.getLogger(__name__) +@dataclass +class Config: + max_power: float = 0 + + +def config_factory() -> Config: + return Config() + + @dataclass class Get: currents: List[float] = field(default_factory=currents_list_factory, metadata={ @@ -41,6 +50,7 @@ def set_factory() -> Set: @dataclass class BatData: + config: Config = field(default_factory=config_factory) get: Get = field(default_factory=get_factory) set: Set = field(default_factory=set_factory) diff --git a/packages/helpermodules/update_config.py b/packages/helpermodules/update_config.py index 8c196a0751..e79152c803 100644 --- a/packages/helpermodules/update_config.py +++ b/packages/helpermodules/update_config.py @@ -57,7 +57,7 @@ class UpdateConfig: - DATASTORE_VERSION = 116 + DATASTORE_VERSION = 117 valid_topic = [ "^openWB/bat/config/bat_control_permitted$", @@ -71,6 +71,7 @@ class UpdateConfig: "^openWB/bat/config/price_limit$", "^openWB/bat/config/price_charge_activated$", "^openWB/bat/config/charge_limit$", + "^openWB/bat/[0-9]+/config/max_power$", "^openWB/bat/[0-9]+/get/max_charge_power$", "^openWB/bat/[0-9]+/get/max_discharge_power$", "^openWB/bat/[0-9]+/get/state_str$", @@ -3004,3 +3005,14 @@ def upgrade(topic: str, payload) -> Optional[dict]: return {topic: payload} self._loop_all_received_topics(upgrade) self._append_datastore_version(116) + + def upgrade_datastore_117(self) -> None: + def upgrade(topic: str, payload) -> Optional[dict]: + if re.search("^openWB/bat/[0-9]+/get/power$", topic) is not None: + index = get_index(topic) + new_topics = {} + if f"openWB/bat/{index}/config/max_power" not in self.all_received_topics: + new_topics[f"openWB/bat/{index}/config/max_power"] = 0 + return new_topics if new_topics else None + self._loop_all_received_topics(upgrade) + self._append_datastore_version(117) diff --git a/packages/modules/common/store/_inverter.py b/packages/modules/common/store/_inverter.py index 733ff460e2..7acb3dcf9c 100644 --- a/packages/modules/common/store/_inverter.py +++ b/packages/modules/common/store/_inverter.py @@ -50,18 +50,10 @@ def set(self, state: InverterState) -> None: self.delegate.set(state) def update(self) -> None: - state = self.filter_peaks(self.delegate.delegate.state) - state = self.fix_hybrid_values(state) + state = self.fix_hybrid_values(self.delegate.delegate.state) self.delegate.set(state) self.delegate.update() - def filter_peaks(self, state: InverterState) -> InverterState: - inverter = data.data.pv_data[f"pv{self.delegate.delegate.num}"] - max_ac_out = inverter.data.config.max_ac_out - if max_ac_out > 0 and abs(state.power) > max_ac_out: - state.power = max_ac_out if state.power > 0 else -max_ac_out - return state - def fix_hybrid_values(self, state: InverterState) -> InverterState: children = data.data.counter_all_data.get_entry_of_element(self.delegate.delegate.num)["children"] power = state.power diff --git a/packages/modules/common/store/_inverter_test.py b/packages/modules/common/store/_inverter_test.py index 380c0820c3..46b2c58092 100644 --- a/packages/modules/common/store/_inverter_test.py +++ b/packages/modules/common/store/_inverter_test.py @@ -50,33 +50,3 @@ def test_fix_hybrid_values(params): # evaluation assert vars(state) == vars(params.expected_state) - - -FilterPeaksParams = NamedTuple("FilterPeaksParams", [( - "name", str), ("max_ac_out", int), ("input_power", float), ("expected_power", float)]) -filter_peaks_cases = [ - FilterPeaksParams("no_limit", 0, -5000, -5000), # max_ac_out = 0 -> keine Begrenzung - FilterPeaksParams("within_limit", 10000, -5000, -5000), # innerhalb der Grenze - FilterPeaksParams("exceeds_positive", 3000, 5000, 3000), # überschreitet positive Grenze - FilterPeaksParams("exceeds_negative", 3000, -5000, -3000), # überschreitet negative Grenze (behält Vorzeichen) - FilterPeaksParams("at_limit_positive", 5000, 5000, 5000), # genau an der positiven Grenze - FilterPeaksParams("at_limit_negative", 5000, -5000, -5000), # genau an der negativen Grenze -] - - -@pytest.mark.parametrize("params", filter_peaks_cases, ids=[c.name for c in filter_peaks_cases]) -def test_filter_peaks(params): - # setup - mock_inverter = Mock() - mock_inverter.data.config.max_ac_out = params.max_ac_out - data.data.pv_data = {"pv1": mock_inverter} - - purge = PurgeInverterState(delegate=Mock(delegate=Mock(num=1))) - - # execution - input_state = InverterState(power=params.input_power, exported=1000) - result_state = purge.filter_peaks(input_state) - - # evaluation - assert result_state.power == params.expected_power - assert result_state.exported == 1000 # exported sollte unverändert bleiben diff --git a/packages/modules/common/utils/peak_filter.py b/packages/modules/common/utils/peak_filter.py new file mode 100644 index 0000000000..6d2647507c --- /dev/null +++ b/packages/modules/common/utils/peak_filter.py @@ -0,0 +1,93 @@ +import logging +from control import data +from typing import Optional + +from modules.common.fault_state import FaultState + +log = logging.getLogger(__name__) + + +class PeakFilter: + def __init__(self, type: str, component_id: int, fault_state: FaultState): + self.type = type + self.component_id = component_id + self.fault_state = fault_state + self.imported = None + self.exported = None + + def check_values( + self, + power: float, + imported: Optional[float] = None, + exported: Optional[float] = None + ) -> tuple[Optional[float], Optional[float]]: + # setze maximale Leistung je nach Komponente + if self.type == "counter": + counter = data.data.counter_data[f"counter{self.component_id}"] + max_power = counter.data.config.max_total_power + elif self.type == "inverter": + inverter = data.data.pv_data[f"pv{self.component_id}"] + max_power = inverter.data.config.max_ac_out + elif self.type == "bat": + bat = data.data.bat_data[f"bat{self.component_id}"] + max_power = bat.data.config.max_power + else: + raise ValueError(f"Unsupported component type {self.type!r} in PeakFilter") + # prüfe Leistung und importierte/exportierte Energie auf Plausibilität + self.check_power(max_power, power) + return self.check_imported_exported(max_power, imported, exported) + + def check_power(self, max_power: float, power: float) -> None: + # Wenn die Leistung mehr als doppelt so hoch ist wie die + # konfigurierte maximale Leistung, ist sie unplausibel. + if max_power > 0 and abs(power) > 2 * max_power: + raise Exception(f"Peakfilter: Die Leistung von {power / 1000}kW überschreitet die konfigurierte max. " + f"Gesamtleistung von {max_power / 1000}kW um mehr als das Doppelte. " + "Werte werden noch nicht berücksichtigt.") + + def check_imported_exported( + self, + max_power: float, + imported: Optional[float] = None, + exported: Optional[float] = None, + ) -> tuple[Optional[float], Optional[float]]: + if max_power > 0: + # Die erlaubte Abweichung ist doppelt so groß wie die mögliche + # Energiemenge pro Intervall bei maximaler Leistung + control_interval = data.data.general_data.data.control_interval + allowed_deviation = 2 * (control_interval / 3600) * max_power + + imp = self.check_total_energy(imported, self.imported, allowed_deviation) + self.imported = imported + + exp = self.check_total_energy(exported, self.exported, allowed_deviation) + self.exported = exported + return imp, exp + return imported, exported + + def check_total_energy( + self, + total_energy: Optional[float], + previous_total_energy: Optional[float], + allowed_deviation: float + ) -> Optional[float]: + if total_energy is not None: + if previous_total_energy is None: + if allowed_deviation > 0: + log.debug(f"PeakFilter: Vorheriger Wert None, aktueller Zählerwert: {total_energy / 1000 }kWh. " + "Warte einen Regelintervall.") + self.fault_state.warning(f"Peakfilter: {total_energy / 1000}kWh. " + "Die PV-Produktion erscheint höher, als laut Anlagenkonfiguration " + "plausibel ist. Erneute Prüfung im nächsten Regelintervall.") + elif allowed_deviation > 0 and (total_energy - previous_total_energy) > allowed_deviation: + log.debug(f"PeakFilter: Unplausibler Zählerwert: {total_energy / 1000}kWh. " + f"Differenz zum vorherigen Wert: {total_energy - previous_total_energy}Wh. " + f"erlaubte Differenz: {round(allowed_deviation, 2)}Wh.") + self.fault_state.warning(f"Peakfilter: {total_energy / 1000}kWh. " + "Die PV-Produktion erscheint höher, als laut Anlagenkonfiguration plausibel " + "ist. Erneute Prüfung im nächsten Regelintervall.") + else: + log.debug(f"PeakFilter: Zählerwert: {total_energy}Wh innerhalb der zulässigen Grenzen. " + f"Differenz zum vorherigen Wert: {total_energy - previous_total_energy}Wh.") + return total_energy + return None diff --git a/packages/modules/common/utils/test_peak_filter.py b/packages/modules/common/utils/test_peak_filter.py new file mode 100644 index 0000000000..d25b2c43e8 --- /dev/null +++ b/packages/modules/common/utils/test_peak_filter.py @@ -0,0 +1,90 @@ +from dataclasses import dataclass +import pytest +from unittest.mock import MagicMock +from modules.common.utils.peak_filter import PeakFilter +from modules.common.fault_state import FaultState + + +class DummyFaultState(FaultState): + def __init__(self): + self.warnings = [] + + def warning(self, msg): + self.warnings.append(msg) + + +class DummyConfig: + def __init__(self, max_power): + self.max_power = max_power + self.max_total_power = max_power + self.max_ac_out = max_power + + +class DummyData: + def __init__(self, max_power): + self.data = MagicMock() + self.data.config = DummyConfig(max_power) + + +@pytest.fixture(autouse=True) +def patch_data(monkeypatch): + import modules.common.utils.peak_filter as pf + pf.data = MagicMock() + pf.data.data = MagicMock() + pf.data.data.counter_data = {"counter1": DummyData(3000)} + pf.data.data.pv_data = {"pv1": DummyData(2000)} + pf.data.data.bat_data = {"bat1": DummyData(1000)} + pf.data.data.general_data = MagicMock() + pf.data.data.general_data.data = MagicMock() + pf.data.data.general_data.data.control_interval = 10 + yield + + +@dataclass +class Params: + name: str + type: str + previous_imported: float + previous_exported: float + power: float + imported: float + exported: float + expected_imported: float + expected_exported: float + expect_exception: bool = False + + +cases = [ + Params("Power Peak Zähler positiv", "counter", 1000, 500, 11000, 1300, 800, None, None, True), + Params("Power Peak Zähler negativ", "counter", 1000, 500, -11000, 1300, 800, None, None, True), + Params("Power Peak Wechselrichter", "inverter", 1000, 500, 11000, 1005, 505, 1005, 505, True), + Params("Power Peak Speicher positiv", "bat", 1000, 500, 11000, 1005, 505, 1005, 505, True), + Params("Power Peak Speicher negativ", "bat", 1000, 500, -11000, 1005, 505, 1005, 505, True), + Params("Imp/ Exp Zähler - Werte valide", "counter", 1000, 500, 900, 1005, 505, 1005, 505), + Params("Imp/ Exp Wechselrichter - Werte valide", "inverter", 1000, 500, 1500, 1005, 505, 1005, 505), + Params("Imp/ Exp Speicher - Werte valide", "bat", 1000, 500, 400, 1005, 505, 1005, 505), + Params("Imp/ Exp Zähler - Werte invalide", "counter", 1000, 500, 1000, 1300, 800, None, None), + Params("Imp/ Exp Zähler - Import invalide", "counter", 1000, 500, 1000, 1300, 505, None, 505), + Params("Imp/ Exp Zähler - Export invalide", "counter", 1000, 500, 1000, 1005, 800, 1005, None), + Params("Imp/ Exp Wechselrichter - Werte invalide", "inverter", 1000, 500, 1500, 1300, 800, None, None), + Params("Imp/ Exp Wechselrichter - Import invalide", "inverter", 1000, 500, 1500, 1300, 505, None, 505), + Params("Imp/ Exp Wechselrichter - Export invalide", "inverter", 1000, 500, 1500, 1005, 800, 1005, None), + Params("Imp/ Exp Speicher - Werte invalide", "bat", 1000, 500, 400, 1300, 800, None, None), + Params("Imp/ Exp Speicher - Import invalide", "bat", 1000, 500, 400, 1300, 505, None, 505), + Params("Imp/ Exp Speicher - Export invalide", "bat", 1000, 500, 400, 1005, 800, 1005, None), +] + + +@pytest.mark.parametrize("params", cases, ids=[c.name for c in cases]) +def test_check_values_valid(params): + fs = DummyFaultState() + pf = PeakFilter(params.type, 1, fs) + pf.imported = params.previous_imported + pf.exported = params.previous_exported + if params.expect_exception: + with pytest.raises(Exception): + imp, exp = pf.check_values(params.power, params.imported, params.exported) + else: + imp, exp = pf.check_values(params.power, params.imported, params.exported) + assert imp == params.expected_imported + assert exp == params.expected_exported diff --git a/packages/modules/devices/algodue/algodue/bat.py b/packages/modules/devices/algodue/algodue/bat.py index 48fecab95f..b114745baf 100644 --- a/packages/modules/devices/algodue/algodue/bat.py +++ b/packages/modules/devices/algodue/algodue/bat.py @@ -10,6 +10,7 @@ from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self): currents = self.__tcp_client.read_input_registers( @@ -37,6 +39,7 @@ def update(self): powers = self.__tcp_client.read_input_registers(0x1020, [ModbusDataType.FLOAT_32]*3, unit=self.__modbus_id) power = sum(powers) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/algodue/algodue/counter.py b/packages/modules/devices/algodue/algodue/counter.py index 162176b8fc..4ea20a4f75 100644 --- a/packages/modules/devices/algodue/algodue/counter.py +++ b/packages/modules/devices/algodue/algodue/counter.py @@ -10,6 +10,7 @@ from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): frequency = self.__tcp_client.read_input_registers(0x1038, ModbusDataType.FLOAT_32, unit=self.__modbus_id) @@ -42,6 +44,7 @@ def update(self): power_factors = self.__tcp_client.read_input_registers( 0x1018, [ModbusDataType.FLOAT_32]*3, unit=self.__modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/algodue/algodue/inverter.py b/packages/modules/devices/algodue/algodue/inverter.py index 63ad9adca2..5b0b60cd06 100644 --- a/packages/modules/devices/algodue/algodue/inverter.py +++ b/packages/modules/devices/algodue/algodue/inverter.py @@ -10,6 +10,7 @@ from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self): currents = self.__tcp_client.read_input_registers( @@ -37,6 +39,7 @@ def update(self): powers = self.__tcp_client.read_input_registers(0x1020, [ModbusDataType.FLOAT_32]*3, unit=self.__modbus_id) power = sum(powers) + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/alpha_ess/alpha_ess/bat.py b/packages/modules/devices/alpha_ess/alpha_ess/bat.py index c7c062ba7c..a0d9c34fd9 100644 --- a/packages/modules/devices/alpha_ess/alpha_ess/bat.py +++ b/packages/modules/devices/alpha_ess/alpha_ess/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.alpha_ess.alpha_ess.config import AlphaEssBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self) -> None: @@ -49,6 +51,7 @@ def update(self) -> None: soc_reg = self.__tcp_client.read_holding_registers(0x0102, ModbusDataType.INT_16, unit=self.__modbus_id) soc = int(soc_reg * 0.1) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/alpha_ess/alpha_ess/counter.py b/packages/modules/devices/alpha_ess/alpha_ess/counter.py index 46fea67721..7df640d25c 100644 --- a/packages/modules/devices/alpha_ess/alpha_ess/counter.py +++ b/packages/modules/devices/alpha_ess/alpha_ess/counter.py @@ -10,6 +10,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType from modules.common.store import get_counter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,6 +30,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): time.sleep(0.1) @@ -53,6 +55,7 @@ def update(self): 0x0014, [ModbusDataType.UINT_16]*3, unit=self.__modbus_id) frequency = self.__tcp_client.read_holding_registers( 0x001A, ModbusDataType.UINT_16, unit=self.__modbus_id) / 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( currents=currents, imported=imported, diff --git a/packages/modules/devices/alpha_ess/alpha_ess/inverter.py b/packages/modules/devices/alpha_ess/alpha_ess/inverter.py index 1724266f52..944a2a314a 100644 --- a/packages/modules/devices/alpha_ess/alpha_ess/inverter.py +++ b/packages/modules/devices/alpha_ess/alpha_ess/inverter.py @@ -10,6 +10,7 @@ from modules.common.modbus import ModbusDataType, Number from modules.common.simcount._simcounter import SimCounter from modules.common.store import get_inverter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -32,10 +33,12 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: reg_p = self.__version_factory() power = self.__get_power(reg_p) + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/ampere/ampere/bat.py b/packages/modules/devices/ampere/ampere/bat.py index 0b376e0fba..beb5fa00b8 100644 --- a/packages/modules/devices/ampere/ampere/bat.py +++ b/packages/modules/devices/ampere/ampere/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.ampere.ampere.config import AmpereBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,12 +31,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.client = self.kwargs['client'] def update(self) -> None: power = self.client.read_input_registers(535, ModbusDataType.INT_16, unit=self.modbus_id) * -1 soc = self.client.read_input_registers(1339, ModbusDataType.UINT_16, unit=self.modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/ampere/ampere/counter.py b/packages/modules/devices/ampere/ampere/counter.py index b2d456197a..ef40d46518 100644 --- a/packages/modules/devices/ampere/ampere/counter.py +++ b/packages/modules/devices/ampere/ampere/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.ampere.ampere.config import AmpereCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -31,11 +32,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): powers = self.client.read_input_registers(1349, [ModbusDataType.INT_16]*3, unit=self.modbus_id) power = self.client.read_input_registers(1348, ModbusDataType.INT_16, unit=self.modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/ampere/ampere/inverter.py b/packages/modules/devices/ampere/ampere/inverter.py index 67f2d673e6..cbaabf6f7e 100644 --- a/packages/modules/devices/ampere/ampere/inverter.py +++ b/packages/modules/devices/ampere/ampere/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.ampere.ampere.config import AmpereInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -31,6 +32,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: pv1_power = self.client.read_holding_registers(519, ModbusDataType.INT_16, unit=self.modbus_id) * -1 @@ -38,6 +40,7 @@ def update(self) -> None: power = pv1_power + pv2_power + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/avm/avm/counter.py b/packages/modules/devices/avm/avm/counter.py index 2c5ea65678..f5bf7f2348 100644 --- a/packages/modules/devices/avm/avm/counter.py +++ b/packages/modules/devices/avm/avm/counter.py @@ -7,6 +7,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store from modules.devices.avm.avm.config import AvmCounterSetup +from modules.common.utils.peak_filter import PeakFilter class AvmCounter(AbstractCounter): @@ -16,6 +17,7 @@ def __init__(self, component_config: AvmCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, deviceListElementTree: Element): for device in deviceListElementTree: @@ -35,7 +37,7 @@ def update(self, deviceListElementTree: Element): voltages = [float(voltageInfo.text)/1000, 0, 0] # AVM returns Wh imported = float(powermeterBlock.find("energy").text) - + imported, _ = self.peak_filter.check_values(power, imported, None) counter_state = CounterState( imported=imported, exported=0, diff --git a/packages/modules/devices/azzurro_zcs/azzurro_zcs/bat.py b/packages/modules/devices/azzurro_zcs/azzurro_zcs/bat.py index 42c2da0931..65a6eed82a 100644 --- a/packages/modules/devices/azzurro_zcs/azzurro_zcs/bat.py +++ b/packages/modules/devices/azzurro_zcs/azzurro_zcs/bat.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store from modules.devices.azzurro_zcs.azzurro_zcs.config import ZCSBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: # 0x020D Battery charge-discharge power Int16 -10-10 kW accuracy 0,01 kW pos charge, neg discharge @@ -40,6 +42,7 @@ def update(self) -> None: exported = self.client.read_input_registers( 0x0229, ModbusDataType.UINT_16, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/azzurro_zcs/azzurro_zcs/counter.py b/packages/modules/devices/azzurro_zcs/azzurro_zcs/counter.py index 0bb0ecc349..6e83bb3e00 100644 --- a/packages/modules/devices/azzurro_zcs/azzurro_zcs/counter.py +++ b/packages/modules/devices/azzurro_zcs/azzurro_zcs/counter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.azzurro_zcs.azzurro_zcs.config import ZCSCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: # 0x0212 Grid Power Int16 -10-10 kW Unit 0,01kW Feed in/out power @@ -50,6 +52,7 @@ def update(self) -> None: 0x0220, [ModbusDataType.UINT_16] * 10, wordorder=Endian.Little, unit=self.__modbus_id)] + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/azzurro_zcs/azzurro_zcs/inverter.py b/packages/modules/devices/azzurro_zcs/azzurro_zcs/inverter.py index 966084e70f..53e09c0bbc 100644 --- a/packages/modules/devices/azzurro_zcs/azzurro_zcs/inverter.py +++ b/packages/modules/devices/azzurro_zcs/azzurro_zcs/inverter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.azzurro_zcs.azzurro_zcs.config import ZCSInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: # 0x0252 PV1 Power UInt16 0-100kW Unit 0,01kW @@ -45,6 +47,7 @@ def update(self) -> None: exported = self.client.read_input_registers(0x0215, ModbusDataType.UINT_16, wordorder=Endian.Little, unit=self.__modbus_id) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/azzurro_zcs/azzurro_zcs_3p/pv_inverter.py b/packages/modules/devices/azzurro_zcs/azzurro_zcs_3p/pv_inverter.py index 8b878fac4b..9167090f0e 100644 --- a/packages/modules/devices/azzurro_zcs/azzurro_zcs_3p/pv_inverter.py +++ b/packages/modules/devices/azzurro_zcs/azzurro_zcs_3p/pv_inverter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.azzurro_zcs.azzurro_zcs_3p.config import ZCSPvInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -27,6 +28,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power = exported = 0 @@ -42,6 +44,7 @@ def update(self) -> None: except Exception: log.debug("Modbus could not be read.") + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( currents=currents, power=power, diff --git a/packages/modules/devices/batterx/batterx/bat.py b/packages/modules/devices/batterx/batterx/bat.py index 4fedc16f4d..4320c038c7 100644 --- a/packages/modules/devices/batterx/batterx/bat.py +++ b/packages/modules/devices/batterx/batterx/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.common import req +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,11 +31,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self, resp: Dict) -> None: power = resp["1121"]["1"] soc = resp["1074"]["1"] + + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/batterx/batterx/counter.py b/packages/modules/devices/batterx/batterx/counter.py index 8d3fcae70b..06f48bfb0d 100644 --- a/packages/modules/devices/batterx/batterx/counter.py +++ b/packages/modules/devices/batterx/batterx/counter.py @@ -9,6 +9,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, resp: Dict) -> None: power = resp["2913"]["0"] @@ -40,6 +42,7 @@ def update(self, resp: Dict) -> None: log.debug( "Leistungsfaktor sollte laut Doku enthalten sein, ID 2881 kann aber nicht ermittelt werden.") power_factors = None + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/batterx/batterx/external_inverter.py b/packages/modules/devices/batterx/batterx/external_inverter.py index b103b507a5..0103b4b5dd 100644 --- a/packages/modules/devices/batterx/batterx/external_inverter.py +++ b/packages/modules/devices/batterx/batterx/external_inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def get_power(self, resp: Dict) -> float: return resp["2913"]["3"] * -1 @@ -31,6 +33,7 @@ def get_power(self, resp: Dict) -> float: def update(self, resp: Dict) -> None: power = self.get_power(resp) + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/batterx/batterx/inverter.py b/packages/modules/devices/batterx/batterx/inverter.py index 65e110c65c..8be5fd941a 100644 --- a/packages/modules/devices/batterx/batterx/inverter.py +++ b/packages/modules/devices/batterx/batterx/inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,11 +25,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def get_power(self, resp: Dict) -> float: return resp["1634"]["0"] * -1 def get_inverter_state(self, power: float) -> InverterState: + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) return InverterState( diff --git a/packages/modules/devices/byd/byd/bat.py b/packages/modules/devices/byd/byd/bat.py index 3157c95d58..5628420560 100644 --- a/packages/modules/devices/byd/byd/bat.py +++ b/packages/modules/devices/byd/byd/bat.py @@ -11,6 +11,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -29,10 +30,12 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: power, soc = self.get_values() + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/carlo_gavazzi/carlo_gavazzi/counter.py b/packages/modules/devices/carlo_gavazzi/carlo_gavazzi/counter.py index 394d0bb2f0..3c89c65c66 100644 --- a/packages/modules/devices/carlo_gavazzi/carlo_gavazzi/counter.py +++ b/packages/modules/devices/carlo_gavazzi/carlo_gavazzi/counter.py @@ -12,6 +12,7 @@ from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -32,6 +33,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): with self.__tcp_client: @@ -46,6 +48,7 @@ def update(self): if frequency > 100: frequency = frequency / 10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/chint/chint/counter.py b/packages/modules/devices/chint/chint/counter.py index 8b0189d453..93eb52bca6 100644 --- a/packages/modules/devices/chint/chint/counter.py +++ b/packages/modules/devices/chint/chint/counter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.chint.chint.config import CHINTCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -26,6 +27,7 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.__modbus_id = self.component_config.configuration.modbus_id + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): powers = voltages = currents = power_factors = None @@ -55,6 +57,8 @@ def update(self): exported_ep = self.client.read_holding_registers(0x4028, ModbusDataType.FLOAT_32, unit=self.__modbus_id) * ep_ratio + imported_ep, exported_ep = self.peak_filter.check_values(power, imported_ep, exported_ep) + counter_state = CounterState( currents=currents, imported=imported_ep, diff --git a/packages/modules/devices/conftest.py b/packages/modules/devices/conftest.py new file mode 100644 index 0000000000..4f7d604655 --- /dev/null +++ b/packages/modules/devices/conftest.py @@ -0,0 +1,10 @@ +from unittest.mock import Mock +import pytest +from modules.common.utils.peak_filter import PeakFilter + + +@pytest.fixture(autouse=True) +def mock_peak_filter(monkeypatch) -> Mock: + mock = Mock(side_effect=lambda power, imported=None, exported=None: (imported, exported)) + monkeypatch.setattr(PeakFilter, 'check_values', mock) + return mock diff --git a/packages/modules/devices/deye/deye/bat.py b/packages/modules/devices/deye/deye/bat.py index e7623cf975..8dbd8c1c08 100644 --- a/packages/modules/devices/deye/deye/bat.py +++ b/packages/modules/devices/deye/deye/bat.py @@ -6,6 +6,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_bat_value_store from modules.devices.deye.deye.config import DeyeBatSetup from modules.devices.deye.deye.device_type import DeviceType @@ -28,6 +29,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.device_type = DeviceType(self.client.read_holding_registers( 0, ModbusDataType.INT_16, unit=self.component_config.configuration.modbus_id)) @@ -42,8 +44,10 @@ def update(self) -> None: if self.device_type == DeviceType.SINGLE_PHASE_HYBRID: imported = self.client.read_holding_registers(72, ModbusDataType.UINT_16, unit=unit) * 100 exported = self.client.read_holding_registers(74, ModbusDataType.UINT_16, unit=unit) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) elif self.device_type == DeviceType.SINGLE_PHASE_STRING: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: # THREE_PHASE_LV (0x0500, 0x0005), THREE_PHASE_HV (0x0006) @@ -52,6 +56,7 @@ def update(self) -> None: if self.device_type == DeviceType.THREE_PHASE_HV: power = power * 10 soc = self.client.read_holding_registers(588, ModbusDataType.INT_16, unit=unit) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/deye/deye/counter.py b/packages/modules/devices/deye/deye/counter.py index e66d5a4706..349e1e423e 100644 --- a/packages/modules/devices/deye/deye/counter.py +++ b/packages/modules/devices/deye/deye/counter.py @@ -7,6 +7,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_counter_value_store from modules.devices.deye.deye.config import DeyeCounterSetup from modules.devices.deye.deye.device_type import DeviceType @@ -27,6 +28,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.device_type = DeviceType(self.client.read_holding_registers( 0, ModbusDataType.INT_16, unit=self.component_config.configuration.modbus_id)) @@ -42,7 +44,6 @@ def update(self): currents = [0]*3 voltages = [0]*3 power = [0] - imported, exported = self.sim_counter.sim_count(power) elif self.device_type == DeviceType.SINGLE_PHASE_STRING: currents = [ @@ -51,7 +52,6 @@ def update(self): v / 10 for v in self.client.read_holding_registers(70, [ModbusDataType.INT_16]*3, unit=unit)] powers = [currents[i] * voltages[i] for i in range(0, 3)] power = sum(powers) - imported, exported = self.sim_counter.sim_count(power) else: # THREE_PHASE_LV (0x0500, 0x0005), THREE_PHASE_HV (0x0006) currents = [c / 100 for c in self.client.read_holding_registers(613, [ModbusDataType.INT_16]*3, unit=unit)] @@ -59,8 +59,9 @@ def update(self): powers = self.client.read_holding_registers(616, [ModbusDataType.INT_16]*3, unit=unit) power = sum(powers) frequency = self.client.read_holding_registers(609, ModbusDataType.INT_16, unit=unit) / 100 - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( currents=currents, voltages=voltages, diff --git a/packages/modules/devices/deye/deye/inverter.py b/packages/modules/devices/deye/deye/inverter.py index 8688d97b07..29d1fdce00 100644 --- a/packages/modules/devices/deye/deye/inverter.py +++ b/packages/modules/devices/deye/deye/inverter.py @@ -7,6 +7,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_inverter_value_store from modules.devices.deye.deye.config import DeyeInverterSetup from modules.devices.deye.deye.device_type import DeviceType @@ -27,6 +28,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.device_type = DeviceType(self.client.read_holding_registers( 0, ModbusDataType.INT_16, unit=self.component_config.configuration.modbus_id)) @@ -42,6 +44,7 @@ def update(self) -> None: if self.device_type == DeviceType.THREE_PHASE_HV: power = power * 10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/discovergy/discovergy/counter.py b/packages/modules/devices/discovergy/discovergy/counter.py index 14f69ff0ab..a60c48c569 100644 --- a/packages/modules/devices/discovergy/discovergy/counter.py +++ b/packages/modules/devices/discovergy/discovergy/counter.py @@ -4,8 +4,10 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store +from modules.common.utils.peak_filter import PeakFilter from modules.devices.discovergy.discovergy import api from modules.devices.discovergy.discovergy.config import DiscovergyCounterSetup +from modules.common.component_state import CounterState class DiscovergyCounter(AbstractCounter): @@ -15,9 +17,19 @@ def __init__(self, component_config: DiscovergyCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, session: Session): - self.store.set(api.get_last_reading(session, self.component_config.configuration.meter_id)) + reading = api.get_last_reading(session, self.component_config.configuration.meter_id) + + imported, exported = self.peak_filter.check_values(reading.power, reading.imported, reading.exported) + self.store.set(CounterState( + imported=imported, + exported=exported, + power=reading.power, + voltages=reading.voltages, + powers=reading.powers + )) component_descriptor = ComponentDescriptor(configuration_factory=DiscovergyCounterSetup) diff --git a/packages/modules/devices/discovergy/discovergy/inverter.py b/packages/modules/devices/discovergy/discovergy/inverter.py index 18eca9da3f..5d87500897 100644 --- a/packages/modules/devices/discovergy/discovergy/inverter.py +++ b/packages/modules/devices/discovergy/discovergy/inverter.py @@ -5,6 +5,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store +from modules.common.utils.peak_filter import PeakFilter from modules.devices.discovergy.discovergy import api from modules.devices.discovergy.discovergy.config import DiscovergyInverterSetup @@ -16,11 +17,14 @@ def __init__(self, component_config: DiscovergyInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, session: Session): reading = api.get_last_reading(session, self.component_config.configuration.meter_id) + + _, exported = self.peak_filter.check_values(reading.power, None, reading.exported) self.store.set(InverterState( - exported=reading.exported, + exported=exported, power=reading.power, currents=reading.currents )) diff --git a/packages/modules/devices/e3dc/e3dc/bat.py b/packages/modules/devices/e3dc/e3dc/bat.py index 5d4773ba80..834dfbc7da 100644 --- a/packages/modules/devices/e3dc/e3dc/bat.py +++ b/packages/modules/devices/e3dc/e3dc/bat.py @@ -9,6 +9,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_bat_value_store from modules.common.simcount._simcounter import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.devices.e3dc.e3dc.config import E3dcBatSetup log = logging.getLogger(__name__) @@ -37,12 +38,15 @@ def initialize(self) -> None: self.__device_id: int = self.kwargs['device_id'] self.__modbus_id: int = self.kwargs['modbus_id'] self.client: modbus.ModbusTcpClient_ = self.kwargs['client'] - self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) + self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") def update(self) -> None: soc, power = read_bat(self.client, self.__modbus_id) + + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/e3dc/e3dc/counter.py b/packages/modules/devices/e3dc/e3dc/counter.py index 7357d3180c..d7874343a7 100644 --- a/packages/modules/devices/e3dc/e3dc/counter.py +++ b/packages/modules/devices/e3dc/e3dc/counter.py @@ -8,6 +8,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.simcount._simcounter import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType from modules.common.store import get_counter_value_store from modules.devices.e3dc.e3dc.config import E3dcCounterSetup @@ -55,12 +56,15 @@ def initialize(self) -> None: self.__device_id: int = self.kwargs['device_id'] self.__modbus_id: int = self.kwargs['modbus_id'] self.client: modbus.ModbusTcpClient_ = self.kwargs['client'] - self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) + self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") def update(self) -> None: power, powers = read_counter(self.client, self.__modbus_id) + + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/e3dc/e3dc/inverter.py b/packages/modules/devices/e3dc/e3dc/inverter.py index 10914bd25d..307a6f3370 100644 --- a/packages/modules/devices/e3dc/e3dc/inverter.py +++ b/packages/modules/devices/e3dc/e3dc/inverter.py @@ -10,6 +10,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.common.simcount._simcounter import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.devices.e3dc.e3dc.config import E3dcInverterSetup log = logging.getLogger(__name__) @@ -35,14 +36,16 @@ def initialize(self) -> None: self.__device_id: int = self.kwargs['device_id'] self.__modbus_id: int = self.kwargs['modbus_id'] self.client: modbus.ModbusTcpClient_ = self.kwargs['client'] - self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) + self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") def update(self) -> None: pv = read_inverter(self.client, self.__modbus_id) # Im gegensatz zur Implementierung in Version 1.9 wird nicht mehr die PV # Leistung vom WR1 gelesen, da die durch v2.0 separat gehandelt wird + self.peak_filter.check_values(pv) _, pv_exported = self.sim_counter.sim_count(pv) inverter_state = InverterState( power=pv, diff --git a/packages/modules/devices/elgris/elgris/bat.py b/packages/modules/devices/elgris/elgris/bat.py index 5558dd3dc0..9b29191c1e 100644 --- a/packages/modules/devices/elgris/elgris/bat.py +++ b/packages/modules/devices/elgris/elgris/bat.py @@ -9,6 +9,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_bat_value_store +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,14 +26,18 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['tcp_client'] self.__modbus_id: int = self.kwargs['modbus_id'] self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.elgris = Elgris(self.__modbus_id, self.__tcp_client, self.fault_state) self.store = get_bat_value_store(self.component_config.id) def update(self): counter_state = self.elgris.get_counter_state() + imported, exported = self.peak_filter.check_values(counter_state.power, + counter_state.imported, + counter_state.exported) bat_state = BatState( - exported=counter_state.exported, - imported=counter_state.imported, + exported=exported, + imported=imported, power=counter_state.power, currents=counter_state.currents, ) diff --git a/packages/modules/devices/elgris/elgris/counter.py b/packages/modules/devices/elgris/elgris/counter.py index 9ee444cda3..fe19e30fee 100644 --- a/packages/modules/devices/elgris/elgris/counter.py +++ b/packages/modules/devices/elgris/elgris/counter.py @@ -7,6 +7,7 @@ from modules.common.abstract_device import AbstractCounter from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_counter_value_store @@ -24,11 +25,17 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['tcp_client'] self.__modbus_id: int = self.kwargs['modbus_id'] self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) self.elgris = Elgris(self.__modbus_id, self.__tcp_client, self.fault_state) self.store = get_counter_value_store(self.component_config.id) def update(self): counter_state = self.elgris.get_counter_state() + imported, exported = self.peak_filter.check_values(counter_state.power, + counter_state.imported, + counter_state.exported) + counter_state.imported = imported + counter_state.exported = exported self.store.set(counter_state) diff --git a/packages/modules/devices/elgris/elgris/elgris_test.py b/packages/modules/devices/elgris/elgris/elgris_test.py index cd300965e5..7b4b071967 100644 --- a/packages/modules/devices/elgris/elgris/elgris_test.py +++ b/packages/modules/devices/elgris/elgris/elgris_test.py @@ -24,8 +24,9 @@ def setup_modbus_mocks(monkeypatch): def test_elgris_bat(monkeypatch): setup_modbus_mocks(monkeypatch) + elgris_bat = ElgrisBatSetup() device = create_device(Elgris()) - device.add_component(ElgrisBatSetup()) + device.add_component(elgris_bat) store_bat_mock = Mock() monkeypatch.setattr(device.components["component0"], "store", store_bat_mock) diff --git a/packages/modules/devices/elgris/elgris/inverter.py b/packages/modules/devices/elgris/elgris/inverter.py index 9d9b9d45b9..dac9a0775c 100644 --- a/packages/modules/devices/elgris/elgris/inverter.py +++ b/packages/modules/devices/elgris/elgris/inverter.py @@ -9,6 +9,7 @@ from modules.common.abstract_device import AbstractInverter from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,14 +26,18 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['tcp_client'] self.__modbus_id: int = self.kwargs['modbus_id'] self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) self.elgris = Elgris(self.__modbus_id, self.__tcp_client, self.fault_state) self.store = get_inverter_value_store(self.component_config.id) def update(self): counter_state = self.elgris.get_counter_state() + imported, exported = self.peak_filter.check_values(counter_state.power, + counter_state.imported, + counter_state.exported) inverter_state = InverterState( - exported=counter_state.exported, - imported=counter_state.imported, + exported=exported, + imported=imported, power=counter_state.power, currents=counter_state.currents, ) diff --git a/packages/modules/devices/enphase/enphase/bat.py b/packages/modules/devices/enphase/enphase/bat.py index 3dd1cbb4e0..1c704baf01 100644 --- a/packages/modules/devices/enphase/enphase/bat.py +++ b/packages/modules/devices/enphase/enphase/bat.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_bat_value_store from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.devices.enphase.enphase.config import EnphaseBatSetup log = logging.getLogger(__name__) @@ -26,6 +27,7 @@ def initialize(self) -> None: self.__device_id: int = self.kwargs['device_id'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") def update(self, response, live_data: Optional[Dict[str, Any]] = None) -> None: @@ -40,6 +42,7 @@ def update(self, response, live_data: Optional[Dict[str, Any]] = None) -> None: # powers = [bat_data['agg_p_ph_a_mw'] / 1000, # bat_data['agg_p_ph_b_mw'] / 1000, # bat_data['agg_p_ph_c_mw'] / 1000] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( imported=imported, diff --git a/packages/modules/devices/enphase/enphase/counter.py b/packages/modules/devices/enphase/enphase/counter.py index 638682c363..6ae2dd04d5 100644 --- a/packages/modules/devices/enphase/enphase/counter.py +++ b/packages/modules/devices/enphase/enphase/counter.py @@ -6,6 +6,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_counter_value_store from modules.devices.enphase.enphase.config import EnphaseCounterSetup @@ -19,6 +20,7 @@ def __init__(self, component_config: EnphaseCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response: Dict[str, Any], live_data): meter = None @@ -29,9 +31,12 @@ def update(self, response: Dict[str, Any], live_data): if meter is None: # configuration wrong or error raise ValueError("Es konnten keine Daten vom Messgerät gelesen werden.") + imported, exported = self.peak_filter.check_values(meter['activePower'], + meter['actEnergyDlvd'], + meter['actEnergyRcvd']) counter_state = CounterState( - imported=meter['actEnergyDlvd'], - exported=meter['actEnergyRcvd'], + imported=imported, + exported=exported, power=meter['activePower'], powers=[meter['channels'][0]['activePower'], meter['channels'][1]['activePower'], diff --git a/packages/modules/devices/enphase/enphase/inverter.py b/packages/modules/devices/enphase/enphase/inverter.py index b728435943..216fa9c097 100644 --- a/packages/modules/devices/enphase/enphase/inverter.py +++ b/packages/modules/devices/enphase/enphase/inverter.py @@ -6,6 +6,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_inverter_value_store from modules.devices.enphase.enphase.config import EnphaseInverterSetup @@ -19,6 +20,7 @@ def __init__(self, component_config: EnphaseInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict[str, Any], live_data) -> None: meter = None @@ -34,9 +36,12 @@ def update(self, response: Dict[str, Any], live_data) -> None: power = power * -1 else: power = 0 + _, exported = self.peak_filter.check_values(power, + None, + meter['actEnergyDlvd']) inverter_state = InverterState( power=power, - exported=meter['actEnergyDlvd'] + exported=exported ) self.store.set(inverter_state) diff --git a/packages/modules/devices/fems/fems/bat.py b/packages/modules/devices/fems/fems/bat.py index a30981958d..44c84983d0 100644 --- a/packages/modules/devices/fems/fems/bat.py +++ b/packages/modules/devices/fems/fems/bat.py @@ -7,6 +7,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_bat_value_store +from modules.common.utils.peak_filter import PeakFilter from modules.devices.fems.fems.version import FemsVersion, get_version from helpermodules.scale_metric import scale_metric @@ -28,6 +29,7 @@ def initialize(self) -> None: self.session: Session = self.kwargs['session'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) if self.component_config.configuration.num == 1: self._data = "ess0" else: @@ -86,6 +88,7 @@ def update(self) -> None: elif address == "_sum/ConsumptionActivePower": haus = scale_metric(singleValue['value'], singleValue.get('unit'), 'W') power = grid + pv - haus + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/fems/fems/counter.py b/packages/modules/devices/fems/fems/counter.py index e9c0b14e76..f1b7723de2 100644 --- a/packages/modules/devices/fems/fems/counter.py +++ b/packages/modules/devices/fems/fems/counter.py @@ -8,6 +8,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_counter_value_store from modules.devices.fems.fems.version import FemsVersion, get_version @@ -29,6 +30,7 @@ def initialize(self) -> None: self.session: Session = self.kwargs['session'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) self.version = get_version(self.get_data_by_multiple_segement_regex_query) log.debug(f"{self.component_config.name} unterstützt {self.version.value}") @@ -106,6 +108,7 @@ def update(self) -> None: imported = scale_metric(singleValue['value'], singleValue.get('unit'), 'Wh') elif (address == '_sum/GridSellActiveEnergy'): exported = scale_metric(singleValue['value'], singleValue.get('unit'), 'Wh') + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/fems/fems/inverter.py b/packages/modules/devices/fems/fems/inverter.py index 33425bb3e7..5d2f17e0db 100644 --- a/packages/modules/devices/fems/fems/inverter.py +++ b/packages/modules/devices/fems/fems/inverter.py @@ -7,6 +7,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_inverter_value_store from modules.devices.fems.fems.version import FemsVersion, get_version @@ -28,6 +29,7 @@ def initialize(self) -> None: self.session: Session = self.kwargs['session'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) self.version = get_version(self.get_data_by_multiple_segement_regex_query) log.debug(f"{self.component_config.name} unterstützt {self.version.value}") @@ -54,6 +56,7 @@ def update(self) -> None: 'http://'+self.ip_address+':8084/rest/channel/_sum/ProductionActiveEnergy', timeout=2).json() exported = scale_metric(response["value"], response.get("unit"), 'Wh') + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/fox_ess/fox_ess/bat.py b/packages/modules/devices/fox_ess/fox_ess/bat.py index e9d27e69ae..8c8de18283 100644 --- a/packages/modules/devices/fox_ess/fox_ess/bat.py +++ b/packages/modules/devices/fox_ess/fox_ess/bat.py @@ -7,6 +7,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store +from modules.common.utils.peak_filter import PeakFilter from modules.devices.fox_ess.fox_ess.config import FoxEssBatSetup log = logging.getLogger(__name__) @@ -25,6 +26,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -36,6 +38,7 @@ def update(self) -> None: # Entladen in kWh * 0,1 exported = self.client.read_holding_registers(32006, ModbusDataType.UINT_32, unit=unit) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/fox_ess/fox_ess/counter.py b/packages/modules/devices/fox_ess/fox_ess/counter.py index ba96b14221..16d57f8922 100644 --- a/packages/modules/devices/fox_ess/fox_ess/counter.py +++ b/packages/modules/devices/fox_ess/fox_ess/counter.py @@ -1,4 +1,5 @@ from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.fox_ess.fox_ess.config import FoxEssCounterSetup @@ -21,6 +22,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -32,6 +34,7 @@ def update(self) -> None: imported = self.client.read_holding_registers(32018, ModbusDataType.UINT_32, unit=unit) * 100 exported = self.client.read_holding_registers(32015, ModbusDataType.UINT_32, unit=unit) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/fox_ess/fox_ess/inverter.py b/packages/modules/devices/fox_ess/fox_ess/inverter.py index be8b608c43..03e5b1b66e 100644 --- a/packages/modules/devices/fox_ess/fox_ess/inverter.py +++ b/packages/modules/devices/fox_ess/fox_ess/inverter.py @@ -5,6 +5,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.fox_ess.fox_ess.config import FoxEssInverterSetup @@ -23,6 +24,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -33,6 +35,7 @@ def update(self) -> None: # Gesamt Produktion Wechselrichter unsigned integer in kWh * 0,1 exported = self.client.read_holding_registers(32000, ModbusDataType.UINT_32, unit=unit) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported, diff --git a/packages/modules/devices/fronius/fronius/bat.py b/packages/modules/devices/fronius/fronius/bat.py index 528032c6e2..fb965e9b1d 100644 --- a/packages/modules/devices/fronius/fronius/bat.py +++ b/packages/modules/devices/fronius/fronius/bat.py @@ -10,6 +10,7 @@ from modules.common.store import get_bat_value_store from modules.devices.fronius.fronius.config import FroniusBatSetup from modules.devices.fronius.fronius.config import FroniusConfiguration +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: meter_id = str(self.component_config.configuration.meter_id) @@ -52,6 +54,7 @@ def update(self) -> None: # Wenn WR aus bzw. im Standby (keine Antwort), ersetze leeren Wert durch eine 0. soc = 0 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/fronius/fronius/counter_s0.py b/packages/modules/devices/fronius/fronius/counter_s0.py index 6528a168a4..1fd3893865 100644 --- a/packages/modules/devices/fronius/fronius/counter_s0.py +++ b/packages/modules/devices/fronius/fronius/counter_s0.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.fronius.fronius.config import FroniusConfiguration, FroniusS0CounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: session = req.get_http_session() @@ -36,6 +38,7 @@ def update(self) -> None: # Wenn WR aus bzw. im Standby (keine Antwort), ersetze leeren Wert durch eine 0. power = float(response.json()["Body"]["Data"]["Site"]["P_Grid"]) or 0 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/fronius/fronius/counter_sm.py b/packages/modules/devices/fronius/fronius/counter_sm.py index c7adfd6f74..82727c9620 100644 --- a/packages/modules/devices/fronius/fronius/counter_sm.py +++ b/packages/modules/devices/fronius/fronius/counter_sm.py @@ -13,6 +13,7 @@ from modules.common.store import get_counter_value_store from modules.devices.fronius.fronius.config import FroniusConfiguration, MeterLocation from modules.devices.fronius.fronius.config import FroniusSmCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: session = req.get_http_session() @@ -43,6 +45,7 @@ def update(self) -> None: counter_state = self.__update_variant_2(session) else: raise ValueError("Unbekannte Variante: "+str(variant)) + self.peak_filter.check_values(counter_state.power) counter_state.imported, counter_state.exported = self.sim_counter.sim_count(counter_state.power) self.store.set(counter_state) diff --git a/packages/modules/devices/fronius/fronius/inverter.py b/packages/modules/devices/fronius/fronius/inverter.py index b3afaa7eab..eb261e3381 100644 --- a/packages/modules/devices/fronius/fronius/inverter.py +++ b/packages/modules/devices/fronius/fronius/inverter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.fronius.fronius.config import FroniusInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: # Rückgabewert ist die aktuelle Wirkleistung in [W]. @@ -36,6 +38,7 @@ def update(self, response: Dict) -> None: # Ohne PV Produktion liefert der WR 'null', ersetze durch Zahl 0 power = 0 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) self.store.set(InverterState( diff --git a/packages/modules/devices/fronius/fronius/inverter_production_meter.py b/packages/modules/devices/fronius/fronius/inverter_production_meter.py index a806eb1efe..4d23f28f96 100644 --- a/packages/modules/devices/fronius/fronius/inverter_production_meter.py +++ b/packages/modules/devices/fronius/fronius/inverter_production_meter.py @@ -13,6 +13,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.fronius.fronius.config import FroniusConfiguration, MeterLocation from modules.devices.fronius.fronius.config import FroniusProductionMeterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: session = req.get_http_session() @@ -77,6 +79,8 @@ def __update_variant_0_1(self, session: Session) -> InverterState: power = response_json_id["PowerReal_P_Sum"] * -1 voltages = [response_json_id["Voltage_AC_Phase_"+str(num)] for num in range(1, 4)] currents = [powers[i] / voltages[i] for i in range(0, 3)] + + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) return InverterState( currents=currents, @@ -102,6 +106,8 @@ def __update_variant_2(self, session: Session) -> InverterState: power = response_json_id["SMARTMETER_POWERACTIVE_MEAN_SUM_F64"] voltages = [response_json_id["SMARTMETER_VOLTAGE_0"+str(num)+"_F64"] for num in range(1, 4)] currents = [powers[i] / voltages[i] for i in range(0, 3)] + + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) return InverterState( currents=currents, diff --git a/packages/modules/devices/fronius/fronius/inverter_secondary.py b/packages/modules/devices/fronius/fronius/inverter_secondary.py index 10bacae7b9..6e1a6b334b 100644 --- a/packages/modules/devices/fronius/fronius/inverter_secondary.py +++ b/packages/modules/devices/fronius/fronius/inverter_secondary.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.fronius.fronius.config import FroniusSecondaryInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: # Rückgabewert ist die aktuelle Wirkleistung in [W]. @@ -42,6 +44,7 @@ def update(self, response: Dict) -> None: # Ohne PV Produktion liefert der WR 'null', ersetze durch Zahl 0 power = 0 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) self.store.set(InverterState( diff --git a/packages/modules/devices/generic/http/bat.py b/packages/modules/devices/generic/http/bat.py index d42c8060cf..4d6ed07850 100644 --- a/packages/modules/devices/generic/http/bat.py +++ b/packages/modules/devices/generic/http/bat.py @@ -11,6 +11,7 @@ from modules.common.store import get_bat_value_store from modules.devices.generic.http.api import create_request_function, create_request_function_array from modules.devices.generic.http.config import HttpBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.__get_currents = create_request_function_array(self.kwargs['url'], [ self.component_config.configuration.current_l1_path, @@ -45,9 +47,9 @@ def update(self, session: Session) -> None: power = self.__get_power(session) exported = self.__get_exported(session) imported = self.__get_imported(session) + imported, exported = self.peak_filter.check_values(power, imported, exported) if imported is None or exported is None: imported, exported = self.sim_counter.sim_count(power) - bat_state = BatState( currents=self.__get_currents(session), power=power, diff --git a/packages/modules/devices/generic/http/counter.py b/packages/modules/devices/generic/http/counter.py index 2924c7c178..d617179ec9 100644 --- a/packages/modules/devices/generic/http/counter.py +++ b/packages/modules/devices/generic/http/counter.py @@ -11,6 +11,7 @@ from modules.common.store import get_counter_value_store from modules.devices.generic.http.api import create_request_function, create_request_function_array from modules.devices.generic.http.config import HttpCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,6 +30,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) self.__get_power = create_request_function(self.url, self.component_config.configuration.power_path) self.__get_imported = create_request_function(self.url, self.component_config.configuration.imported_path) @@ -43,6 +45,8 @@ def update(self, session: Session) -> None: power = self.__get_power(session) exported = self.__get_exported(session) imported = self.__get_imported(session) + + imported, exported = self.peak_filter.check_values(power, imported, exported) if imported is None or exported is None: imported, exported = self.sim_counter.sim_count(power) diff --git a/packages/modules/devices/generic/http/inverter.py b/packages/modules/devices/generic/http/inverter.py index c542bb7eb3..085e38610f 100644 --- a/packages/modules/devices/generic/http/inverter.py +++ b/packages/modules/devices/generic/http/inverter.py @@ -12,6 +12,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.generic.http.api import create_request_function from modules.devices.generic.http.config import HttpInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) self.__get_power = create_request_function(self.url, self.component_config.configuration.power_path) self.__get_exported = create_request_function(self.url, self.component_config.configuration.exported_path) @@ -40,6 +42,7 @@ def update(self, session: Session) -> None: # for compatibility: in 1.x power URL values are positive! power *= -1 exported = self.__get_exported(session) + _, exported = self.peak_filter.check_values(power, None, exported) if exported is None: _, exported = self.sim_counter.sim_count(power) diff --git a/packages/modules/devices/generic/json/bat.py b/packages/modules/devices/generic/json/bat.py index 5dfc5fe74a..b9ccc6705a 100644 --- a/packages/modules/devices/generic/json/bat.py +++ b/packages/modules/devices/generic/json/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.generic.json.config import JsonBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -34,6 +35,7 @@ def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self._compile_jq_filters() self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self, response) -> None: currents = ( @@ -46,10 +48,12 @@ def update(self, response) -> None: soc = float(self.jq_soc.input(response).first()) if self.jq_soc else 0 if self.jq_imported is None or self.jq_exported is None: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: imported = float(self.jq_imported.input(response).first()) exported = float(self.jq_exported.input(response).first()) + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( currents=currents, diff --git a/packages/modules/devices/generic/json/counter.py b/packages/modules/devices/generic/json/counter.py index d8688097d2..b54108390b 100644 --- a/packages/modules/devices/generic/json/counter.py +++ b/packages/modules/devices/generic/json/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.common.store import get_counter_value_store from modules.devices.generic.json.config import JsonCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -37,6 +38,7 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self._compile_jq_filters() self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response) -> None: power = float(self.jq_power.input(response).first()) @@ -62,10 +64,12 @@ def update(self, response) -> None: ) if self.jq_imported is None or self.jq_exported is None: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: imported = float(self.jq_imported.input(response).first()) exported = float(self.jq_exported.input(response).first()) + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/generic/json/inverter.py b/packages/modules/devices/generic/json/inverter.py index 57e9d24440..b182f82ee3 100644 --- a/packages/modules/devices/generic/json/inverter.py +++ b/packages/modules/devices/generic/json/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.generic.json.config import JsonInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -32,6 +33,7 @@ def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self._compile_jq_filters() self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response) -> None: power = float(self.jq_power.input(response).first()) @@ -44,9 +46,11 @@ def update(self, response) -> None: ) if self.jq_exported is None: + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) else: exported = float(self.jq_exported.input(response).first()) + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/generic/mqtt/bat.py b/packages/modules/devices/generic/mqtt/bat.py index 08d8b94e02..dc21bf07c5 100644 --- a/packages/modules/devices/generic/mqtt/bat.py +++ b/packages/modules/devices/generic/mqtt/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.common.store._battery import get_bat_value_store from modules.devices.generic.mqtt.config import MqttBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def __init__(self, component_config: MqttBatSetup, **kwargs: Any) -> None: def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="bat") + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.store = get_bat_value_store(self.component_config.id) def update(self, received_topics: Dict) -> None: @@ -38,7 +40,9 @@ def parse_received_topics(value: str): received_topics.get(f"{topic_prefix}exported") is not None): imported = received_topics[f"{topic_prefix}imported"] exported = received_topics[f"{topic_prefix}exported"] + imported, exported = self.peak_filter.check_values(power, imported, exported) else: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/generic/mqtt/counter.py b/packages/modules/devices/generic/mqtt/counter.py index 5fc5ad5a88..050f3163b3 100644 --- a/packages/modules/devices/generic/mqtt/counter.py +++ b/packages/modules/devices/generic/mqtt/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.common.store._counter import get_counter_value_store from modules.devices.generic.mqtt.config import MqttCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def __init__(self, component_config: MqttCounterSetup, **kwargs: Any) -> None: def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) self.store = get_counter_value_store(self.component_config.id) def update(self, received_topics: Dict) -> None: @@ -38,9 +40,11 @@ def parse_received_topics(value: str): voltages = parse_received_topics("voltages") if (received_topics.get(f"{topic_prefix}imported") and received_topics.get(f"{topic_prefix}exported")): - imported = received_topics[f"{topic_prefix}imported"] - exported = received_topics[f"{topic_prefix}exported"] + imported, exported = self.peak_filter.check_values(power, + received_topics[f"{topic_prefix}imported"], + received_topics[f"{topic_prefix}exported"]) else: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/generic/mqtt/inverter.py b/packages/modules/devices/generic/mqtt/inverter.py index a29a0980ce..c191a35e90 100644 --- a/packages/modules/devices/generic/mqtt/inverter.py +++ b/packages/modules/devices/generic/mqtt/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.common.store._inverter import get_inverter_value_store from modules.devices.generic.mqtt.config import MqttInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def __init__(self, component_config: MqttInverterSetup, **kwargs: Any) -> None: def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="pv") + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) self.store = get_inverter_value_store(self.component_config.id) def update(self, received_topics: Dict) -> None: @@ -33,6 +35,7 @@ def parse_received_topics(value: str): power = received_topics[f"{topic_prefix}power"] if received_topics.get(f"{topic_prefix}exported") is None: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: exported = received_topics[f"{topic_prefix}exported"] @@ -40,6 +43,7 @@ def parse_received_topics(value: str): imported = 0 else: imported = received_topics[f"{topic_prefix}imported"] + imported, exported = self.peak_filter.check_values(power, imported, exported) currents = parse_received_topics("currents") dc_power = parse_received_topics("dc_power") diff --git a/packages/modules/devices/good_we/good_we/bat.py b/packages/modules/devices/good_we/good_we/bat.py index b23c16d6d7..fd9f41050d 100644 --- a/packages/modules/devices/good_we/good_we/bat.py +++ b/packages/modules/devices/good_we/good_we/bat.py @@ -12,6 +12,7 @@ from modules.common.store import get_bat_value_store from modules.devices.good_we.good_we.config import GoodWeBatSetup from modules.devices.good_we.good_we.version import GoodWeVersion +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -38,6 +39,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self) -> None: @@ -55,9 +57,11 @@ def update(self) -> None: 35206, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 exported = self.__tcp_client.read_holding_registers( 35209, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) else: power = self.__tcp_client.read_holding_registers(35264, ModbusDataType.INT_32, unit=self.__modbus_id)*-1 soc = self.__tcp_client.read_holding_registers(39005, ModbusDataType.UINT_16, unit=self.__modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/good_we/good_we/counter.py b/packages/modules/devices/good_we/good_we/counter.py index 56c1f82e0d..a91535f600 100644 --- a/packages/modules/devices/good_we/good_we/counter.py +++ b/packages/modules/devices/good_we/good_we/counter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter from modules.common.store import get_counter_value_store from modules.devices.good_we.good_we.config import GoodWeCounterSetup from modules.devices.good_we.good_we.version import GoodWeVersion @@ -34,6 +35,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: @@ -61,9 +63,11 @@ def update(self) -> None: 36015, ModbusDataType.FLOAT_32, unit=self.__modbus_id) imported = self.__tcp_client.read_holding_registers( 36017, ModbusDataType.FLOAT_32, unit=self.__modbus_id) + imported, exported = self.peak_filter.check_values(power, imported, exported) else: # v1.0 und v1.1 liefern keine Werte zurueck obwohl Register laut Doku gleich # Alternative Register für die BTC Serie liefern statische Werte + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/good_we/good_we/inverter.py b/packages/modules/devices/good_we/good_we/inverter.py index 10f66a44c1..7da7bf1780 100644 --- a/packages/modules/devices/good_we/good_we/inverter.py +++ b/packages/modules/devices/good_we/good_we/inverter.py @@ -6,6 +6,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType from modules.common.store import get_inverter_value_store from modules.devices.good_we.good_we.config import GoodWeInverterSetup @@ -31,6 +32,7 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: @@ -40,6 +42,7 @@ def update(self) -> None: exported = self.__tcp_client.read_holding_registers( 35191, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/growatt/growatt/bat.py b/packages/modules/devices/growatt/growatt/bat.py index 66054b257f..58436ae343 100644 --- a/packages/modules/devices/growatt/growatt/bat.py +++ b/packages/modules/devices/growatt/growatt/bat.py @@ -3,6 +3,7 @@ from modules.common.abstract_device import AbstractBat from modules.common.component_state import BatState +from modules.common.utils.peak_filter import PeakFilter from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ @@ -28,6 +29,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: if self.version == GrowattVersion.max_series: @@ -55,6 +57,7 @@ def update(self) -> None: exported = self.client.read_input_registers( 3127, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/growatt/growatt/counter.py b/packages/modules/devices/growatt/growatt/counter.py index cc69bd150a..b3ef9b4f11 100644 --- a/packages/modules/devices/growatt/growatt/counter.py +++ b/packages/modules/devices/growatt/growatt/counter.py @@ -5,6 +5,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.growatt.growatt.config import GrowattCounterSetup @@ -28,6 +29,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: if self.version == GrowattVersion.max_series: @@ -66,6 +68,7 @@ def update(self) -> None: exported = self.client.read_input_registers(3073, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 imported = self.client.read_input_registers(3069, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/growatt/growatt/inverter.py b/packages/modules/devices/growatt/growatt/inverter.py index 0044b8f5e9..93376839e0 100644 --- a/packages/modules/devices/growatt/growatt/inverter.py +++ b/packages/modules/devices/growatt/growatt/inverter.py @@ -5,6 +5,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.growatt.growatt.config import GrowattInverterSetup @@ -28,6 +29,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: if self.version == GrowattVersion.max_series: @@ -41,6 +43,7 @@ def update(self) -> None: exported = self.client.read_input_registers( 3053, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/huawei/huawei/bat.py b/packages/modules/devices/huawei/huawei/bat.py index 7e74530e40..34aa25bfe3 100644 --- a/packages/modules/devices/huawei/huawei/bat.py +++ b/packages/modules/devices/huawei/huawei/bat.py @@ -4,6 +4,7 @@ from modules.common.abstract_device import AbstractBat from modules.common.component_state import BatState +from modules.common.utils.peak_filter import PeakFilter from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: if self.type == HuaweiType.SDongle: @@ -42,6 +44,7 @@ def update(self) -> None: time.sleep(1) soc = self.client.read_holding_registers(37760, ModbusDataType.INT_16, unit=self.modbus_id) / 10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/huawei/huawei/counter.py b/packages/modules/devices/huawei/huawei/counter.py index 4c2e440073..13caccb901 100644 --- a/packages/modules/devices/huawei/huawei/counter.py +++ b/packages/modules/devices/huawei/huawei/counter.py @@ -6,6 +6,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: if self.type == HuaweiType.SDongle: @@ -43,6 +45,7 @@ def update(self) -> None: time.sleep(1) power = self.client.read_holding_registers(37113, ModbusDataType.INT_32, unit=self.modbus_id) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/huawei/huawei/inverter.py b/packages/modules/devices/huawei/huawei/inverter.py index 56ada1ce8b..d112bf29f3 100644 --- a/packages/modules/devices/huawei/huawei/inverter.py +++ b/packages/modules/devices/huawei/huawei/inverter.py @@ -6,6 +6,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store @@ -33,12 +34,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: if self.type == HuaweiType.SDongle: time.sleep(1) power = self.client.read_holding_registers(32064, ModbusDataType.INT_32, unit=self.modbus_id) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/huawei/huawei_emma/bat.py b/packages/modules/devices/huawei/huawei_emma/bat.py index cdf43d8a13..58ab9a4633 100644 --- a/packages/modules/devices/huawei/huawei_emma/bat.py +++ b/packages/modules/devices/huawei/huawei_emma/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.huawei.huawei_emma.config import Huawei_EmmaBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,11 +30,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers(30360, ModbusDataType.INT_32, unit=self.modbus_id) soc = self.client.read_holding_registers(30368, ModbusDataType.UINT_16, unit=self.modbus_id) * 0.01 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/huawei/huawei_emma/counter.py b/packages/modules/devices/huawei/huawei_emma/counter.py index 912f70a97e..3eaeed6097 100644 --- a/packages/modules/devices/huawei/huawei_emma/counter.py +++ b/packages/modules/devices/huawei/huawei_emma/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.huawei.huawei_emma.config import Huawei_EmmaCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,12 +30,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: currents = self.client.read_holding_registers(31651, [ModbusDataType.INT_32]*3, unit=self.modbus_id) currents = [val * 0.1 for val in currents] power = self.client.read_holding_registers(31657, ModbusDataType.INT_32, unit=self.modbus_id) - + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/huawei/huawei_emma/inverter.py b/packages/modules/devices/huawei/huawei_emma/inverter.py index 8f0ea76be2..ba14cd41ab 100644 --- a/packages/modules/devices/huawei/huawei_emma/inverter.py +++ b/packages/modules/devices/huawei/huawei_emma/inverter.py @@ -6,9 +6,9 @@ from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState from modules.common.modbus import ModbusDataType, ModbusTcpClient_ -from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.huawei.huawei_emma.config import Huawei_EmmaInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,14 +26,14 @@ def initialize(self) -> None: self.__device_id: int = self.kwargs['device_id'] self.modbus_id: int = self.kwargs['modbus_id'] self.client: ModbusTcpClient_ = self.kwargs['client'] - self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers(30354, ModbusDataType.INT_32, unit=self.modbus_id) * -1 exported = self.client.read_holding_registers(30348, ModbusDataType.UINT_64, unit=self.modbus_id) * 10 - + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/huawei/huawei_smartlogger/bat.py b/packages/modules/devices/huawei/huawei_smartlogger/bat.py index b2349ecad0..58ba47296d 100644 --- a/packages/modules/devices/huawei/huawei_smartlogger/bat.py +++ b/packages/modules/devices/huawei/huawei_smartlogger/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.huawei.huawei_smartlogger.config import Huawei_SmartloggerBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,12 +29,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: modbus_id = self.component_config.configuration.modbus_id power = self.__tcp_client.read_holding_registers(37765, ModbusDataType.INT_32, unit=modbus_id) soc = self.__tcp_client.read_holding_registers(37760, ModbusDataType.INT_16, unit=modbus_id) / 10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/huawei/huawei_smartlogger/counter.py b/packages/modules/devices/huawei/huawei_smartlogger/counter.py index 733d61759f..36da734583 100644 --- a/packages/modules/devices/huawei/huawei_smartlogger/counter.py +++ b/packages/modules/devices/huawei/huawei_smartlogger/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.huawei.huawei_smartlogger.config import Huawei_SmartloggerCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: modbus_id = self.component_config.configuration.modbus_id @@ -36,6 +38,8 @@ def update(self) -> None: voltages = [val / 100 for val in self.client.read_holding_registers( 32260, [ModbusDataType.INT_32] * 3, unit=modbus_id)] powers = self.client.read_holding_registers(32335, [ModbusDataType.INT_32] * 3, unit=modbus_id) + + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( currents=currents, diff --git a/packages/modules/devices/huawei/huawei_smartlogger/inverter.py b/packages/modules/devices/huawei/huawei_smartlogger/inverter.py index 3ad1ce9f1d..3551ac6848 100644 --- a/packages/modules/devices/huawei/huawei_smartlogger/inverter.py +++ b/packages/modules/devices/huawei/huawei_smartlogger/inverter.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.huawei.huawei_smartlogger.config import Huawei_SmartloggerInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -31,11 +32,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: modbus_id = self.component_config.configuration.modbus_id power = self.client.read_holding_registers(32080, ModbusDataType.INT_32, unit=modbus_id) * -1 exported = self.client.read_holding_registers(32106, ModbusDataType.INT_32, unit=modbus_id) * 10 + + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/idm/idm/counter.py b/packages/modules/devices/idm/idm/counter.py index 44ff2ab5b9..45c03d502d 100644 --- a/packages/modules/devices/idm/idm/counter.py +++ b/packages/modules/devices/idm/idm/counter.py @@ -6,6 +6,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store @@ -30,11 +31,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.modbus_id power = self.client.read_input_registers(4122, ModbusDataType.FLOAT_32, wordorder=Endian.Little, unit=unit) * 1000 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/janitza/janitza/bat.py b/packages/modules/devices/janitza/janitza/bat.py index c1e58908b0..b4f4f3d69d 100644 --- a/packages/modules/devices/janitza/janitza/bat.py +++ b/packages/modules/devices/janitza/janitza/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.janitza.janitza.config import JanitzaBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,9 +30,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self): power = self.__tcp_client.read_holding_registers(19026, ModbusDataType.FLOAT_32, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/janitza/janitza/counter.py b/packages/modules/devices/janitza/janitza/counter.py index 5cb2c4f64e..48c0355bdd 100644 --- a/packages/modules/devices/janitza/janitza/counter.py +++ b/packages/modules/devices/janitza/janitza/counter.py @@ -6,6 +6,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: @@ -44,6 +46,7 @@ def update(self) -> None: 19044, [ModbusDataType.FLOAT_32] * 3, unit=self.__modbus_id) frequency = self.__tcp_client.read_holding_registers(19050, ModbusDataType.FLOAT_32, unit=self.__modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/janitza/janitza/inverter.py b/packages/modules/devices/janitza/janitza/inverter.py index 4fd99e6c0c..13573d1e2a 100644 --- a/packages/modules/devices/janitza/janitza/inverter.py +++ b/packages/modules/devices/janitza/janitza/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.janitza.janitza.config import JanitzaInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,9 +30,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self): power = self.__tcp_client.read_holding_registers(19026, ModbusDataType.FLOAT_32, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/kaco/kaco_nh/bat.py b/packages/modules/devices/kaco/kaco_nh/bat.py index 01ca5c7159..471a3faf64 100644 --- a/packages/modules/devices/kaco/kaco_nh/bat.py +++ b/packages/modules/devices/kaco/kaco_nh/bat.py @@ -10,6 +10,7 @@ from modules.common.store import get_bat_value_store from modules.devices.kaco.kaco_nh.config import KacoNHBatSetup from modules.devices.kaco.kaco_nh.config import KacoNHConfiguration +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: response = req.get_http_session().get( @@ -37,6 +39,7 @@ def update(self) -> None: power = int(response["pb"]) * -1 soc = float(response["soc"]) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/kaco/kaco_nh/counter.py b/packages/modules/devices/kaco/kaco_nh/counter.py index f52a6e75b4..1e6ea365be 100644 --- a/packages/modules/devices/kaco/kaco_nh/counter.py +++ b/packages/modules/devices/kaco/kaco_nh/counter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store from modules.devices.kaco.kaco_nh.config import KacoNHConfiguration, KacoNHCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def initialize(self) -> None: self.device_config: KacoNHConfiguration = self.kwargs['device_config'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: response = req.get_http_session().get( @@ -33,6 +35,7 @@ def update(self) -> None: imported = float(response["iet"]) * 100 exported = float(response["oet"]) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/kaco/kaco_nh/inverter.py b/packages/modules/devices/kaco/kaco_nh/inverter.py index ca2d0c075e..e55ca1ca0c 100644 --- a/packages/modules/devices/kaco/kaco_nh/inverter.py +++ b/packages/modules/devices/kaco/kaco_nh/inverter.py @@ -9,6 +9,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.kaco.kaco_nh.config import KacoNHInverterSetup from modules.devices.kaco.kaco_nh.config import KacoNHConfiguration +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.device_config: KacoNHConfiguration = self.kwargs['device_config'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: response = req.get_http_session().get( @@ -34,6 +36,7 @@ def update(self) -> None: power = float(response["pac"]) * -1 exported = float(response["eto"]) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) self.store.set(InverterState( power=power, exported=exported diff --git a/packages/modules/devices/kaco/kaco_tx/inverter.py b/packages/modules/devices/kaco/kaco_tx/inverter.py index d089b3d17f..6398cab163 100644 --- a/packages/modules/devices/kaco/kaco_tx/inverter.py +++ b/packages/modules/devices/kaco/kaco_tx/inverter.py @@ -10,6 +10,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.kaco.kaco_tx.config import KacoInverterSetup from modules.devices.kaco.kaco_tx.scale import create_scaled_reader +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -33,6 +34,7 @@ def initialize(self) -> None: self._read_scaled_int32 = create_scaled_reader( self.__tcp_client, self.component_config.configuration.modbus_id, ModbusDataType.INT_32 ) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read_state()) @@ -46,6 +48,7 @@ def read_state(self): # 40096 | AC Energy scale factor | sunssf exported = self._read_scaled_int32(40094, 1)[0] + _, exported = self.peak_filter.check_values(power, None, exported) return InverterState( power=power, exported=exported diff --git a/packages/modules/devices/kostal/kostal_piko/counter.py b/packages/modules/devices/kostal/kostal_piko/counter.py index 683fbf4129..3be439ae56 100644 --- a/packages/modules/devices/kostal/kostal_piko/counter.py +++ b/packages/modules/devices/kostal/kostal_piko/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.kostal.kostal_piko.config import KostalPikoCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def get_values(self) -> Tuple[float, List[float]]: params = (('dxsEntries', ['83887106', '83887362', '83887618']),) @@ -42,6 +44,8 @@ def get_values(self) -> Tuple[float, List[float]]: def update(self): power, powers = self.get_values() + + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/kostal/kostal_piko/inverter.py b/packages/modules/devices/kostal/kostal_piko/inverter.py index 47ee4e8357..29b21dfb7e 100644 --- a/packages/modules/devices/kostal/kostal_piko/inverter.py +++ b/packages/modules/devices/kostal/kostal_piko/inverter.py @@ -8,6 +8,7 @@ from modules.common.store import get_inverter_value_store from modules.common import req from modules.devices.kostal.kostal_piko.config import KostalPikoInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def initialize(self) -> None: self.ip_address: str = self.kwargs['ip_address'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> Tuple[float, float]: # Die Differenz der Einträge entspricht nicht der Batterieleistung. @@ -37,6 +39,7 @@ def update(self) -> Tuple[float, float]: exported = float(resp["dxsEntries"][1]["value"]) * 1000 + _, exported = self.peak_filter.check_values(power, None, exported) inverter = InverterState( exported=exported, power=power diff --git a/packages/modules/devices/kostal/kostal_piko_ci/counter.py b/packages/modules/devices/kostal/kostal_piko_ci/counter.py index 3552783c8a..204dbf0c74 100644 --- a/packages/modules/devices/kostal/kostal_piko_ci/counter.py +++ b/packages/modules/devices/kostal/kostal_piko_ci/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.kostal.kostal_piko_ci.config import KostalPikoCiCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -35,8 +37,9 @@ def update(self) -> None: powers = [self.client.read_holding_registers( reg, ModbusDataType.FLOAT_32, unit=unit) for reg in [224, 234, 244]] frequency = self.client.read_holding_registers(220, ModbusDataType.FLOAT_32, unit=unit) - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( power=power, powers=powers, diff --git a/packages/modules/devices/kostal/kostal_piko_ci/inverter.py b/packages/modules/devices/kostal/kostal_piko_ci/inverter.py index 2965dfd76b..f026b99f28 100644 --- a/packages/modules/devices/kostal/kostal_piko_ci/inverter.py +++ b/packages/modules/devices/kostal/kostal_piko_ci/inverter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.kostal.kostal_piko_ci.config import KostalPikoCiInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -33,7 +35,7 @@ def update(self) -> None: currents = [self.client.read_holding_registers( reg, ModbusDataType.FLOAT_32, unit=unit) for reg in [154, 160, 166]] exported = self.client.read_holding_registers(320, ModbusDataType.FLOAT_32, unit=unit) - + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, currents=currents, diff --git a/packages/modules/devices/kostal/kostal_piko_old/inverter.py b/packages/modules/devices/kostal/kostal_piko_old/inverter.py index a785aa10b6..e020142651 100644 --- a/packages/modules/devices/kostal/kostal_piko_old/inverter.py +++ b/packages/modules/devices/kostal/kostal_piko_old/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.kostal.kostal_piko_old.config import KostalPikoOldInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: str) -> None: # power may be a string "xxx" when the inverter is offline, so we cannot match as a number @@ -50,8 +52,8 @@ def update(self, response: str) -> None: log.info("Inverter power is not a number! Inverter may be offline. Setting power to 0 W.") power = 0 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) - inverter_state = InverterState( exported=exported, power=power diff --git a/packages/modules/devices/kostal/kostal_plenticore/bat.py b/packages/modules/devices/kostal/kostal_plenticore/bat.py index fef74a1d91..68596e2ff0 100644 --- a/packages/modules/devices/kostal/kostal_plenticore/bat.py +++ b/packages/modules/devices/kostal/kostal_plenticore/bat.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.kostal.kostal_plenticore.config import KostalPlenticoreBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -35,6 +36,7 @@ def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers( @@ -44,8 +46,9 @@ def update(self) -> None: if power < 0: power = self.client.read_holding_registers( 106, ModbusDataType.FLOAT_32, unit=self.modbus_id, wordorder=self.endianess) * -1 - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/kostal/kostal_plenticore/counter.py b/packages/modules/devices/kostal/kostal_plenticore/counter.py index 1c8c5e867a..264b61cadd 100644 --- a/packages/modules/devices/kostal/kostal_plenticore/counter.py +++ b/packages/modules/devices/kostal/kostal_plenticore/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.kostal.kostal_plenticore.config import KostalPlenticoreCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -32,11 +33,11 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers( 252, ModbusDataType.FLOAT_32, unit=self.modbus_id, wordorder=self.endianess) - imported, exported = self.sim_counter.sim_count(power) power_factor = self.client.read_holding_registers( 150, ModbusDataType.FLOAT_32, unit=self.modbus_id, wordorder=self.endianess) currents = [self.client.read_holding_registers( @@ -48,6 +49,8 @@ def update(self) -> None: frequency = self.client.read_holding_registers( 220, ModbusDataType.FLOAT_32, unit=self.modbus_id, wordorder=self.endianess) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( powers=powers, currents=currents, diff --git a/packages/modules/devices/kostal/kostal_plenticore/inverter.py b/packages/modules/devices/kostal/kostal_plenticore/inverter.py index e8904a4d48..17d43aee90 100644 --- a/packages/modules/devices/kostal/kostal_plenticore/inverter.py +++ b/packages/modules/devices/kostal/kostal_plenticore/inverter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.kostal.kostal_plenticore.config import KostalPlenticoreInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -36,6 +37,7 @@ def initialize(self) -> None: "Es kann keine DC-Leistung aus dem Wechselrichter ausgelesen werden, " "möglicherweise kann ein Firmware-Update für den Wechselrichter nötig sein." ) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers( @@ -50,8 +52,9 @@ def update(self) -> None: except Exception: dc_power = None self.fault_state.no_error(self.fault_text) - imported, _ = self.sim_counter.sim_count(power) + _, exported = self.peak_filter.check_values(power, None, exported) + imported, _ = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, exported=exported, diff --git a/packages/modules/devices/kostal/kostal_sem/counter.py b/packages/modules/devices/kostal/kostal_sem/counter.py index f14fbc0dbf..57f3bacdd7 100644 --- a/packages/modules/devices/kostal/kostal_sem/counter.py +++ b/packages/modules/devices/kostal/kostal_sem/counter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_counter_value_store from modules.devices.kostal.kostal_sem.config import KostalSemCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): with self.__tcp_client: @@ -47,7 +49,7 @@ def update(self): power_temp = self.__tcp_client.read_holding_registers(0, [ModbusDataType.UINT_32]*2, unit=self.__modbus_id) power = (power_temp[0] if power_temp[0] >= power_temp[1] else -power_temp[1]) * 0.1 - + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( voltages=voltages, currents=currents, diff --git a/packages/modules/devices/kostal/kostal_steca/inverter.py b/packages/modules/devices/kostal/kostal_steca/inverter.py index b05e3d3089..9c8d2e82d6 100644 --- a/packages/modules/devices/kostal/kostal_steca/inverter.py +++ b/packages/modules/devices/kostal/kostal_steca/inverter.py @@ -12,6 +12,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.kostal.kostal_steca.config import KostalStecaInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -29,6 +30,7 @@ def initialize(self) -> None: self.ip_address: str = self.kwargs['ip_address'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power, exported = self.get_values() @@ -64,7 +66,7 @@ def get_values(self) -> Tuple[float, Optional[float]]: except AttributeError: log.debug("PVkWh: Could not find 'data' in gen.yield.total.chart.js.") exported = None - + _, exported = self.peak_filter.check_values(power, None, exported) return power, exported diff --git a/packages/modules/devices/kostal/kostal_steca/inverter_test.py b/packages/modules/devices/kostal/kostal_steca/inverter_test.py index b0a7f3d0c6..506b5344cb 100644 --- a/packages/modules/devices/kostal/kostal_steca/inverter_test.py +++ b/packages/modules/devices/kostal/kostal_steca/inverter_test.py @@ -30,4 +30,4 @@ def test_get_values(measurements_file, expected_power, requests_mock): # evaluation assert power == expected_power - assert exported == 12306056 + assert exported == 12306056.0 diff --git a/packages/modules/devices/lg/lg/bat.py b/packages/modules/devices/lg/lg/bat.py index a7be8f812e..ff7dbec9ca 100644 --- a/packages/modules/devices/lg/lg/bat.py +++ b/packages/modules/devices/lg/lg/bat.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.lg.lg.config import LgBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self, response) -> None: if 'batconv_power' in response['statistics']: @@ -38,6 +40,7 @@ def update(self, response) -> None: self.fault_state.warning('Speicher-SOC ist nicht numerisch und wird auf 0 gesetzt.') soc = 0 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/lg/lg/counter.py b/packages/modules/devices/lg/lg/counter.py index 747afa4523..5bcd2675ad 100644 --- a/packages/modules/devices/lg/lg/counter.py +++ b/packages/modules/devices/lg/lg/counter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.lg.lg.config import LgCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response) -> None: if 'grid_power' in response['statistics']: @@ -32,6 +34,7 @@ def update(self, response) -> None: power = power*-1 else: power = float(response["statistics"]["grid_power_01kW"]) * 100 # Home 15 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/lg/lg/inverter.py b/packages/modules/devices/lg/lg/inverter.py index 7242c52260..b35ff38035 100644 --- a/packages/modules/devices/lg/lg/inverter.py +++ b/packages/modules/devices/lg/lg/inverter.py @@ -5,6 +5,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.lg.lg.config import LgInverterSetup @@ -24,12 +25,15 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: if 'pcs_pv_total_power' in response['statistics']: power = float(response["statistics"]["pcs_pv_total_power"]) * -1 else: power = float(response["statistics"]["pv_total_power_01kW"]) * -100 # Home 15 + + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( exported=exported, diff --git a/packages/modules/devices/marstek/venus_c_e/bat.py b/packages/modules/devices/marstek/venus_c_e/bat.py index 1f57a668d4..f8186e5f59 100644 --- a/packages/modules/devices/marstek/venus_c_e/bat.py +++ b/packages/modules/devices/marstek/venus_c_e/bat.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.marstek.venus_c_e.config import VenusCEBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def _read_reg(self, addr: int, type_: ModbusDataType) -> Union[int, float]: return self.client.read_holding_registers(addr, type_, unit=self.component_config.configuration.modbus_id) @@ -38,6 +40,7 @@ def update(self) -> None: power = -self._read_reg(32202, ModbusDataType.INT_32) soc = self._read_reg(32104, ModbusDataType.UINT_16) + self.peak_filter.check_values(power) # Marstek Venus has internal counter but it's buggy, hence we cannot use it imported, exported = self.sim_counter.sim_count(power) diff --git a/packages/modules/devices/mtec/mtec/bat.py b/packages/modules/devices/mtec/mtec/bat.py index bbff74c22d..de4501151b 100644 --- a/packages/modules/devices/mtec/mtec/bat.py +++ b/packages/modules/devices/mtec/mtec/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.mtec.mtec.config import MTecBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,6 +31,7 @@ def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -42,8 +44,9 @@ def update(self) -> None: else: power = self.client.read_holding_registers(30258, ModbusDataType.INT_32, unit=unit) * -1 soc = self.client.read_holding_registers(33000, ModbusDataType.UINT_16, unit=unit) / 100 - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/mtec/mtec/counter.py b/packages/modules/devices/mtec/mtec/counter.py index c0b08d3bdd..89da9de270 100644 --- a/packages/modules/devices/mtec/mtec/counter.py +++ b/packages/modules/devices/mtec/mtec/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.mtec.mtec.config import MTecCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -34,8 +36,9 @@ def update(self) -> None: power = self.client.read_holding_registers(11000, ModbusDataType.INT_32, unit=unit) * -1 powers = self.client.read_holding_registers(10994, [ModbusDataType.INT_32]*3, unit=unit) powers = [value * -1 for value in powers] - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/mtec/mtec/inverter.py b/packages/modules/devices/mtec/mtec/inverter.py index 15ddd58dd8..87ec1ab8c2 100644 --- a/packages/modules/devices/mtec/mtec/inverter.py +++ b/packages/modules/devices/mtec/mtec/inverter.py @@ -5,6 +5,7 @@ from modules.common.component_state import InverterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store @@ -27,13 +28,15 @@ def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id power = self.client.read_holding_registers(11028, ModbusDataType.UINT_32, unit=unit) * -1 - _, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, exported=exported, diff --git a/packages/modules/devices/mystrom/mystrom/counter.py b/packages/modules/devices/mystrom/mystrom/counter.py index 17b82538e4..7a5b0d921b 100644 --- a/packages/modules/devices/mystrom/mystrom/counter.py +++ b/packages/modules/devices/mystrom/mystrom/counter.py @@ -5,6 +5,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.mystrom.mystrom.config import MystromCounterSetup @@ -26,12 +27,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, session: Session): resp = session.get(f"http://{self.ip_address}/report").json() power = resp["power"] - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/nibe/nibe/counter.py b/packages/modules/devices/nibe/nibe/counter.py index 8fc69323a9..767f662462 100644 --- a/packages/modules/devices/nibe/nibe/counter.py +++ b/packages/modules/devices/nibe/nibe/counter.py @@ -6,6 +6,7 @@ from modules.common.component_state import CounterState from modules.common.component_type import ComponentDescriptor from modules.common.fault_state import ComponentInfo, FaultState +from modules.common.utils.peak_filter import PeakFilter from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store @@ -28,12 +29,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.component_config.configuration.modbus_id power = self.client.read_input_registers(2166, ModbusDataType.UINT_32, wordorder=Endian.Little, unit=unit) - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/openwb/openwb_flex/bat.py b/packages/modules/devices/openwb/openwb_flex/bat.py index ffa7b5eae2..29eaa4b700 100644 --- a/packages/modules/devices/openwb/openwb_flex/bat.py +++ b/packages/modules/devices/openwb/openwb_flex/bat.py @@ -9,11 +9,11 @@ from modules.common.lovato import Lovato from modules.common.mpm3pm import Mpm3pm from modules.common.sdm import Sdm120 -from modules.common.sdm import Sdm630_72 from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.openwb.openwb_flex.config import BatKitFlexSetup from modules.devices.openwb.openwb_flex.versions import kit_bat_version_factory +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -34,6 +34,7 @@ def initialize(self) -> None: self.__client = factory(self.component_config.configuration.id, self.__tcp_client, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self): # TCP-Verbindung schließen möglichst bevor etwas anderes gemacht wird, um im Fehlerfall zu verhindern, @@ -42,9 +43,8 @@ def update(self): counter_state = self.__client.get_counter_state() power = counter_state.power - if isinstance(self.__client, Sdm630_72): - power = power * -1 if isinstance(self.__client, Lovato) or isinstance(self.__client, Sdm120): + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: imported = counter_state.imported @@ -52,7 +52,7 @@ def update(self): voltages = self.__client.get_voltages() powers, power = self.__client.get_power() - + imported, exported = self.peak_filter.check_values(power, imported, exported) if isinstance(self.__client, Mpm3pm): currents = [powers[i] / voltages[i] for i in range(3)] else: diff --git a/packages/modules/devices/openwb/openwb_flex/counter.py b/packages/modules/devices/openwb/openwb_flex/counter.py index bfc25ed810..1cdd56d44c 100644 --- a/packages/modules/devices/openwb/openwb_flex/counter.py +++ b/packages/modules/devices/openwb/openwb_flex/counter.py @@ -11,6 +11,7 @@ from modules.common.store import get_counter_value_store from modules.devices.openwb.openwb_flex.config import EvuKitFlexSetup from modules.devices.openwb.openwb_flex.versions import kit_counter_version_factory +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -31,6 +32,7 @@ def initialize(self) -> None: self.__client = factory(self.component_config.configuration.id, self.__tcp_client, self.fault_state) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): # TCP-Verbindung schließen möglichst bevor etwas anderes gemacht wird, um im Fehlerfall zu verhindern, @@ -38,9 +40,13 @@ def update(self): with self.__tcp_client: counter_state = self.__client.get_counter_state() - if isinstance(self.__client, Mpm3pm or B23): + if isinstance(self.__client, Mpm3pm) or isinstance(self.__client, B23): counter_state.currents = [counter_state.powers[i] / counter_state.voltages[i] for i in range(3)] + counter_state.imported, counter_state.exported = self.peak_filter.check_values(counter_state.power, + counter_state.imported, + counter_state.exported) else: + self.peak_filter.check_values(counter_state.power) counter_state.imported, counter_state.exported = self.sim_counter.sim_count(counter_state.power) self.store.set(counter_state) diff --git a/packages/modules/devices/openwb/openwb_flex/inverter.py b/packages/modules/devices/openwb/openwb_flex/inverter.py index ccceb7db50..3f8225867a 100644 --- a/packages/modules/devices/openwb/openwb_flex/inverter.py +++ b/packages/modules/devices/openwb/openwb_flex/inverter.py @@ -12,6 +12,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.openwb.openwb_flex.config import PvKitFlexSetup from modules.devices.openwb.openwb_flex.versions import kit_inverter_version_factory +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.simulation = {} self.store = get_inverter_value_store(self.component_config.id) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: """ liest die Werte des Moduls aus. @@ -47,9 +49,10 @@ def update(self) -> None: if power > 10: power = power*-1 if isinstance(self.__client, Lovato) or isinstance(self.__client, Sdm120): + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) else: - exported = counter_state.exported + _, exported = self.peak_filter.check_values(power, None, counter_state.exported) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/orno/orno/counter.py b/packages/modules/devices/orno/orno/counter.py index 6f34f1ede7..3674fbc8bf 100644 --- a/packages/modules/devices/orno/orno/counter.py +++ b/packages/modules/devices/orno/orno/counter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.orno.orno.config import OrnoCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,13 +24,14 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): power = self.client.read_holding_registers( 0x141, ModbusDataType.INT_32, unit=self.component_config.configuration.modbus_id) imported = self.client.read_holding_registers( 0xA001, ModbusDataType.INT_32, unit=self.component_config.configuration.modbus_id) * 10 - + imported, _ = self.peak_filter.check_values(power, imported, None) counter_state = CounterState( imported=imported, exported=0, diff --git a/packages/modules/devices/powerdog/powerdog/counter.py b/packages/modules/devices/powerdog/powerdog/counter.py index 9aa98760c6..3b72f5ede3 100644 --- a/packages/modules/devices/powerdog/powerdog/counter.py +++ b/packages/modules/devices/powerdog/powerdog/counter.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.powerdog.powerdog.config import PowerdogCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,6 +34,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, inverter_power: float) -> None: with self.__tcp_client: @@ -48,6 +50,7 @@ def update(self, inverter_power: float) -> None: power = home_consumption + inverter_power log.debug("Powerdog Hausverbrauch[W]: " + str(home_consumption)) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/powerdog/powerdog/inverter.py b/packages/modules/devices/powerdog/powerdog/inverter.py index 83abb5faeb..e72a3498e7 100644 --- a/packages/modules/devices/powerdog/powerdog/inverter.py +++ b/packages/modules/devices/powerdog/powerdog/inverter.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.powerdog.powerdog.config import PowerdogInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,11 +34,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> float: with self.__tcp_client: power = self.__tcp_client.read_input_registers(40002, ModbusDataType.INT_32, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/powerfox/powerfox/counter.py b/packages/modules/devices/powerfox/powerfox/counter.py index ee572767d2..902b35acbe 100644 --- a/packages/modules/devices/powerfox/powerfox/counter.py +++ b/packages/modules/devices/powerfox/powerfox/counter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store from modules.devices.powerfox.powerfox.config import PowerfoxCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,14 +20,17 @@ def __init__(self, component_config: PowerfoxCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, session: Session) -> None: response = session.get('https://backend.powerfox.energy/api/2.0/my/' + self.component_config.configuration.id + '/current', timeout=3).json() - + imported, exported = self.peak_filter.check_values(float(response['Watt']), + float(response['A_Plus']), + float(response['A_Minus'])) self.store.set(CounterState( - imported=float(response['A_Plus']), - exported=float(response['A_Minus']), + imported=imported, + exported=exported, power=float(response['Watt']) )) diff --git a/packages/modules/devices/powerfox/powerfox/inverter.py b/packages/modules/devices/powerfox/powerfox/inverter.py index 646daf97b4..56e60447b3 100644 --- a/packages/modules/devices/powerfox/powerfox/inverter.py +++ b/packages/modules/devices/powerfox/powerfox/inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.powerfox.powerfox.config import PowerfoxInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,13 +20,18 @@ def __init__(self, component_config: PowerfoxInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, session: Session) -> None: response = session.get('https://backend.powerfox.energy/api/2.0/my/' + self.component_config.configuration.id + '/current', timeout=3).json() + _, exported = self.peak_filter.check_values(float(response['Watt']), + None, + float(response['A_Plus'])) + self.store.set(InverterState( - exported=float(response['A_Plus']), + exported=exported, power=float(response['Watt']) )) diff --git a/packages/modules/devices/qcells/qcells/bat.py b/packages/modules/devices/qcells/qcells/bat.py index f381a7894f..d30c864f81 100644 --- a/packages/modules/devices/qcells/qcells/bat.py +++ b/packages/modules/devices/qcells/qcells/bat.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store from modules.devices.qcells.qcells.config import QCellsBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_input_registers(0x0016, ModbusDataType.INT_16, unit=self.__modbus_id) @@ -34,6 +36,7 @@ def update(self) -> None: exported = self.client.read_input_registers( 0x001D, ModbusDataType.UINT_16, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/qcells/qcells/counter.py b/packages/modules/devices/qcells/qcells/counter.py index 6e5d04eabc..3b40413227 100644 --- a/packages/modules/devices/qcells/qcells/counter.py +++ b/packages/modules/devices/qcells/qcells/counter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_counter_value_store from modules.devices.qcells.qcells.config import QCellsCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_input_registers(0x0046, ModbusDataType.INT_32, wordorder=Endian.Little, @@ -60,6 +62,7 @@ def update(self) -> None: wordorder=Endian.Little, unit=self.__modbus_id )] + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/qcells/qcells/inverter.py b/packages/modules/devices/qcells/qcells/inverter.py index 4d0a638145..3dfcc01a77 100644 --- a/packages/modules/devices/qcells/qcells/inverter.py +++ b/packages/modules/devices/qcells/qcells/inverter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.qcells.qcells.config import QCellsInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power_string1 = (self.client.read_input_registers( @@ -38,6 +40,7 @@ def update(self) -> None: exported = self.client.read_input_registers(0x0094, ModbusDataType.UINT_32, wordorder=Endian.Little, unit=self.__modbus_id) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/rct/rct/bat.py b/packages/modules/devices/rct/rct/bat.py index 5a5fd7643b..bcb5fab3c6 100644 --- a/packages/modules/devices/rct/rct/bat.py +++ b/packages/modules/devices/rct/rct/bat.py @@ -8,6 +8,7 @@ from modules.common.store import get_bat_value_store from modules.devices.rct.rct.config import RctBatSetup from modules.devices.rct.rct.rct_lib import RCT +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,6 +20,7 @@ def __init__(self, component_config: RctBatSetup) -> None: def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self, rct_client: RCT) -> None: my_tab = [] @@ -33,11 +35,12 @@ def update(self, rct_client: RCT) -> None: # read all parameters rct_client.read(my_tab) + imported, exported = self.peak_filter.check_values(watt1.value * -1, watt2.value, watt3.value) bat_state = BatState( power=watt1.value * -1, soc=socx.value * 100, - imported=watt2.value, - exported=watt3.value + imported=imported, + exported=exported ) self.store.set(bat_state) if (stat1.value + stat2.value + stat3.value) > 0: diff --git a/packages/modules/devices/rct/rct/counter.py b/packages/modules/devices/rct/rct/counter.py index 9f75bafbf4..c45628f24a 100644 --- a/packages/modules/devices/rct/rct/counter.py +++ b/packages/modules/devices/rct/rct/counter.py @@ -8,6 +8,7 @@ from modules.common.store import get_counter_value_store from modules.devices.rct.rct.config import RctCounterSetup from modules.devices.rct.rct.rct_lib import RCT +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,6 +20,7 @@ def __init__(self, component_config: RctCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, rct_client: RCT): # generate id list for fast bulk read @@ -41,9 +43,10 @@ def update(self, rct_client: RCT): # read all parameters rct_client.read(my_tab) + imported, exported = self.peak_filter.check_values(power.value, imported.value, exported.value*-1.0) counter_state = CounterState( - imported=imported.value, - exported=exported.value*-1.0, + imported=imported, + exported=exported, power=power.value, frequency=freq.value, powers=[power1.value, power2.value, power3.value], diff --git a/packages/modules/devices/rct/rct/inverter.py b/packages/modules/devices/rct/rct/inverter.py index 026fa3de46..2728a14615 100644 --- a/packages/modules/devices/rct/rct/inverter.py +++ b/packages/modules/devices/rct/rct/inverter.py @@ -6,6 +6,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.rct.rct.config import RctInverterSetup from modules.devices.rct.rct.rct_lib import RCT +from modules.common.utils.peak_filter import PeakFilter class RctInverter(AbstractInverter): @@ -15,6 +16,7 @@ def __init__(self, component_config: RctInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, rct_client: RCT) -> None: my_tab = [] @@ -28,10 +30,12 @@ def update(self, rct_client: RCT) -> None: # read all parameters rct_client.read(my_tab) - + power = (power1.value + power2.value + power3.value) * -1 + exported = (exported1.value + exported2.value + exported3.value) + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( - power=(power1.value + power2.value + power3.value) * -1, - exported=(exported1.value + exported2.value + exported3.value), + power=power, + exported=exported, ) self.store.set(inverter_state) diff --git a/packages/modules/devices/saxpower/saxpower/bat.py b/packages/modules/devices/saxpower/saxpower/bat.py index 887fe74c84..e57a8805b1 100644 --- a/packages/modules/devices/saxpower/saxpower/bat.py +++ b/packages/modules/devices/saxpower/saxpower/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.saxpower.saxpower.config import SaxpowerBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,13 +31,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: # Die beiden Register müssen zwingend zusammen ausgelesen werden, sonst scheitert die zweite Abfrage. soc, power = self.__tcp_client.read_holding_registers(46, [ModbusDataType.INT_16]*2, unit=self.__modbus_id) power = power * -1 + 16384 - + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/saxpower/saxpower/counter.py b/packages/modules/devices/saxpower/saxpower/counter.py index fb5dd4da2a..b015daa4b5 100644 --- a/packages/modules/devices/saxpower/saxpower/counter.py +++ b/packages/modules/devices/saxpower/saxpower/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.saxpower.saxpower.config import SaxpowerCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,10 +30,12 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers(48, ModbusDataType.INT_16, unit=self.__modbus_id) power = power - 16384 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/shelly/shelly/bat.py b/packages/modules/devices/shelly/shelly/bat.py index e80938f35d..dcf9525441 100644 --- a/packages/modules/devices/shelly/shelly/bat.py +++ b/packages/modules/devices/shelly/shelly/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.devices.shelly.shelly.config import ShellyBatSetup from modules.devices.shelly.shelly.constants import ALPHABETICAL_INDEX +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -36,6 +37,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: if self.generation == 1: @@ -84,6 +86,7 @@ def update(self) -> None: meters = status['em1:0'] currents[self.phase-1] = meters['current'] * self.factor power = meters['act_power'] * self.factor # shelly Pro EM Gen 2 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/shelly/shelly/counter.py b/packages/modules/devices/shelly/shelly/counter.py index cb4ec9d8d4..29ddd2ba41 100644 --- a/packages/modules/devices/shelly/shelly/counter.py +++ b/packages/modules/devices/shelly/shelly/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.devices.shelly.shelly.config import ShellyCounterSetup from modules.devices.shelly.shelly.constants import ALPHABETICAL_INDEX +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -36,6 +37,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: power = 0 @@ -125,6 +127,7 @@ def update(self) -> None: power = meters['act_power'] # shelly Pro EM Gen 2 frequency = meters['freq'] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/shelly/shelly/inverter.py b/packages/modules/devices/shelly/shelly/inverter.py index 893f3263a0..c23b70e4a9 100644 --- a/packages/modules/devices/shelly/shelly/inverter.py +++ b/packages/modules/devices/shelly/shelly/inverter.py @@ -10,6 +10,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.devices.shelly.shelly.config import ShellyInverterSetup from modules.devices.shelly.shelly.constants import ALPHABETICAL_INDEX +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -36,6 +37,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power = 0 @@ -83,6 +85,8 @@ def update(self) -> None: meters = status['em1:0'] currents[self.phase-1] = meters['current'] * self.factor power = meters['act_power'] * self.factor # shelly Pro EM Gen 2 + + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/siemens/siemens/bat.py b/packages/modules/devices/siemens/siemens/bat.py index 594856e24a..cd2c2bfebd 100644 --- a/packages/modules/devices/siemens/siemens/bat.py +++ b/packages/modules/devices/siemens/siemens/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.siemens.siemens.config import SiemensBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,12 +31,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: power = self.__tcp_client.read_holding_registers(6, ModbusDataType.INT_32, unit=self.__modbus_id) * -1 soc = int(self.__tcp_client.read_holding_registers(8, ModbusDataType.INT_32, unit=self.__modbus_id)) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/siemens/siemens/counter.py b/packages/modules/devices/siemens/siemens/counter.py index 499692cd44..7960e91def 100644 --- a/packages/modules/devices/siemens/siemens/counter.py +++ b/packages/modules/devices/siemens/siemens/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.siemens.siemens.config import SiemensCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,11 +31,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: power = self.__tcp_client.read_holding_registers(14, ModbusDataType.INT_32, unit=self.__modbus_id) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/siemens/siemens/inverter.py b/packages/modules/devices/siemens/siemens/inverter.py index de765d5ccd..2f01ec66b1 100644 --- a/packages/modules/devices/siemens/siemens/inverter.py +++ b/packages/modules/devices/siemens/siemens/inverter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.siemens.siemens.config import SiemensInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,11 +31,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: power = self.__tcp_client.read_holding_registers(16, ModbusDataType.INT_32, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/siemens/siemens_sentron/bat.py b/packages/modules/devices/siemens/siemens_sentron/bat.py index b1a5d39a0c..58986dd1fa 100644 --- a/packages/modules/devices/siemens/siemens_sentron/bat.py +++ b/packages/modules/devices/siemens/siemens_sentron/bat.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_bat_value_store from modules.devices.siemens.siemens_sentron.config import SiemensSentronBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: @@ -33,6 +35,7 @@ def update(self) -> None: imported = self.__tcp_client.read_holding_registers(801, ModbusDataType.FLOAT_64, unit=self.__modbus_id) exported = self.__tcp_client.read_holding_registers(809, ModbusDataType.FLOAT_64, unit=self.__modbus_id) + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( imported=imported, exported=exported, diff --git a/packages/modules/devices/siemens/siemens_sentron/counter.py b/packages/modules/devices/siemens/siemens_sentron/counter.py index 3d74f9d5f1..b5e6639296 100644 --- a/packages/modules/devices/siemens/siemens_sentron/counter.py +++ b/packages/modules/devices/siemens/siemens_sentron/counter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_counter_value_store from modules.devices.siemens.siemens_sentron.config import SiemensSentronCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: @@ -40,6 +42,7 @@ def update(self) -> None: power_factors = self.__tcp_client.read_holding_registers( 37, [ModbusDataType.FLOAT_32] * 3, unit=self.__modbus_id) + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/siemens/siemens_sentron/inverter.py b/packages/modules/devices/siemens/siemens_sentron/inverter.py index 2cd4d3c038..73fe1393a3 100644 --- a/packages/modules/devices/siemens/siemens_sentron/inverter.py +++ b/packages/modules/devices/siemens/siemens_sentron/inverter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_inverter_value_store from modules.devices.siemens.siemens_sentron.config import SiemensSentronInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,12 +27,14 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: with self.__tcp_client: power = self.__tcp_client.read_holding_registers(65, ModbusDataType.FLOAT_32, unit=self.__modbus_id) * -1 exported = self.__tcp_client.read_holding_registers(809, ModbusDataType.FLOAT_64, unit=self.__modbus_id) + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/sigenergy/sigenergy/bat.py b/packages/modules/devices/sigenergy/sigenergy/bat.py index 8858eb2289..7e5b480dec 100644 --- a/packages/modules/devices/sigenergy/sigenergy/bat.py +++ b/packages/modules/devices/sigenergy/sigenergy/bat.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.sigenergy.sigenergy.config import SigenergyBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -29,6 +30,7 @@ def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self) -> None: @@ -37,8 +39,9 @@ def update(self) -> None: power = self.client.read_holding_registers(30037, ModbusDataType.INT_32, unit=unit) # soc unit 0.1% soc = self.client.read_holding_registers(30014, ModbusDataType.UINT_16, unit=unit) / 10 - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/sigenergy/sigenergy/counter.py b/packages/modules/devices/sigenergy/sigenergy/counter.py index 589d8c06cf..9fa2aea461 100644 --- a/packages/modules/devices/sigenergy/sigenergy/counter.py +++ b/packages/modules/devices/sigenergy/sigenergy/counter.py @@ -7,6 +7,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.sigenergy.sigenergy.config import SigenergyCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,14 +26,16 @@ def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.component_config.configuration.modbus_id powers = self.client.read_holding_registers(30052, [ModbusDataType.INT_32]*3, unit=unit) power = self.client.read_holding_registers(30005, ModbusDataType.INT_32, unit=unit) - imported, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/sigenergy/sigenergy/inverter.py b/packages/modules/devices/sigenergy/sigenergy/inverter.py index 3ceffcf844..073f0cf8a9 100644 --- a/packages/modules/devices/sigenergy/sigenergy/inverter.py +++ b/packages/modules/devices/sigenergy/sigenergy/inverter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.sigenergy.sigenergy.config import SigenergyInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,13 +27,15 @@ def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id power = self.client.read_holding_registers(30035, ModbusDataType.INT_32, unit=unit) * -1 - _, exported = self.sim_counter.sim_count(power) + self.peak_filter.check_values(power) + _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, exported=exported, diff --git a/packages/modules/devices/sma/sma_sunny_boy/bat.py b/packages/modules/devices/sma/sma_sunny_boy/bat.py index 6d03cd8e60..6e3f1aafdb 100644 --- a/packages/modules/devices/sma/sma_sunny_boy/bat.py +++ b/packages/modules/devices/sma/sma_sunny_boy/bat.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusTcpClient_, ModbusDataType from modules.common.store import get_bat_value_store from modules.devices.sma.sma_sunny_boy.config import SmaSunnyBoyBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -28,6 +29,7 @@ def initialize(self) -> None: self.__tcp_client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def read(self) -> BatState: unit = self.component_config.configuration.modbus_id @@ -47,7 +49,7 @@ def read(self) -> BatState: raise ValueError(f'Batterie lieferte nicht plausible Werte. Export: {exported}, Import: {imported}. ', 'Sobald die Batterie geladen/entladen wird sollte sich dieser Wert ändern, ', 'andernfalls kann ein Defekt vorliegen.') - + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/sma/sma_sunny_boy/bat_smart_energy.py b/packages/modules/devices/sma/sma_sunny_boy/bat_smart_energy.py index 080a2b7eb6..9fd1af9ebe 100644 --- a/packages/modules/devices/sma/sma_sunny_boy/bat_smart_energy.py +++ b/packages/modules/devices/sma/sma_sunny_boy/bat_smart_energy.py @@ -9,6 +9,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.component_state import BatState from modules.common.abstract_device import AbstractBat +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -44,6 +45,7 @@ def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.last_mode = 'Undefined' self.inverter_type = None + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read()) @@ -83,11 +85,14 @@ def read(self) -> BatState: 'andernfalls kann ein Defekt vorliegen.' ) + imported, exported = self.peak_filter.check_values(power, + values["Battery_ChargedEnergy"], + values["Battery_DischargedEnergy"]) bat_state = BatState( power=power, soc=values["Battery_SoC"], - exported=values["Battery_DischargedEnergy"], - imported=values["Battery_ChargedEnergy"] + exported=exported, + imported=imported ) if self.inverter_type is None: self.inverter_type = values["Inverter_Type"] diff --git a/packages/modules/devices/sma/sma_sunny_boy/bat_tesvolt.py b/packages/modules/devices/sma/sma_sunny_boy/bat_tesvolt.py index ca348e1708..2eadfe6db1 100644 --- a/packages/modules/devices/sma/sma_sunny_boy/bat_tesvolt.py +++ b/packages/modules/devices/sma/sma_sunny_boy/bat_tesvolt.py @@ -10,6 +10,7 @@ from modules.common.simcount._simcounter import SimCounter from modules.common.store import get_bat_value_store from modules.devices.sma.sma_sunny_boy.config import SmaTesvoltBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,10 +31,12 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: soc = self.__tcp_client.read_input_registers(1056, ModbusDataType.INT_32, unit=25) / 10 power = self.__tcp_client.read_input_registers(1012, ModbusDataType.INT_32, unit=25) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/sma/sma_sunny_boy/counter.py b/packages/modules/devices/sma/sma_sunny_boy/counter.py index 4c3e641770..c2605704af 100644 --- a/packages/modules/devices/sma/sma_sunny_boy/counter.py +++ b/packages/modules/devices/sma/sma_sunny_boy/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.sma.sma_sunny_boy.config import SmaSunnyBoyCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.component_config.configuration.modbus_id @@ -39,6 +41,7 @@ def update(self): else: power = exp * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/sma/sma_sunny_boy/inverter.py b/packages/modules/devices/sma/sma_sunny_boy/inverter.py index c391d9aabf..907889c28d 100644 --- a/packages/modules/devices/sma/sma_sunny_boy/inverter.py +++ b/packages/modules/devices/sma/sma_sunny_boy/inverter.py @@ -12,6 +12,7 @@ from modules.devices.sma.sma_sunny_boy.config import SmaSunnyBoyInverterSetup from modules.devices.sma.sma_sunny_boy.inv_version import SmaInverterVersion from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -38,6 +39,7 @@ def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="Wechselrichter") + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read()) @@ -99,13 +101,13 @@ def read(self) -> InverterState: 'Sobald PV Ertrag vorhanden ist sollte sich dieser Wert ändern, ' 'andernfalls kann ein Defekt vorliegen.' ) - + _, exported = self.peak_filter.check_values(power_total * -1, None, energy) imported, _ = self.sim_counter.sim_count(power_total * -1) inverter_state = InverterState( power=power_total * -1, dc_power=dc_power * -1, - exported=energy, + exported=exported, imported=imported ) if 'currents' in locals(): diff --git a/packages/modules/devices/sma/sma_sunny_island/bat.py b/packages/modules/devices/sma/sma_sunny_island/bat.py index fbf58abf9c..9720c7873c 100644 --- a/packages/modules/devices/sma/sma_sunny_island/bat.py +++ b/packages/modules/devices/sma/sma_sunny_island/bat.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_bat_value_store from modules.devices.sma.sma_sunny_island.config import SmaSunnyIslandBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def read(self) -> BatState: unit = self.component_config.configuration.modbus_id @@ -34,6 +36,7 @@ def read(self) -> BatState: power = self.__tcp_client.read_holding_registers(30775, ModbusDataType.INT_32, unit=unit) * -1 imported, exported = self.__tcp_client.read_holding_registers(30595, [ModbusDataType.INT_32]*2, unit=unit) + imported, exported = self.peak_filter.check_values(power, imported, exported) return BatState( power=power, soc=soc, diff --git a/packages/modules/devices/sma/sma_webbox/inverter.py b/packages/modules/devices/sma/sma_webbox/inverter.py index 3447f884ac..c98498193b 100644 --- a/packages/modules/devices/sma/sma_webbox/inverter.py +++ b/packages/modules/devices/sma/sma_webbox/inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.sma.sma_webbox.config import SmaWebboxInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def initialize(self) -> None: self.ip_address: str = self.kwargs['ip_address'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read()) @@ -30,10 +32,13 @@ def update(self) -> None: def read(self) -> InverterState: data = {'RPC': '{"version": "1.0","proc": "GetPlantOverview","id": "1","format": "JSON"}'} response = req.get_http_session().post(f'http://{self.ip_address}/rpc', data=data, timeout=3).json() + power = -int(response["result"]["overview"][0]["value"]) + exported = float(response["result"]["overview"][2]["value"]) * 1000 + _, exported = self.peak_filter.check_values(power, None, exported) return InverterState( - exported=float(response["result"]["overview"][2]["value"]) * 1000, - power=-int(response["result"]["overview"][0]["value"]) + exported=exported, + power=power ) diff --git a/packages/modules/devices/smart_me/smart_me/counter.py b/packages/modules/devices/smart_me/smart_me/counter.py index 3a4c9f0db3..75a107b9df 100644 --- a/packages/modules/devices/smart_me/smart_me/counter.py +++ b/packages/modules/devices/smart_me/smart_me/counter.py @@ -9,6 +9,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store from modules.devices.smart_me.smart_me.config import SmartMeCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -20,6 +21,7 @@ def __init__(self, component_config: SmartMeCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, session: Session) -> None: def parse_phase_values(key: str) -> List[float]: @@ -37,10 +39,14 @@ def parse_phase_values(key: str) -> List[float]: if powers[0] == 0: powers[0] = response["ActivePower"] + imported = response["CounterReadingImport"] * 1000 + exported = response["CounterReadingExport"] * 1000 + power = response["ActivePower"] * 1000 + imported, exported = self.peak_filter.check_values(power, imported, exported) self.store.set(CounterState( - imported=response["CounterReadingImport"] * 1000, - exported=response["CounterReadingExport"] * 1000, - power=response["ActivePower"] * 1000, + imported=imported, + exported=exported, + power=power, powers=powers, currents=currents, power_factors=parse_phase_values("PowerFactorL"), diff --git a/packages/modules/devices/smart_me/smart_me/inverter.py b/packages/modules/devices/smart_me/smart_me/inverter.py index 6db8543b5e..e14867c7c3 100644 --- a/packages/modules/devices/smart_me/smart_me/inverter.py +++ b/packages/modules/devices/smart_me/smart_me/inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.smart_me.smart_me.config import SmartMeInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,14 +20,18 @@ def __init__(self, component_config: SmartMeInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, session: Session) -> None: response = session.get('https://smart-me.com:443/api/Devices/' + self.component_config.configuration.id, timeout=3).json() + exported = response["CounterReadingExport"] * 1000 + power = response["ActivePower"] * 1000 + _, exported = self.peak_filter.check_values(power, None, exported) self.store.set(InverterState( - exported=response["CounterReadingExport"] * 1000, - power=response["ActivePower"] * 1000, + exported=exported, + power=power, )) diff --git a/packages/modules/devices/smartfox/smartfox/counter.py b/packages/modules/devices/smartfox/smartfox/counter.py index 5950c7eb01..683bd13406 100644 --- a/packages/modules/devices/smartfox/smartfox/counter.py +++ b/packages/modules/devices/smartfox/smartfox/counter.py @@ -10,6 +10,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_counter_value_store from modules.devices.smartfox.smartfox.config import SmartfoxCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -27,6 +28,7 @@ def initialize(self) -> None: self.ip_address: int = self.kwargs['ip_address'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: def get_xml_text(attribute_value: str) -> str: @@ -54,10 +56,14 @@ def get_xml_text(attribute_value: str) -> str: # Leistungsfaktor ist nach dem Firmwareupgrade auf EM2 00.01.03.06 (04-2021) # nicht mehr in der values.xml daher fix auf 1 + imported = float((get_xml_text("energyValue"))[:-4]) * 1000 + exported = float((get_xml_text("eToGridValue"))[:-4]) * 1000 + power = float((get_xml_text("detailsPowerValue"))[:-2]) + imported, exported = self.peak_filter.check_values(power, imported, exported) self.store.set(CounterState( - imported=float((get_xml_text("energyValue"))[:-4]) * 1000, - exported=float((get_xml_text("eToGridValue"))[:-4]) * 1000, - power=float((get_xml_text("detailsPowerValue"))[:-2]), + imported=imported, + exported=exported, + power=power, powers=[float(get_xml_text(key)[:-2]) for key in ["powerL1Value", "powerL2Value", "powerL3Value"]], voltages=[float(get_xml_text(key)[:-2]) for key in ["voltageL1Value", "voltageL2Value", "voltageL3Value"]], currents=[float(get_xml_text(key)[:-2]) for key in ["ampereL1Value", "ampereL2Value", "ampereL3Value"]] diff --git a/packages/modules/devices/sofar/sofar/bat.py b/packages/modules/devices/sofar/sofar/bat.py index 334ddc10db..76bb8779b4 100644 --- a/packages/modules/devices/sofar/sofar/bat.py +++ b/packages/modules/devices/sofar/sofar/bat.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store from modules.devices.sofar.sofar.config import SofarBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: # 0x900D High 8 bits: the number of battery packs in parallel @@ -45,6 +47,7 @@ def update(self) -> None: exported = self.client.read_holding_registers( 0x069A, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/sofar/sofar/counter.py b/packages/modules/devices/sofar/sofar/counter.py index ae0ac2d5f2..ec9e28b997 100644 --- a/packages/modules/devices/sofar/sofar/counter.py +++ b/packages/modules/devices/sofar/sofar/counter.py @@ -8,6 +8,7 @@ from modules.common.component_type import ComponentDescriptor from modules.common.component_state import CounterState from modules.common.abstract_device import AbstractCounter +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): # 0x0485 ActivePower_output_total Int16 in kW accuracy 0,01 discharge + charge - @@ -47,6 +49,7 @@ def update(self): # 0x068F Energy_Purchase_Total UInt32 in kwH accuracy 0,01 imported = self.client.read_holding_registers(0x068E, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/sofar/sofar/inverter.py b/packages/modules/devices/sofar/sofar/inverter.py index 6c1f873c84..361778e056 100644 --- a/packages/modules/devices/sofar/sofar/inverter.py +++ b/packages/modules/devices/sofar/sofar/inverter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.sofar.sofar.config import SofarInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,12 +26,14 @@ def initialize(self) -> None: self.__modbus_id: int = self.kwargs['modbus_id'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: # 0x05C4 Power_PV_Total UINT16 in kW accuracy 0,1 power = self.client.read_holding_registers(0x05C4, ModbusDataType.UINT_16, unit=self.__modbus_id) * -100 exported = self.client.read_holding_registers(0x0686, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/solakon/solakon_one/bat.py b/packages/modules/devices/solakon/solakon_one/bat.py index 4d8d2c5342..fbecb2a031 100644 --- a/packages/modules/devices/solakon/solakon_one/bat.py +++ b/packages/modules/devices/solakon/solakon_one/bat.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store from modules.devices.solakon.solakon_one.config import SolakonOneBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -25,6 +26,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -39,6 +41,7 @@ def update(self) -> None: # gesamte DC Entladung der Batterie in Wh exported = self.client.read_holding_registers(39609, ModbusDataType.UINT_32, unit=unit) * 10 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/solakon/solakon_one/inverter.py b/packages/modules/devices/solakon/solakon_one/inverter.py index 130bb10e1b..c6c0440c8b 100644 --- a/packages/modules/devices/solakon/solakon_one/inverter.py +++ b/packages/modules/devices/solakon/solakon_one/inverter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.solakon.solakon_one.config import SolakonOneInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -31,6 +33,7 @@ def update(self) -> None: # Gesamte DC PV Produktion in Wh exported = self.client.read_holding_registers(39601, ModbusDataType.UINT_32, unit=unit) * 10 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/solar_log/solar_log/counter.py b/packages/modules/devices/solar_log/solar_log/counter.py index 82abc683cb..d8f2c702c3 100644 --- a/packages/modules/devices/solar_log/solar_log/counter.py +++ b/packages/modules/devices/solar_log/solar_log/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.solar_log.solar_log.config import SolarLogCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -27,11 +28,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: self.store_values(self.get_power(response)) def store_values(self, power) -> None: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) self.store.set(CounterState( diff --git a/packages/modules/devices/solar_log/solar_log/inverter.py b/packages/modules/devices/solar_log/solar_log/inverter.py index 07b4698f1b..de03bfc730 100644 --- a/packages/modules/devices/solar_log/solar_log/inverter.py +++ b/packages/modules/devices/solar_log/solar_log/inverter.py @@ -8,6 +8,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.solar_log.solar_log.config import SolarLogInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -20,14 +21,18 @@ def __init__(self, def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: self.store.set(self.get_values(response)) def get_values(self, response: Dict) -> InverterState: + power = -abs(float(response["801"]["170"]["101"])) + exported = float(response["801"]["170"]["109"]) + _, exported = self.peak_filter.check_values(power, None, exported) return InverterState( - exported=float(response["801"]["170"]["109"]), - power=-abs(float(response["801"]["170"]["101"])) + exported=exported, + power=power ) diff --git a/packages/modules/devices/solar_view/solar_view/counter.py b/packages/modules/devices/solar_view/solar_view/counter.py index 08e3e2a65d..daef9fc444 100644 --- a/packages/modules/devices/solar_view/solar_view/counter.py +++ b/packages/modules/devices/solar_view/solar_view/counter.py @@ -8,6 +8,7 @@ from modules.common.store import get_counter_value_store from modules.devices.solar_view.solar_view.api import request from modules.devices.solar_view.solar_view.config import SolarViewCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,6 +20,7 @@ def __init__(self, component_config: SolarViewCounterSetup) -> None: def initialize(self) -> None: self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, ip_address: str, port: int, timeout: int) -> None: exported_values = request(ip_address, port, timeout, '21*') @@ -28,6 +30,7 @@ def update(self, ip_address: str, port: int, timeout: int) -> None: imported = 1000 * int(values[9]) power = -1 * int(values[10]) + imported, exported = self.peak_filter.check_values(power, imported, exported) if len(values) > 20: self.store.set(CounterState( imported=imported, diff --git a/packages/modules/devices/solar_view/solar_view/inverter.py b/packages/modules/devices/solar_view/solar_view/inverter.py index d57d4bc876..b354aef842 100644 --- a/packages/modules/devices/solar_view/solar_view/inverter.py +++ b/packages/modules/devices/solar_view/solar_view/inverter.py @@ -8,6 +8,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.solar_view.solar_view.api import request from modules.devices.solar_view.solar_view.config import SolarViewInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -19,12 +20,17 @@ def __init__(self, component_config: SolarViewInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, ip_address: str, port: int, timeout: int) -> None: values = request(ip_address, port, timeout, self.component_config.configuration.command) + + power = -1 * int(values[10]) + exported = 1000 * int(values[9]) + _, exported = self.peak_filter.check_values(power, None, exported) self.store.set(InverterState( - exported=1000 * int(values[9]), - power=-1 * int(values[10]) + exported=exported, + power=power )) diff --git a/packages/modules/devices/solar_watt/solar_watt/bat.py b/packages/modules/devices/solar_watt/solar_watt/bat.py index bfe1e8a4c1..16b37d3862 100644 --- a/packages/modules/devices/solar_watt/solar_watt/bat.py +++ b/packages/modules/devices/solar_watt/solar_watt/bat.py @@ -10,6 +10,7 @@ from modules.common.store import get_bat_value_store from modules.devices.solar_watt.solar_watt.api import parse_value from modules.devices.solar_watt.solar_watt.config import SolarWattBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self, response: Dict, energy_manager: bool) -> None: if energy_manager: @@ -39,6 +41,7 @@ def update(self, response: Dict, energy_manager: bool) -> None: else: power = response["FData"]["IBat"] * response["FData"]["VBat"] * -1 soc = response["SData"]["SoC"] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) self.store.set(BatState( imported=imported, diff --git a/packages/modules/devices/solar_watt/solar_watt/counter.py b/packages/modules/devices/solar_watt/solar_watt/counter.py index 6ca53ea90b..fe15601cc9 100644 --- a/packages/modules/devices/solar_watt/solar_watt/counter.py +++ b/packages/modules/devices/solar_watt/solar_watt/counter.py @@ -10,6 +10,7 @@ from modules.common.store import get_counter_value_store from modules.devices.solar_watt.solar_watt.api import parse_value from modules.devices.solar_watt.solar_watt.config import SolarWattCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response: Dict, energy_manager: bool) -> None: if energy_manager: @@ -36,6 +38,7 @@ def update(self, response: Dict, energy_manager: bool) -> None: power = power_consumed - power_out else: power = int(response["FData"]["PGrid"]) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) self.store.set(CounterState( imported=imported, diff --git a/packages/modules/devices/solar_watt/solar_watt/inverter.py b/packages/modules/devices/solar_watt/solar_watt/inverter.py index 28c14ee47a..e24d314031 100644 --- a/packages/modules/devices/solar_watt/solar_watt/inverter.py +++ b/packages/modules/devices/solar_watt/solar_watt/inverter.py @@ -10,6 +10,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.solar_watt.solar_watt.api import parse_value from modules.devices.solar_watt.solar_watt.config import SolarWattInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -28,9 +29,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response: Dict) -> None: power = parse_value(response, "PowerProduced") * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) self.store.set(InverterState( exported=exported, diff --git a/packages/modules/devices/solar_world/solar_world/counter.py b/packages/modules/devices/solar_world/solar_world/counter.py index b6885a1404..1ff19b5ea0 100644 --- a/packages/modules/devices/solar_world/solar_world/counter.py +++ b/packages/modules/devices/solar_world/solar_world/counter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.solar_world.solar_world.config import SolarWorldCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,9 +25,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response): power = response["PowerIn"] - response["PowerOut"] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/solar_world/solar_world/inverter.py b/packages/modules/devices/solar_world/solar_world/inverter.py index 3eefa6f404..affd769e49 100644 --- a/packages/modules/devices/solar_world/solar_world/inverter.py +++ b/packages/modules/devices/solar_world/solar_world/inverter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.solar_world.solar_world.config import SolarWorldInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response) -> None: try: @@ -31,6 +33,7 @@ def update(self, response) -> None: except ValueError: # wenn eManager aus bzw. keine Antwort ersetze leeren Wert durch eine 0 power = 0 + self.peak_filter.check_values(power) exported = self.sim_counter.sim_count(power)[1] inverter_state = InverterState( diff --git a/packages/modules/devices/solaredge/solaredge/bat.py b/packages/modules/devices/solaredge/solaredge/bat.py index e61897c877..c9669abde6 100644 --- a/packages/modules/devices/solaredge/solaredge/bat.py +++ b/packages/modules/devices/solaredge/solaredge/bat.py @@ -17,6 +17,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.solaredge.solaredge.config import SolaredgeBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -59,12 +60,14 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read_state()) def read_state(self): power, soc = self.get_values() + self.peak_filter.check_values(power) imported, exported = self.get_imported_exported(power) return BatState( power=power, diff --git a/packages/modules/devices/solaredge/solaredge/counter.py b/packages/modules/devices/solaredge/solaredge/counter.py index be654e2ef4..117d408af7 100644 --- a/packages/modules/devices/solaredge/solaredge/counter.py +++ b/packages/modules/devices/solaredge/solaredge/counter.py @@ -12,6 +12,7 @@ from modules.devices.solaredge.solaredge.config import SolaredgeCounterSetup from modules.devices.solaredge.solaredge.scale import scale_registers from modules.devices.solaredge.solaredge.meter import SolaredgeMeterRegisters, set_component_registers +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -31,6 +32,7 @@ def initialize(self) -> None: self.registers = SolaredgeMeterRegisters() self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) components = list(self.kwargs['components'].values()) components.append(self) @@ -56,10 +58,14 @@ def update(self): resp = self.__tcp_client.read_holding_registers_bulk( self.registers.currents, 52, mapping=reg_mapping, unit=self.component_config.configuration.modbus_id) + imported = scale_registers(resp[self.registers.imported], resp[self.registers.imp_exp_scale]) + exported = scale_registers(resp[self.registers.exported], resp[self.registers.imp_exp_scale]) + power = scale_registers(resp[self.registers.power], resp[self.registers.powers_scale]) * -1 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( - imported=scale_registers(resp[self.registers.imported], resp[self.registers.imp_exp_scale]), - exported=scale_registers(resp[self.registers.exported], resp[self.registers.imp_exp_scale]), - power=scale_registers(resp[self.registers.power], resp[self.registers.powers_scale]) * -1, + imported=imported, + exported=exported, + power=power, powers=[-power for power in scale_registers(resp[self.registers.powers], resp[self.registers.powers_scale])], voltages=scale_registers(resp[self.registers.voltages], resp[self.registers.voltages_scale]), diff --git a/packages/modules/devices/solaredge/solaredge/external_inverter.py b/packages/modules/devices/solaredge/solaredge/external_inverter.py index 668b3b9d42..a8621b8796 100644 --- a/packages/modules/devices/solaredge/solaredge/external_inverter.py +++ b/packages/modules/devices/solaredge/solaredge/external_inverter.py @@ -12,6 +12,7 @@ from modules.devices.solaredge.solaredge.config import SolaredgeExternalInverterSetup from modules.devices.solaredge.solaredge.scale import scale_registers from modules.devices.solaredge.solaredge.meter import SolaredgeMeterRegisters, set_component_registers +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,6 +34,7 @@ def initialize(self) -> None: self.registers = SolaredgeMeterRegisters(self.component_config.configuration.meter_id) self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) components = list(self.kwargs['components'].values()) components.append(self) @@ -54,9 +56,13 @@ def read_state(self) -> InverterState: self.registers.currents, 52, mapping=reg_mapping, unit=self.component_config.configuration.modbus_id) factor = self.component_config.configuration.factor + + exported = scale_registers(resp[self.registers.exported], resp[self.registers.imp_exp_scale]) + power = scale_registers(resp[self.registers.power], resp[self.registers.powers_scale]) * factor + _, exported = self.peak_filter.check_values(power, None, exported) return InverterState( - exported=scale_registers(resp[self.registers.exported], resp[self.registers.imp_exp_scale]), - power=scale_registers(resp[self.registers.power], resp[self.registers.powers_scale]) * factor, + exported=exported, + power=power, currents=scale_registers(resp[self.registers.currents], resp[self.registers.currents_scale]) ) diff --git a/packages/modules/devices/solaredge/solaredge/inverter.py b/packages/modules/devices/solaredge/solaredge/inverter.py index 9009a26a10..0a17de1be4 100644 --- a/packages/modules/devices/solaredge/solaredge/inverter.py +++ b/packages/modules/devices/solaredge/solaredge/inverter.py @@ -12,6 +12,7 @@ from modules.devices.solaredge.solaredge.config import SolaredgeInverterSetup from modules.devices.solaredge.solaredge.scale import scale_registers from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -53,6 +54,7 @@ def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(self.kwargs['device_id'], self.component_config.id, prefix="Wechselrichter") + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: self.store.set(self.read_state()) @@ -62,6 +64,7 @@ def read_state(self): Register.CURRENTS, 30, mapping=self.REG_MAPPING, unit=self.component_config.configuration.modbus_id) power = scale_registers(resp[Register.POWER], resp[Register.POWER_SCALE]) * -1 + self.peak_filter.check_values(power) imported, _ = self.sim_counter.sim_count(power) return InverterState( diff --git a/packages/modules/devices/solarmax/solarmax/bat.py b/packages/modules/devices/solarmax/solarmax/bat.py index 16fe483c76..944ec31129 100644 --- a/packages/modules/devices/solarmax/solarmax/bat.py +++ b/packages/modules/devices/solarmax/solarmax/bat.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.solarmax.solarmax.config import SolarmaxBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -31,11 +32,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id power = self.client.read_input_registers(114, ModbusDataType.INT_32, unit=unit, wordorder=Endian.Little) soc = self.client.read_input_registers(122, ModbusDataType.INT_16, unit=unit) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/solarmax/solarmax/counter_maxstorage.py b/packages/modules/devices/solarmax/solarmax/counter_maxstorage.py index 8d524f4856..33a3afeaf8 100644 --- a/packages/modules/devices/solarmax/solarmax/counter_maxstorage.py +++ b/packages/modules/devices/solarmax/solarmax/counter_maxstorage.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.solarmax.solarmax.config import SolarmaxMsCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,10 +31,12 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id power = self.client.read_input_registers(118, ModbusDataType.INT_32, unit=unit, wordorder=Endian.Little) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/solarmax/solarmax/inverter.py b/packages/modules/devices/solarmax/solarmax/inverter.py index b2ea19d55f..a7f79328b6 100644 --- a/packages/modules/devices/solarmax/solarmax/inverter.py +++ b/packages/modules/devices/solarmax/solarmax/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.solarmax.solarmax.config import SolarmaxInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,11 +30,13 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: power = self.client.read_holding_registers(4151, ModbusDataType.UINT_32, unit=self.component_config.configuration.modbus_id) * -1 power = power / 10 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/solarmax/solarmax/inverter_maxstorage.py b/packages/modules/devices/solarmax/solarmax/inverter_maxstorage.py index d8d9722380..79cce5cd5d 100644 --- a/packages/modules/devices/solarmax/solarmax/inverter_maxstorage.py +++ b/packages/modules/devices/solarmax/solarmax/inverter_maxstorage.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.solarmax.solarmax.config import SolarmaxMsInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,10 +31,12 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id power = self.client.read_input_registers(120, ModbusDataType.INT_32, unit=unit, wordorder=Endian.Little) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/solax/solax/bat.py b/packages/modules/devices/solax/solax/bat.py index 59b89cadb6..75c25eb46a 100644 --- a/packages/modules/devices/solax/solax/bat.py +++ b/packages/modules/devices/solax/solax/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.solax.solax.config import SolaxBatSetup, Solax +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.device_config.configuration.modbus_id @@ -35,7 +37,7 @@ def update(self) -> None: # kein Speicher für Versionen G2 und G4 power = self.__tcp_client.read_input_registers(0x0016, ModbusDataType.INT_16, unit=unit) soc = self.__tcp_client.read_input_registers(0x001C, ModbusDataType.UINT_16, unit=unit) - + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/solax/solax/counter.py b/packages/modules/devices/solax/solax/counter.py index f25f556e51..c792b76551 100644 --- a/packages/modules/devices/solax/solax/counter.py +++ b/packages/modules/devices/solax/solax/counter.py @@ -11,6 +11,7 @@ from modules.common.store import get_counter_value_store from modules.devices.solax.solax.config import SolaxCounterSetup, Solax from modules.devices.solax.solax.version import SolaxVersion +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.device_config = self.kwargs['device_config'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.device_config.configuration.modbus_id @@ -60,7 +62,7 @@ def update(self): powers = None exported, imported = [value * 100 for value in self.__tcp_client.read_input_registers( 0x042F, [ModbusDataType.UINT_32] * 2, wordorder=Endian.Little, unit=unit)] - + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/solax/solax/inverter.py b/packages/modules/devices/solax/solax/inverter.py index eb3a7129e6..9f9c7b992d 100644 --- a/packages/modules/devices/solax/solax/inverter.py +++ b/packages/modules/devices/solax/solax/inverter.py @@ -11,6 +11,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.solax.solax.config import SolaxInverterSetup, Solax from modules.devices.solax.solax.version import SolaxVersion +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.device_config = self.kwargs['device_config'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.device_config.configuration.modbus_id @@ -47,6 +49,7 @@ def update(self) -> None: exported = self.__tcp_client.read_input_registers( 0x042B, ModbusDataType.UINT_32, wordorder=Endian.Little, unit=unit) * 100 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/solis/solis/bat.py b/packages/modules/devices/solis/solis/bat.py index 9c1cb5578b..d9ae1562e0 100644 --- a/packages/modules/devices/solis/solis/bat.py +++ b/packages/modules/devices/solis/solis/bat.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_bat_value_store from modules.devices.solis.solis.config import SolisBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -26,6 +27,7 @@ def initialize(self) -> None: self.client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -37,6 +39,7 @@ def update(self) -> None: # Entladen in kWh exported = self.client.read_input_registers(33165, ModbusDataType.UINT_32, unit=unit) * 1000 + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/solis/solis/counter.py b/packages/modules/devices/solis/solis/counter.py index 8a500f94b9..b43271ba93 100644 --- a/packages/modules/devices/solis/solis/counter.py +++ b/packages/modules/devices/solis/solis/counter.py @@ -7,6 +7,7 @@ from modules.common.store import get_counter_value_store from modules.devices.solis.solis.config import SolisCounterSetup from modules.devices.solis.solis.version import SolisVersion +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -26,6 +27,7 @@ def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.version = self.kwargs['version'] self.client = self.kwargs['client'] + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.component_config.configuration.modbus_id @@ -40,6 +42,7 @@ def update(self): imported = self.client.read_input_registers(3283 + register_offset, ModbusDataType.UINT_32, unit=unit) * 10 exported = self.client.read_input_registers(3285 + register_offset, ModbusDataType.UINT_32, unit=unit) * 10 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/solis/solis/inverter.py b/packages/modules/devices/solis/solis/inverter.py index 9e18df42c6..532af9d317 100644 --- a/packages/modules/devices/solis/solis/inverter.py +++ b/packages/modules/devices/solis/solis/inverter.py @@ -8,6 +8,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.solis.solis.config import SolisInverterSetup from modules.devices.solis.solis.version import SolisVersion +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.version: SolisVersion = self.kwargs['version'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -36,6 +38,7 @@ def update(self) -> None: power = self.client.read_input_registers(33057, ModbusDataType.UINT_32, unit=unit) * -1 exported = self.client.read_input_registers(33029, ModbusDataType.UINT_32, unit=unit) * 1000 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/sonnen/sonnenbatterie/api.py b/packages/modules/devices/sonnen/sonnenbatterie/api.py index 752e850e9c..a27adfc87c 100644 --- a/packages/modules/devices/sonnen/sonnenbatterie/api.py +++ b/packages/modules/devices/sonnen/sonnenbatterie/api.py @@ -5,6 +5,7 @@ from modules.common import req from modules.common.component_state import BatState, CounterState, InverterState from modules.common.simcount import SimCounter +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -34,7 +35,7 @@ def __read(self, device_endpoint: str = 'battery') -> dict: f'http://{self.host}:7979/rest/devices/{device_endpoint}', timeout=5).json() - def update_battery(self, sim_counter: SimCounter) -> BatState: + def update_battery(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> BatState: """ Updates the battery state by reading data from the REST API. Returns: @@ -45,6 +46,7 @@ def update_battery(self, sim_counter: SimCounter) -> BatState: battery_export_power = int(battery_state["M34"]) battery_import_power = int(battery_state["M35"]) battery_power = battery_import_power - battery_export_power + peak_filter.check_values(battery_power) imported, exported = sim_counter.sim_count(battery_power) return BatState(power=battery_power, soc=battery_soc, @@ -79,18 +81,19 @@ def __read_element(self, device: str, element: str) -> str: response.encoding = 'utf-8' return response.text.strip(" \n\r") - def update_inverter(self, sim_counter: SimCounter) -> InverterState: + def update_inverter(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> InverterState: """ Updates the inverter state by reading data from the REST API v2. Returns: InverterState: The updated inverter state. """ pv_power = -int(float(self.__read_element(device="battery", element="M03"))) + peak_filter.check_values(pv_power) _, exported = sim_counter.sim_count(pv_power) return InverterState(exported=exported, power=pv_power) - def update_grid_counter(self, sim_counter: SimCounter) -> CounterState: + def update_grid_counter(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> CounterState: """ Updates the grid counter state by reading data from the REST API v2. Returns: @@ -99,12 +102,13 @@ def update_grid_counter(self, sim_counter: SimCounter) -> CounterState: grid_export_power = int(float(self.__read_element(device="battery", element="M38"))) grid_import_power = int(float(self.__read_element(device="battery", element="M39"))) grid_power = grid_import_power - grid_export_power # export power must be negative + peak_filter.check_values(grid_power) imported, exported = sim_counter.sim_count(grid_power) return CounterState(power=grid_power, imported=imported, exported=exported) - def update_battery(self, sim_counter: SimCounter) -> BatState: + def update_battery(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> BatState: """ Updates the battery state by reading data from the REST API v2. Returns: @@ -114,6 +118,7 @@ def update_battery(self, sim_counter: SimCounter) -> BatState: battery_export_power = int(float(self.__read_element(device="battery", element="M01"))) battery_import_power = int(float(self.__read_element(device="battery", element="M02"))) battery_power = battery_import_power - battery_export_power + peak_filter.check_values(battery_power) imported, exported = sim_counter.sim_count(battery_power) return BatState(power=battery_power, soc=battery_soc, @@ -340,7 +345,7 @@ def power_limit_controllable(self) -> bool: """ return self.api_version == JsonApiVersion.V2 and self.auth_token is not None - def update_battery(self, sim_counter: SimCounter) -> BatState: + def update_battery(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> BatState: """ Updates the battery state by reading data from the JSON API. Returns: @@ -357,6 +362,7 @@ def update_battery(self, sim_counter: SimCounter) -> BatState: currents = [float(battery_state[f"Sac{phase}"]) / battery_ac_voltage if battery_state.get(f"Sac{phase}") else None for phase in range(1, 4)] + peak_filter.check_values(battery_power) imported, exported = sim_counter.sim_count(battery_power) return BatState(power=battery_power, currents=currents if None not in currents else None, @@ -364,7 +370,7 @@ def update_battery(self, sim_counter: SimCounter) -> BatState: imported=imported, exported=exported) - def update_grid_counter(self, sim_counter: SimCounter) -> CounterState: + def update_grid_counter(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> CounterState: """ Updates the grid counter state by reading data from the JSON API. Returns: @@ -374,6 +380,7 @@ def update_grid_counter(self, sim_counter: SimCounter) -> CounterState: grid_power = -counter_state["GridFeedIn_W"] grid_voltage = counter_state["Uac"] grid_frequency = counter_state["Fac"] + peak_filter.check_values(grid_power) imported, exported = sim_counter.sim_count(grid_power) return CounterState(power=grid_power, voltages=[grid_voltage]*3, @@ -381,7 +388,7 @@ def update_grid_counter(self, sim_counter: SimCounter) -> CounterState: imported=imported, exported=exported) - def update_inverter(self, sim_counter: SimCounter) -> InverterState: + def update_inverter(self, sim_counter: SimCounter, peak_filter: PeakFilter) -> InverterState: """ Updates the inverter state by reading data from the JSON API. Returns: @@ -390,6 +397,7 @@ def update_inverter(self, sim_counter: SimCounter) -> InverterState: if self.api_version == JsonApiVersion.V1: inverter_state = self.__read_status() pv_power = -inverter_state["Production_W"] + peak_filter.check_values(pv_power) _, exported = sim_counter.sim_count(pv_power) return InverterState(exported=exported, power=pv_power) diff --git a/packages/modules/devices/sonnen/sonnenbatterie/bat.py b/packages/modules/devices/sonnen/sonnenbatterie/bat.py index bbf321b7fb..c7520a9733 100644 --- a/packages/modules/devices/sonnen/sonnenbatterie/bat.py +++ b/packages/modules/devices/sonnen/sonnenbatterie/bat.py @@ -10,6 +10,7 @@ from modules.devices.sonnen.sonnenbatterie.api import JsonApi, JsonApiVersion, RestApi1, RestApi2 from modules.devices.sonnen.sonnenbatterie.config import SonnenbatterieBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -45,10 +46,11 @@ def initialize(self) -> None: self.api = JsonApi(host=self.__device_address, api_version=JsonApiVersion.V2 if self.__device_variant == 3 else JsonApiVersion.V1, auth_token=self.__api_v2_token if self.__device_variant == 3 else None) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self) -> None: - self.store.set(self.api.update_battery(sim_counter=self.sim_counter)) + self.store.set(self.api.update_battery(sim_counter=self.sim_counter, peak_filter=self.peak_filter)) def set_power_limit(self, power_limit: Optional[int]) -> None: if power_limit is None: diff --git a/packages/modules/devices/sonnen/sonnenbatterie/counter.py b/packages/modules/devices/sonnen/sonnenbatterie/counter.py index ab4c154c52..cf8625ffaa 100644 --- a/packages/modules/devices/sonnen/sonnenbatterie/counter.py +++ b/packages/modules/devices/sonnen/sonnenbatterie/counter.py @@ -10,6 +10,7 @@ from modules.devices.sonnen.sonnenbatterie.api import JsonApi, RestApi2, JsonApiVersion from modules.devices.sonnen.sonnenbatterie.config import SonnenbatterieCounterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -44,9 +45,10 @@ def initialize(self) -> None: self.api = JsonApi(host=self.__device_address, api_version=JsonApiVersion.V2 if self.__device_variant == 3 else JsonApiVersion.V1, auth_token=self.__api_v2_token if self.__device_variant == 3 else None) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self) -> None: - self.store.set(self.api.update_grid_counter(sim_counter=self.sim_counter)) + self.store.set(self.api.update_grid_counter(sim_counter=self.sim_counter, peak_filter=self.peak_filter)) component_descriptor = ComponentDescriptor(configuration_factory=SonnenbatterieCounterSetup) diff --git a/packages/modules/devices/sonnen/sonnenbatterie/inverter.py b/packages/modules/devices/sonnen/sonnenbatterie/inverter.py index 446420297e..68679b3efc 100644 --- a/packages/modules/devices/sonnen/sonnenbatterie/inverter.py +++ b/packages/modules/devices/sonnen/sonnenbatterie/inverter.py @@ -10,6 +10,7 @@ from modules.devices.sonnen.sonnenbatterie.api import JsonApi, RestApi2, JsonApiVersion from modules.devices.sonnen.sonnenbatterie.config import SonnenbatterieInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -38,6 +39,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) if self.__device_variant == 2: self.api = RestApi2(host=self.__device_address) else: @@ -46,7 +48,7 @@ def initialize(self) -> None: auth_token=self.__api_v2_token if self.__device_variant == 3 else None) def update(self) -> None: - self.store.set(self.api.update_inverter(sim_counter=self.sim_counter)) + self.store.set(self.api.update_inverter(sim_counter=self.sim_counter, peak_filter=self.peak_filter)) component_descriptor = ComponentDescriptor(configuration_factory=SonnenbatterieInverterSetup) diff --git a/packages/modules/devices/studer/studer/bat.py b/packages/modules/devices/studer/studer/bat.py index 707e7814fd..730e90cd3a 100644 --- a/packages/modules/devices/studer/studer/bat.py +++ b/packages/modules/devices/studer/studer/bat.py @@ -9,6 +9,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_bat_value_store from modules.devices.studer.studer.config import StuderBatSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -24,6 +25,7 @@ def initialize(self) -> None: self.__tcp_client: modbus.ModbusTcpClient_ = self.kwargs['client'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: unit = self.component_config.configuration.modbus_id @@ -34,6 +36,7 @@ def update(self) -> None: exported = self.__tcp_client.read_input_registers(16, ModbusDataType.FLOAT_32, unit=unit) * 48 soc = self.__tcp_client.read_input_registers(4, ModbusDataType.FLOAT_32, unit=unit) + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, soc=soc, diff --git a/packages/modules/devices/studer/studer/inverter.py b/packages/modules/devices/studer/studer/inverter.py index ed267c57d3..7614f1b741 100644 --- a/packages/modules/devices/studer/studer/inverter.py +++ b/packages/modules/devices/studer/studer/inverter.py @@ -8,6 +8,7 @@ from modules.common.modbus import ModbusDataType, ModbusTcpClient_ from modules.common.store import get_inverter_value_store from modules.devices.studer.studer.config import StuderInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -23,6 +24,7 @@ def initialize(self) -> None: self.__tcp_client: ModbusTcpClient_ = self.kwargs['client'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: vc_count = self.component_config.configuration.vc_count @@ -54,6 +56,7 @@ def update(self) -> None: unit=mb_unit_dev) exported = exported * 1000000 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/sungrow/sungrow_ihm/bat.py b/packages/modules/devices/sungrow/sungrow_ihm/bat.py index a32c35d0b6..49b227f2d8 100644 --- a/packages/modules/devices/sungrow/sungrow_ihm/bat.py +++ b/packages/modules/devices/sungrow/sungrow_ihm/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.sungrow.sungrow_ihm.config import SungrowIHMBatSetup, SungrowIHM +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -30,6 +31,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) self.last_mode = 'Undefined' def update(self) -> None: @@ -39,8 +41,8 @@ def update(self) -> None: bat_power = self.__tcp_client.read_input_registers(8160, ModbusDataType.INT_32, wordorder=Endian.Little, unit=unit) * -10 + self.peak_filter.check_values(bat_power) imported, exported = self.sim_counter.sim_count(bat_power) - bat_state = BatState( power=bat_power, soc=soc, diff --git a/packages/modules/devices/sungrow/sungrow_ihm/counter.py b/packages/modules/devices/sungrow/sungrow_ihm/counter.py index 17dbaf150b..44bc946025 100644 --- a/packages/modules/devices/sungrow/sungrow_ihm/counter.py +++ b/packages/modules/devices/sungrow/sungrow_ihm/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.sungrow.sungrow_ihm.config import SungrowIHM, SungrowIHMCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="evu") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.device_config.configuration.modbus_id @@ -43,8 +45,8 @@ def update(self): voltages = [value / 10 for value in voltages] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) - counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/sungrow/sungrow_ihm/inverter.py b/packages/modules/devices/sungrow/sungrow_ihm/inverter.py index eaa705b9fa..6a8f23b6e2 100644 --- a/packages/modules/devices/sungrow/sungrow_ihm/inverter.py +++ b/packages/modules/devices/sungrow/sungrow_ihm/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.sungrow.sungrow_ihm.config import SungrowIHMInverterSetup, SungrowIHM +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> float: unit = self.device_config.configuration.modbus_id @@ -34,8 +36,8 @@ def update(self) -> float: power = self.__tcp_client.read_input_registers(8154, ModbusDataType.INT_32, wordorder=Endian.Little, unit=unit) * -10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) - inverter_state = InverterState( power=power, imported=imported, diff --git a/packages/modules/devices/sungrow/sungrow_micro/inverter.py b/packages/modules/devices/sungrow/sungrow_micro/inverter.py index 9eb479e4b7..641c0c2969 100644 --- a/packages/modules/devices/sungrow/sungrow_micro/inverter.py +++ b/packages/modules/devices/sungrow/sungrow_micro/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.sungrow.sungrow_micro.config import SungrowMicroInverterSetup, SungrowMicro +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> float: unit = self.device_config.configuration.modbus_id @@ -34,8 +36,8 @@ def update(self) -> float: power = self.__tcp_client.read_input_registers(32213, ModbusDataType.UINT_32, wordorder=Endian.Little, unit=unit) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) - inverter_state = InverterState( power=power, imported=imported, diff --git a/packages/modules/devices/sungrow/sungrow_sg/counter.py b/packages/modules/devices/sungrow/sungrow_sg/counter.py index 593ef19c10..b68b224d4c 100644 --- a/packages/modules/devices/sungrow/sungrow_sg/counter.py +++ b/packages/modules/devices/sungrow/sungrow_sg/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.sungrow.sungrow_sg.config import SungrowSG, SungrowSGCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -30,6 +31,7 @@ def initialize(self) -> None: self.fault_text = "Dieser Sungrow Zähler liefert von Werk aus (entgegen der Dokumentation) "\ "keine Leistung der einzelnen Phasen. "\ "Das Lastmanagement ist daher nur anhand der Gesamtleistung (nicht phasenbasiert) möglich." + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.device_config.configuration.modbus_id @@ -52,8 +54,8 @@ def update(self): voltages = [value / 10 for value in voltages] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) - counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/sungrow/sungrow_sg/inverter.py b/packages/modules/devices/sungrow/sungrow_sg/inverter.py index 344c17a3f9..6107686f0f 100644 --- a/packages/modules/devices/sungrow/sungrow_sg/inverter.py +++ b/packages/modules/devices/sungrow/sungrow_sg/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.sungrow.sungrow_sg.config import SungrowSGInverterSetup, SungrowSG +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> float: unit = self.device_config.configuration.modbus_id @@ -40,8 +42,8 @@ def update(self) -> float: currents = [value * -0.1 for value in currents] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power, dc_power) - inverter_state = InverterState( power=power, dc_power=dc_power, diff --git a/packages/modules/devices/sungrow/sungrow_sh/bat.py b/packages/modules/devices/sungrow/sungrow_sh/bat.py index fc5a6a767d..4a8a5572d5 100644 --- a/packages/modules/devices/sungrow/sungrow_sh/bat.py +++ b/packages/modules/devices/sungrow/sungrow_sh/bat.py @@ -11,6 +11,7 @@ from modules.common.store import get_bat_value_store from modules.devices.sungrow.sungrow_sh.config import SungrowSHBatSetup, SungrowSH from modules.devices.sungrow.sungrow_sh.registers import RegMode +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -33,6 +34,7 @@ def initialize(self) -> None: self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.last_mode = 'Undefined' self.register_check = self.detect_register_check() + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def detect_register_check(self) -> RegMode: # Battery register availability test @@ -104,6 +106,7 @@ def update(self) -> None: currents = [bat_current / 3] * 3 + self.peak_filter.check_values(bat_power) imported, exported = self.sim_counter.sim_count(bat_power) bat_state = BatState( power=bat_power, diff --git a/packages/modules/devices/sungrow/sungrow_sh/counter.py b/packages/modules/devices/sungrow/sungrow_sh/counter.py index d1ad8e4d9e..5bf10ffa5b 100644 --- a/packages/modules/devices/sungrow/sungrow_sh/counter.py +++ b/packages/modules/devices/sungrow/sungrow_sh/counter.py @@ -10,6 +10,7 @@ from modules.common.store import get_counter_value_store from modules.devices.sungrow.sungrow_sh.config import SungrowSH, SungrowSHCounterSetup from modules.devices.sungrow.sungrow_sh.version import Version +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -31,6 +32,7 @@ def initialize(self) -> None: self.fault_text = "Dieser Sungrow Zähler liefert von Werk aus (entgegen der Dokumentation) "\ "keine Leistung der einzelnen Phasen. "\ "Das Lastmanagement ist daher nur anhand der Gesamtleistung (nicht phasenbasiert) möglich." + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.device_config.configuration.modbus_id @@ -61,8 +63,8 @@ def update(self): voltages = [value / 10 for value in voltages] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) - counter_state = CounterState( imported=imported, exported=exported, diff --git a/packages/modules/devices/sungrow/sungrow_sh/inverter.py b/packages/modules/devices/sungrow/sungrow_sh/inverter.py index acaf859403..3a4dc26695 100644 --- a/packages/modules/devices/sungrow/sungrow_sh/inverter.py +++ b/packages/modules/devices/sungrow/sungrow_sh/inverter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.sungrow.sungrow_sh.config import SungrowSHInverterSetup, SungrowSH +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -27,6 +28,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.device_config.id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> float: unit = self.device_config.configuration.modbus_id @@ -40,8 +42,8 @@ def update(self) -> float: currents = [value * -0.1 for value in currents] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power, dc_power) - inverter_state = InverterState( power=power, dc_power=dc_power, diff --git a/packages/modules/devices/sunways/sunways/inverter.py b/packages/modules/devices/sunways/sunways/inverter.py index 5443b891cf..caf63c05ec 100644 --- a/packages/modules/devices/sunways/sunways/inverter.py +++ b/packages/modules/devices/sunways/sunways/inverter.py @@ -9,6 +9,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.sunways.sunways.config import SunwaysInverterSetup +from modules.common.utils.peak_filter import PeakFilter """Example Output for ajax.txt 109 W;103 W;111 VA;41 var;333.8;223.2;0.3;0.5;109.0;103.0;---;---;0.93 c;1.60;105.2;190.2;55342.2;132;0;0;NT 5000;1; @@ -32,6 +33,7 @@ def initialize(self) -> None: self.password: str = self.kwargs['password'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: params = ( @@ -43,9 +45,12 @@ def update(self) -> None: auth=HTTPDigestAuth("customer", self.password)) values = response.text.split(';') + power = float(values[1].split(' ')[0])*-1 + exported = float(values[16])*1000 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( - power=float(values[1].split(' ')[0])*-1, - exported=float(values[16])*1000 + power=power, + exported=exported ) self.store.set(inverter_state) diff --git a/packages/modules/devices/tasmota/tasmota/bat.py b/packages/modules/devices/tasmota/tasmota/bat.py index d38f1a4090..4aaf5852f2 100644 --- a/packages/modules/devices/tasmota/tasmota/bat.py +++ b/packages/modules/devices/tasmota/tasmota/bat.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common import req from modules.common.component_state import BatState +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -32,6 +33,7 @@ def initialize(self) -> None: self.__phase: int = self.kwargs['phase'] self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self): url = "http://" + self.__ip_address + "/cm?cmnd=Status%208" @@ -43,6 +45,7 @@ def update(self): power = float(response['StatusSNS']['ENERGY']['Power']) currents[self.__phase-1] = (response['StatusSNS']['ENERGY']['Current']), 0.0, 0.0 imported = float(response['StatusSNS']['ENERGY']['Total']*1000) + imported, _ = self.peak_filter.check_values(power, imported, None) _, exported = self.sim_counter.sim_count(power) bat_state = BatState( @@ -55,6 +58,7 @@ def update(self): power = float(response['StatusSNS']['Itron']['Power']) imported = float(response['StatusSNS']['Itron']['E_in']*1000) exported = float(response['StatusSNS']['Itron']['E_out']*1000) + imported, exported = self.peak_filter.check_values(power, imported, exported) bat_state = BatState( power=power, diff --git a/packages/modules/devices/tasmota/tasmota/counter.py b/packages/modules/devices/tasmota/tasmota/counter.py index 4a9419ab06..04d598db7b 100644 --- a/packages/modules/devices/tasmota/tasmota/counter.py +++ b/packages/modules/devices/tasmota/tasmota/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common import req from modules.common.component_state import CounterState +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -32,6 +33,7 @@ def initialize(self) -> None: self.__phase: int = self.kwargs['phase'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): url = "http://" + self.__ip_address + "/cm?cmnd=Status%208" @@ -49,15 +51,18 @@ def update(self): currents[self.__phase-1] = float(response['StatusSNS']['ENERGY']['Current']) power_factors[self.__phase-1] = float(response['StatusSNS']['ENERGY']['Factor']) imported = float(response['StatusSNS']['ENERGY']['Total']*1000) + imported, _ = self.peak_filter.check_values(power, imported, None) _, exported = self.sim_counter.sim_count(power) elif 'Itron' in response['StatusSNS']: power = float(response['StatusSNS']['Itron']['Power']) imported = float(response['StatusSNS']['Itron']['E_in']*1000) exported = float(response['StatusSNS']['Itron']['E_out']*1000) + imported, exported = self.peak_filter.check_values(power, imported, exported) elif 'MT681' in response['StatusSNS']: power = float(response['StatusSNS']['MT681']['Watt_summe']) imported = float(response['StatusSNS']['MT681']['Total_in']*1000) exported = float(response['StatusSNS']['MT681']['Total_out']*1000) + imported, exported = self.peak_filter.check_values(power, imported, exported) else: raise ValueError("Nicht unterstützter Tasmota Zählertyp. Bitte an den Support wenden.") diff --git a/packages/modules/devices/tasmota/tasmota/inverter.py b/packages/modules/devices/tasmota/tasmota/inverter.py index c610831c28..d1c0552490 100644 --- a/packages/modules/devices/tasmota/tasmota/inverter.py +++ b/packages/modules/devices/tasmota/tasmota/inverter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common import req from modules.common.component_state import InverterState +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -32,6 +33,7 @@ def initialize(self) -> None: self.__phase: int = self.kwargs['phase'] self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self): url = "http://" + self.__ip_address + "/cm?cmnd=Status%208" @@ -42,6 +44,7 @@ def update(self): power = float(response['StatusSNS']['ENERGY']['Power']) * -1 currents[self.__phase-1] = (response['StatusSNS']['ENERGY']['Current']), 0.0, 0.0 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( @@ -52,7 +55,7 @@ def update(self): else: power = float(response['StatusSNS']['Itron']['Power']) * -1 exported = float(response['StatusSNS']['Itron']['E_out']*1000) - + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/thermia/thermia/counter.py b/packages/modules/devices/thermia/thermia/counter.py index 20d39d773e..705041ac09 100644 --- a/packages/modules/devices/thermia/thermia/counter.py +++ b/packages/modules/devices/thermia/thermia/counter.py @@ -9,6 +9,7 @@ from modules.common.store import get_counter_value_store from modules.devices.thermia.thermia.config import ThermiaCounterSetup from pymodbus.constants import Endian +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,6 +30,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): with self.client: @@ -44,6 +46,7 @@ def update(self): unit=self.modbus_id) * 100 exported = 0 + imported, _ = self.peak_filter.check_values(power, imported, None) counter_state = CounterState( currents=currents, imported=imported, diff --git a/packages/modules/devices/upower/upower/bat.py b/packages/modules/devices/upower/upower/bat.py index ce1be62c90..3968a15d1f 100644 --- a/packages/modules/devices/upower/upower/bat.py +++ b/packages/modules/devices/upower/upower/bat.py @@ -11,6 +11,7 @@ from modules.common.store import get_bat_value_store from modules.devices.upower.upower.config import UPowerBatSetup from modules.devices.upower.upower.version import UPowerVersion +from modules.common.utils.peak_filter import PeakFilter class UPowerBat(AbstractBat): @@ -27,6 +28,7 @@ def __init__(self, self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(device_id, self.component_config.id, prefix="speicher") + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: if self.version == UPowerVersion.GEN_1: @@ -36,12 +38,14 @@ def update(self) -> None: 31108, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 exported = self.client.read_input_registers( 31110, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) else: # 1221 Total Bat Power # 1427 Battery 1 current power # Bat 1 (additional batteries offset by 50) power = self.client.read_input_registers(1427, ModbusDataType.INT_16, unit=self.__modbus_id) soc = self.client.read_input_registers(1402, ModbusDataType.UINT_16, unit=self.__modbus_id) / 10 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( diff --git a/packages/modules/devices/upower/upower/counter.py b/packages/modules/devices/upower/upower/counter.py index 85756a7d91..4fada12951 100644 --- a/packages/modules/devices/upower/upower/counter.py +++ b/packages/modules/devices/upower/upower/counter.py @@ -11,6 +11,7 @@ from modules.common.store import get_counter_value_store from modules.devices.upower.upower.config import UPowerCounterSetup from modules.devices.upower.upower.version import UPowerVersion +from modules.common.utils.peak_filter import PeakFilter class UPowerCounter(AbstractCounter): @@ -27,6 +28,7 @@ def __init__(self, self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.sim_counter = SimCounter(device_id, self.component_config.id, prefix="bezug") + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): if self.version == UPowerVersion.GEN_1: @@ -37,6 +39,7 @@ def update(self): 10994, [ModbusDataType.INT_32] * 3, unit=self.__modbus_id)] exported = self.client.read_holding_registers(31102, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 imported = self.client.read_holding_registers(31104, ModbusDataType.UINT_32, unit=self.__modbus_id) * 100 + imported, exported = self.peak_filter.check_values(power, imported, exported) else: power = self.client.read_holding_registers(1219, ModbusDataType.INT_16, unit=self.__modbus_id) * -10 frequency = self.client.read_holding_registers( @@ -45,6 +48,7 @@ def update(self): powers = [-10 * value for value in self.client.read_holding_registers( 1750, [ModbusDataType.INT_16] * 3, unit=self.__modbus_id )] + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/upower/upower/inverter.py b/packages/modules/devices/upower/upower/inverter.py index 6fd13770df..c7abf210c1 100644 --- a/packages/modules/devices/upower/upower/inverter.py +++ b/packages/modules/devices/upower/upower/inverter.py @@ -10,6 +10,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.upower.upower.config import UPowerInverterSetup from modules.devices.upower.upower.version import UPowerVersion +from modules.common.utils.peak_filter import PeakFilter class UPowerInverter(AbstractInverter): @@ -24,6 +25,7 @@ def __init__(self, self.client = client self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: if self.version == UPowerVersion.GEN_1: @@ -33,6 +35,7 @@ def update(self) -> None: power = self.client.read_holding_registers(1220, ModbusDataType.UINT_16, unit=self.__modbus_id) * -1 exported = self.client.read_holding_registers(1006, ModbusDataType.UINT_32, unit=self.__modbus_id) * 10 + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, exported=exported diff --git a/packages/modules/devices/varta/varta/bat_modbus.py b/packages/modules/devices/varta/varta/bat_modbus.py index f0ac3b5b31..0d374e301a 100644 --- a/packages/modules/devices/varta/varta/bat_modbus.py +++ b/packages/modules/devices/varta/varta/bat_modbus.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.varta.varta.config import VartaBatModbusSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,6 +30,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="speicher") self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: self.set_state(self.get_state()) @@ -36,6 +38,7 @@ def update(self) -> None: def get_state(self) -> BatState: soc = self.client.read_holding_registers(1068, ModbusDataType.INT_16, unit=self.__modbus_id) power = self.client.read_holding_registers(1066, ModbusDataType.INT_16, unit=self.__modbus_id) + self.peak_filter.check_values(power) return BatState( power=power, soc=soc, diff --git a/packages/modules/devices/varta/varta/counter.py b/packages/modules/devices/varta/varta/counter.py index 0f84a0fb23..495d1c5e8a 100644 --- a/packages/modules/devices/varta/varta/counter.py +++ b/packages/modules/devices/varta/varta/counter.py @@ -9,6 +9,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.varta.varta.config import VartaCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -29,9 +30,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): power = self.client.read_holding_registers(1078, ModbusDataType.INT_16, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) counter_state = CounterState( diff --git a/packages/modules/devices/varta/varta/inverter.py b/packages/modules/devices/varta/varta/inverter.py index 5c7627a819..704bdd0c42 100644 --- a/packages/modules/devices/varta/varta/inverter.py +++ b/packages/modules/devices/varta/varta/inverter.py @@ -8,6 +8,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.varta.varta.config import VartaInverterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,9 +29,11 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self): power = self.client.read_holding_registers(1102, ModbusDataType.UINT_16, unit=self.__modbus_id) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( diff --git a/packages/modules/devices/victron/victron/bat.py b/packages/modules/devices/victron/victron/bat.py index 603d7f728d..4782034fe5 100644 --- a/packages/modules/devices/victron/victron/bat.py +++ b/packages/modules/devices/victron/victron/bat.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_bat_value_store from modules.devices.victron.victron.config import VictronBatSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -32,13 +33,14 @@ def initialize(self) -> None: self.store = get_bat_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) self.last_mode = 'Undefined' + self.peak_filter = PeakFilter("bat", self.component_config.id, self.fault_state) def update(self) -> None: modbus_id = self.component_config.configuration.modbus_id with self.__tcp_client: power = self.__tcp_client.read_holding_registers(842, ModbusDataType.INT_16, unit=modbus_id) soc = self.__tcp_client.read_holding_registers(843, ModbusDataType.UINT_16, unit=modbus_id) - + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) bat_state = BatState( power=power, diff --git a/packages/modules/devices/victron/victron/counter.py b/packages/modules/devices/victron/victron/counter.py index 138fa638a4..c91ac5ce1e 100644 --- a/packages/modules/devices/victron/victron/counter.py +++ b/packages/modules/devices/victron/victron/counter.py @@ -10,6 +10,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_counter_value_store from modules.devices.victron.victron.config import VictronCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -28,6 +29,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = self.component_config.configuration.modbus_id @@ -46,6 +48,7 @@ def update(self): powers = self.__tcp_client.read_holding_registers(820, [ModbusDataType.INT_16]*3, unit=unit) power = sum(powers) + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) if energy_meter: diff --git a/packages/modules/devices/victron/victron/inverter.py b/packages/modules/devices/victron/victron/inverter.py index 84b677e13e..31eea771cd 100644 --- a/packages/modules/devices/victron/victron/inverter.py +++ b/packages/modules/devices/victron/victron/inverter.py @@ -11,6 +11,7 @@ from modules.common.simcount import SimCounter from modules.common.store import get_inverter_value_store from modules.devices.victron.victron.config import VictronInverterSetup +from modules.common.utils.peak_filter import PeakFilter log = logging.getLogger(__name__) @@ -31,6 +32,7 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self) -> None: modbus_id = self.component_config.configuration.modbus_id @@ -53,6 +55,7 @@ def update(self) -> None: power_temp2 = self.__tcp_client.read_holding_registers(850, ModbusDataType.UINT_16, unit=100) power = (sum(power_temp1)+power_temp2) * -1 + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/victron/victron_3p75ct/counter.py b/packages/modules/devices/victron/victron_3p75ct/counter.py index 87fea94375..bcd76e1388 100644 --- a/packages/modules/devices/victron/victron_3p75ct/counter.py +++ b/packages/modules/devices/victron/victron_3p75ct/counter.py @@ -9,6 +9,7 @@ from modules.common.modbus import ModbusDataType from modules.common.store import get_counter_value_store from modules.devices.victron.victron_3p75ct.config import VictronCounterSetup +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,6 +26,7 @@ def initialize(self) -> None: self.__udp_client = self.kwargs['client'] self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self): unit = 1 # Modbus ID ist immer 1 da Standalone Produkt @@ -47,6 +49,7 @@ def update(self): imported = self.__udp_client.read_holding_registers(0x3034, ModbusDataType.UINT_32, unit=unit) * 10 exported = self.__udp_client.read_holding_registers(0x3036, ModbusDataType.UINT_32, unit=unit) * 10 + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( voltages=voltages, currents=currents, diff --git a/packages/modules/devices/vzlogger/vzlogger/counter.py b/packages/modules/devices/vzlogger/vzlogger/counter.py index 0927af64e7..f9fef2ed2d 100644 --- a/packages/modules/devices/vzlogger/vzlogger/counter.py +++ b/packages/modules/devices/vzlogger/vzlogger/counter.py @@ -9,6 +9,7 @@ from modules.common.store import get_counter_value_store from modules.devices.vzlogger.vzlogger.config import VZLoggerCounterSetup from modules.devices.vzlogger.vzlogger.utils import parse_line +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,16 +26,19 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="bezug") self.store = get_counter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("counter", self.component_config.id, self.fault_state) def update(self, response): config = self.component_config.configuration power = parse_line(response, config.line_power) if config.line_imported is None or config.line_exported is None: + self.peak_filter.check_values(power) imported, exported = self.sim_counter.sim_count(power) else: imported = parse_line(response, config.line_imported) exported = parse_line(response, config.line_exported) + imported, exported = self.peak_filter.check_values(power, imported, exported) counter_state = CounterState( imported=imported, diff --git a/packages/modules/devices/vzlogger/vzlogger/inverter.py b/packages/modules/devices/vzlogger/vzlogger/inverter.py index fda1d30dc2..ad71db01de 100644 --- a/packages/modules/devices/vzlogger/vzlogger/inverter.py +++ b/packages/modules/devices/vzlogger/vzlogger/inverter.py @@ -9,6 +9,7 @@ from modules.common.store import get_inverter_value_store from modules.devices.vzlogger.vzlogger.config import VZLoggerInverterSetup from modules.devices.vzlogger.vzlogger.utils import parse_line +from modules.common.utils.peak_filter import PeakFilter class KwargsDict(TypedDict): @@ -25,15 +26,18 @@ def initialize(self) -> None: self.sim_counter = SimCounter(self.__device_id, self.component_config.id, prefix="pv") self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response) -> None: config = self.component_config.configuration power = parse_line(response, config.line_power) if config.line_exported is None: + self.peak_filter.check_values(power) _, exported = self.sim_counter.sim_count(power) else: exported = parse_line(response, config.line_exported) + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=power, diff --git a/packages/modules/devices/youless/youless/inverter.py b/packages/modules/devices/youless/youless/inverter.py index a26da3a205..220d9cb169 100644 --- a/packages/modules/devices/youless/youless/inverter.py +++ b/packages/modules/devices/youless/youless/inverter.py @@ -5,6 +5,7 @@ from modules.common.fault_state import ComponentInfo, FaultState from modules.common.store import get_inverter_value_store from modules.devices.youless.youless.config import YoulessInverterSetup +from modules.common.utils.peak_filter import PeakFilter class YoulessInverter(AbstractInverter): @@ -14,6 +15,7 @@ def __init__(self, component_config: YoulessInverterSetup) -> None: def initialize(self) -> None: self.store = get_inverter_value_store(self.component_config.id) self.fault_state = FaultState(ComponentInfo.from_component_config(self.component_config)) + self.peak_filter = PeakFilter("inverter", self.component_config.id, self.fault_state) def update(self, response) -> None: if self.component_config.configuration.source_s0: @@ -22,7 +24,7 @@ def update(self, response) -> None: else: power = int(response["pwr"]) exported = int(response["cnt"].replace(",", "")) - + _, exported = self.peak_filter.check_values(power, None, exported) inverter_state = InverterState( power=-abs(power), exported=exported,