def update_using_powerwall_client(client: PowerwallHttpClient): # read firmware version status = client.get_json("/api/status") log.debug('Firmware: ' + status["version"]) # read aggregate aggregate = client.get_json("/api/meters/aggregates") try: # read additional info if firmware supports meters_site = client.get_json("/api/meters/site") powerwall_state = CounterState( imported=aggregate["site"]["energy_imported"], exported=aggregate["site"]["energy_exported"], power=aggregate["site"]["instant_power"], voltages=[ meters_site[0]["Cached_readings"]["v_l" + str(phase) + "n"] for phase in range(1, 4) ], currents=[ meters_site[0]["Cached_readings"]["i_" + phase + "_current"] for phase in ["a", "b", "c"] ], powers=[ meters_site[0]["Cached_readings"]["real_power_" + phase] for phase in ["a", "b", "c"] ]) except (KeyError, HTTPError): log.debug( "Firmware seems not to provide detailed phase measurements. Fallback to total power only." ) powerwall_state = CounterState( imported=aggregate["site"]["energy_imported"], exported=aggregate["site"]["energy_exported"], power=aggregate["site"]["instant_power"]) get_counter_value_store(1).set(powerwall_state)
def update(ipaddress: str): log.debug("Beginning update") client = ModbusClient(ipaddress, port=502) #40074 EVU Punkt negativ -> Einspeisung in Watt power_all = client.read_holding_registers(40073, ModbusDataType.INT_32, wordorder=Endian.Little, unit=1) #40130 Phasenleistung in Watt # max 6 Leistungsmesser verbaut ab 410105, typ 1 ist evu # bei den meisten e3dc auf 40128 #for i in range (40104,40132,4): for i in range(40128, 40103, -4): #powers = client.read_holding_registers(40129, [ModbusDataType.INT_16] * 3, unit=1) powers = client.read_holding_registers(i, [ModbusDataType.INT_16] * 4, unit=1) log.debug("I: %d, p[0] typ %d p[1] a1 %d p[2] a2 %d p[3] a3 %d", i, powers[0], powers[1], powers[2], powers[3]) if powers[0] == 1: log.debug("Evu Leistungsmessung gefunden") break counter_import, counter_export = SimCountFactory().get_sim_counter()( ).sim_count(power_all, prefix="bezug") get_counter_value_store(1).set( CounterState(imported=counter_import, exported=counter_export, power=power_all, powers=powers[1:])) log.debug("Update completed successfully")
def read_legacy(component_type: str, address: str, bat_module: str, bat_ip: str, bat_username: str, bat_password: str, num: Optional[int] = None) -> None: dev = Device( KostalPiko(configuration=KostalPikoConfiguration(ip_address=address))) if component_type in COMPONENT_TYPE_TO_MODULE: component_config = COMPONENT_TYPE_TO_MODULE[ component_type].component_descriptor.configuration_factory() else: raise Exception("illegal component type " + component_type + ". Allowed values: " + ','.join(COMPONENT_TYPE_TO_MODULE.keys())) component_config.id = num dev.add_component(component_config) log.debug('KostalPiko IP-Adresse: ' + address) log.debug('KostalPiko Speicher: ' + bat_module) if component_type == "inverter": with SingleComponentUpdateContext( dev.components["component" + str(num)].component_info): power, exported = dev.components["component" + str(num)].get_values() if bat_module == "speicher_bydhv": bat_power = _get_byd_bat_power(bat_ip, bat_username, bat_password, num) power -= bat_power get_inverter_value_store(num).set( InverterState(power=power, exported=exported)) elif component_type == "counter": with SingleComponentUpdateContext( dev.components["componentNone"].component_info): home_consumption, powers = dev.components[ "componentNone"].get_values() if bat_module == "speicher_bydhv": bat_power = _get_byd_bat_power(bat_ip, bat_username, bat_password, num) home_consumption += bat_power dev.add_component(KostalPikoInverterSetup(id=num)) inverter_power, _ = dev.components["component" + str(num)].get_values() power = home_consumption + inverter_power imported, exported = simcount.SimCountFactory().get_sim_counter()( ).sim_count(power, topic="topic_str", data={}, prefix="bezug") counter_state = CounterState(imported=imported, exported=exported, power=power, powers=powers) get_counter_value_store(None).set(counter_state)
def update(ipaddress: str, modbusport: int, slaveid: int): log.debug("Beginning update") client = ModbusClient(ipaddress, port=modbusport) def read_scaled_int16(address: int, count: int): return scale_registers( client.read_holding_registers(address, [ModbusDataType.INT_16] * (count + 1), unit=slaveid)) # 40206: Total Real Power (sum of active phases) # 40206/40207/40208: Real Power by phase # 40210: AC Real Power Scale Factor powers = [-power for power in read_scaled_int16(40206, 4)] # 40191/40192/40193: AC Current by phase # 40194: AC Current Scale Factor currents = read_scaled_int16(40191, 3) # 40196/40197/40198: Voltage per phase # 40203: AC Voltage Scale Factor voltages = read_scaled_int16(40196, 7)[:3] # 40204: AC Frequency # 40205: AC Frequency Scale Factor frequency, = read_scaled_int16(40204, 1) # 40222/40223/40224: Power factor by phase (unit=%) # 40225: AC Power Factor Scale Factor power_factors = [ power_factor / 100 for power_factor in read_scaled_int16(40222, 3) ] # 40234: Total Imported Real Energy counter_imported = client.read_holding_registers(40234, ModbusDataType.UINT_32, unit=slaveid) # 40226: Total Exported Real Energy counter_exported = client.read_holding_registers(40226, ModbusDataType.UINT_32, unit=slaveid) get_counter_value_store(1).set( CounterState(imported=counter_imported, exported=counter_exported, power=powers[0], powers=powers[1:], voltages=voltages, currents=currents, power_factors=power_factors, frequency=frequency)) log.debug("Update completed successfully")
def __init__(self, device_id: int, component_config: dict) -> None: self.__device_id = device_id self.component_config = component_config self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(component_config["id"]) self.component_info = ComponentInfo.from_component_config(component_config)
def __init__(self, component_config: Union[Dict, TeslaCounterSetup]) -> None: self.component_config = dataclass_from_dict(TeslaCounterSetup, component_config) self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config)
def __init__(self, device_id: int, component_config: dict, tcp_client: modbus.ModbusClient) -> None: self.component_config = component_config self.__tcp_client = tcp_client self.__store = get_counter_value_store(component_config["id"]) self.component_info = ComponentInfo.from_component_config( component_config)
def __init__(self, device_id: int, component_config: Union[Dict, SolaredgeCounterSetup], tcp_client: modbus.ModbusTcpClient_) -> None: self.component_config = dataclass_from_dict(SolaredgeCounterSetup, component_config) self.__tcp_client = tcp_client self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config)
def __init__(self, device_id: int, component_config: dict) -> None: self.__device_id = device_id self.component_config = component_config ip_address = component_config["configuration"]["ip_address"] self.__tcp_client = modbus.ModbusClient(ip_address, 502) self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(component_config["id"]) self.component_info = ComponentInfo.from_component_config(component_config)
def __init__(self, device_id: int, component_config: Union[Dict, LgCounterSetup]) -> None: self.__device_id = device_id self.component_config = dataclass_from_dict(LgCounterSetup, component_config) self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config)
def __init__(self, device_id: int, component_config: Union[Dict, SungrowCounterSetup], tcp_client: modbus.ModbusTcpClient_) -> None: self.__device_id = device_id self.component_config = dataclass_from_dict(SungrowCounterSetup, component_config) self.__tcp_client = tcp_client self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config(self.component_config)
def __init__( self, device_id: int, device_address: str, device_variant: int, component_config: Union[Dict, SonnenbatterieCounterSetup]) -> None: self.__device_id = device_id self.__device_address = device_address self.__device_variant = device_variant self.component_config = dataclass_from_dict(SonnenbatterieCounterSetup, component_config) self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config)
def __init__(self, device_id: int, component_config: dict, tcp_client: modbus.ModbusClient) -> None: self.__device_id = device_id self.component_config = component_config factory = kit_counter_inverter_version_factory( component_config["configuration"]["version"]) self.__client = factory(component_config["configuration"]["id"], tcp_client) self.__tcp_client = tcp_client self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(component_config["id"]) self.component_info = ComponentInfo.from_component_config(component_config)
def write_readings_to_ramdisk(discovergy: dict): values = discovergy["values"] try: voltages = [ values["voltage" + str(phase)] / 1000 for phase in range(1, 4) ] # Es gibt verschiedene Antworten vom Discovergy-Modul. except KeyError: try: voltages = [ values["phase" + str(phase) + "Voltage"] / 1000 for phase in range(1, 4) ] except KeyError: # Some discovergy counters do not report voltage at all voltages = None try: powers = [values["power" + str(phase)] / 1000 for phase in range(1, 4)] except KeyError: powers = [ values["phase" + str(phase) + "Power"] / 1000 for phase in range(1, 4) ] power_total = values["power"] / 1000 get_counter_value_store(1).set( CounterState( imported=values["energy"] / 10000000, exported=values["energyOut"] / 10000000, power=power_total, voltages=voltages, currents=[ power / voltage for power, voltage in zip(powers, [230] * 3 if voltages is None else voltages) ], powers=powers)) log.debug("Update complete. Total Power: %g W", power_total)
def update_using_cookie(address: str, cookie): # read firmware version status = read_status(address, cookie) # since 21.44.1 tesla adds the commit hash '21.44.1 c58c2df3' # so we split by whitespace and take the first element for comparison log.debug('Firmware: ' + status["version"]) firmwareversion = int(''.join(status["version"].split()[0].split("."))) # read aggregate aggregate = read_aggregate(address, cookie) # read additional info if firmware supports if firmwareversion >= 20490: meters_site = read_site(address, cookie) get_counter_value_store(1).set( CounterState( imported=aggregate["site"]["energy_imported"], exported=aggregate["site"]["energy_exported"], power=aggregate["site"]["instant_power"], voltages=[ meters_site["0"]["Cached_readings"]["v_l" + str(phase) + "n"] for phase in range(1, 4) ], currents=[ meters_site["0"]["Cached_readings"]["i_" + phase + "_current"] for phase in ["a", "b", "c"] ], powers=[ meters_site["0"]["Cached_readings"]["real_power_" + phase] for phase in ["a", "b", "c"] ])) else: get_counter_value_store(1).set( CounterState(imported=aggregate["site"]["energy_imported"], exported=aggregate["site"]["energy_exported"], power=aggregate["site"]["instant_power"]))
def __init__(self, device_id: int, component_config: Union[Dict, EvuKitFlexSetup], tcp_client: modbus.ModbusTcpClient_) -> None: self.__device_id = device_id self.component_config = dataclass_from_dict(EvuKitFlexSetup, component_config) factory = kit_counter_inverter_version_factory( self.component_config.configuration.version) self.__client = factory(self.component_config.configuration.id, tcp_client) self.__tcp_client = tcp_client self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config)
def __init__(self, component_config: dict, domain: str) -> None: self.__get_power = create_request_function( domain, component_config["configuration"]["power_path"]) self.__get_imported = create_request_function( domain, component_config["configuration"]["imported_path"]) self.__get_exported = create_request_function( domain, component_config["configuration"]["exported_path"]) self.__get_powers = [ create_request_function( domain, component_config["configuration"]["power_l" + str(i) + "_path"]) for i in range(1, 4) ] self.component_config = component_config self.__store = get_counter_value_store(component_config["id"]) self.component_info = ComponentInfo.from_component_config( component_config)
def __init__(self, device_id: int, component_config: Union[Dict, HttpCounterSetup], url: str) -> None: self.__device_id = device_id self.component_config = dataclass_from_dict(HttpCounterSetup, component_config) self.__sim_count = simcount.SimCountFactory().get_sim_counter()() self.simulation = {} self.__store = get_counter_value_store(self.component_config.id) self.component_info = ComponentInfo.from_component_config( self.component_config) self.__get_power = create_request_function( url, self.component_config.configuration.power_path) self.__get_imported = create_request_function( url, self.component_config.configuration.imported_path) self.__get_exported = create_request_function( url, self.component_config.configuration.exported_path) self.__get_currents = [ create_request_function( url, getattr(self.component_config.configuration, "current_l" + str(i) + "_path")) for i in range(1, 4) ]
def create_component(component_config: DiscovergyCounterSetup): return DiscovergyComponent( component_config, get_counter_value_store(component_config.id).set)
def create_component(component_config: dict): return DiscovergyComponent( component_config, get_counter_value_store(component_config["id"]).set)