Skip to content

Commit

Permalink
Fix to inverter_model and addition of async_scan
Browse files Browse the repository at this point in the history
  • Loading branch information
mvandersteen committed May 29, 2022
1 parent 26a5d47 commit bb42674
Show file tree
Hide file tree
Showing 6 changed files with 47 additions and 17 deletions.
10 changes: 5 additions & 5 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -87,7 +87,7 @@ timeout: <in seconds> tcp connection is timed out and fails after this long

### Methods

Available methods and how to use
Available methods

`client.inverter_model()` Returns a object of sungrowinverter.common.SungrowInverterModel with details of model, serial, nominal output power (kWh)

Expand All @@ -97,7 +97,7 @@ Available methods and how to use

#### All inverters

`model:` provides device model (ie. SH5K - as found in current models supported above)
`model:` Provides device model (ie. SH5K - as found in current models supported above)

`device_code:` Sungrow device code found at register 5000 (refer docs for actual codes if needed)

Expand All @@ -109,13 +109,13 @@ Available methods and how to use

`mppt_input:` The number of mppt inputs the inverter supports, refer notes below.

`data:` provides a dictionary of data of all registers queried (key = register name, value = register value) refer to the https://github.com/mvandersteen/SungrowInverter/tree/main/sungrowinverter/configs for details on what registers are exposed.
`data:` Provides a dictionary of data of all registers queried (key = register name, value = register value) refer to the https://github.com/mvandersteen/SungrowInverter/tree/main/sungrowinverter/configs for details on what registers are exposed.

#### Hybrid (storage) inverters only

`battery_type:` , this will show the configured details for the inverter
`battery_type:` Show the battery type configured for the inverter

`battery_capacity :` hybrid inverters only, this will show the configured details for the inverter
`battery_energy_capacity:` hybrid only, this will show the capacity of the battery configured for the inverter


## Note
Expand Down
2 changes: 1 addition & 1 deletion setup.cfg
Original file line number Diff line number Diff line change
@@ -1,6 +1,6 @@
[metadata]
name = SungrowInverter
version = 0.1.8
version = 0.1.9
author = Mark Vandersteen
author_email = [email protected]
description = A client to allow access to a Sungrow inverter modbus parameters (read only).
Expand Down
41 changes: 35 additions & 6 deletions sungrowinverter/SungrowInverter.py
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@
Refer configs/hybrid.py and configs/string.py for inverters that are supported.
"""

__version__ = "0.1.8"
__version__ = "0.1.9"

from SungrowModbusTcpClient import SungrowModbusTcpClient

Expand Down Expand Up @@ -246,11 +246,13 @@ async def inverter_model(self) -> SungrowInverterModel:
self.data["battery_energy_capacity"] = self.battery_energy_capacity

logging.info("Storage device attached to inverter: [Model: %s, Capacity: %s kWh]", self.battery_type, self.battery_energy_capacity)
return inverter_model
else:
logging.error("CONNECTION ERROR: Could not connect to inverter @ Host: %s, Port: %s", self._modbusclient.host, self._modbusclient.port)

logging.error("UPSUPPORT INVERTER: Supported inverter device_type_code [%s] is not supported", self.data["device_type_code"])
return inverter_model

else:
logging.error("UPSUPPORT INVERTER: Supported inverter device_type_code [%s] is not supported", self.data["device_type_code"])
else:
logging.error("DEVICE CODE NOT FOUND: A device code could not be obtained from the inverter")
else:
logging.error("CONNECTION ERROR: Could not connect to inverter @ Host: %s, Port: %s", self._modbusclient.host, self._modbusclient.port)
else:
Expand Down Expand Up @@ -313,4 +315,31 @@ async def async_update(self):
else:
logging.error("CONNECTION ERROR: Could not connect to inverter to read modbus registers")

return False
return False


# Core monitoring loop
async def async_scan(self, register_type, start_register, register_count, step_by = 20):
"""Connect to the inverter and scan for register locations"""

connected = self._modbusclient.connect()

if connected:
for start in range(start_register, start_register + register_count, step_by):
try:
if register_type == "read":
response = self._modbusclient.read_input_registers(int(start - 1), count=step_by, unit=self._slave)
elif register_type == "holding":
response = self._modbusclient.read_holding_registers(int(start - 1), count=step_by, unit=self._slave)

if hasattr(response, 'registers'):
logging.info("[start_register: %s, register_count: %s] contents: %s", int(start_register) , register_count, response.registers)
else:
logging.info("[start_register: %s, register_count: %s] nothing returned", int(start_register) , register_count)

except Exception:
logging.info("Exception thrown")

self._modbusclient.close()
return True
return False
6 changes: 4 additions & 2 deletions sungrowinverter/configs/hybrid.py
Original file line number Diff line number Diff line change
Expand Up @@ -143,6 +143,8 @@

HYBRID_CALCULATED_REGISTERS: tuple[CalcRegister, ...] = (
CalcRegister("daily_export_energy", "self.data['daily_export_from_pv'] + self.data['daily_export_from_battery']", unit_of_measure=KILO_WATT_HOUR),
CalcRegister("total_export_energy", "self.data['total_export_from_pv'] + self.data['total_export_from_battery']", unit_of_measure=KILO_WATT_HOUR),
CalcRegister("inverter_efficiency", "int((self.data['daily_energy_yield'] / self.data['daily_pv_generation']) * 100)", unit_of_measure=PERCENTAGE, description="Energy yield from the days pv generation"),
CalcRegister("total_export_energy", "self.data['total_export_from_pv'] + self.data['total_export_from_battery']", unit_of_measure=KILO_WATT_HOUR),
CalcRegister("daily_batery_charge", "self.data['daily_battery_charge_from_pv'] + self.data['daily_charge_from_grid']", unit_of_measure=KILO_WATT_HOUR),
CalcRegister("total_batery_charge", "self.data['total_battery_charge_from_pv'] + self.data['total_charge_from_grid']", unit_of_measure=KILO_WATT_HOUR),
CalcRegister("inverter_efficiency", "int((self.data['daily_energy_yield'] / self.data['daily_pv_generation']) * 100)", unit_of_measure=PERCENTAGE, description="Energy yield from the days pv generation")
)
1 change: 0 additions & 1 deletion sungrowinverter/configs/inverter.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,6 @@
SungrowInverterModel,
KILO_WATT,
VOLTAGE,
AMPERE,
AMP_HOUR,
BATTERY_TYPES,
)
Expand Down
4 changes: 2 additions & 2 deletions test.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@

from sungrowinverter import SungrowInverter

logging.basicConfig(format='%(levelname)s:%(message)s', level=logging.ERROR)
logging.basicConfig(format='%(levelname)s:%(message)s', level=logging.INFO)
#logging.basicConfig(format='%(levelname)s:%(message)s', level=logging.DEBUG)

# Change IP Address (192.168.4.2) to suit your inverter
Expand All @@ -14,7 +14,7 @@
result = loop.run_until_complete(client.async_update())

#Get a list data returned from the inverter.
if result != False:
if result:
print(client.data)
else:
print("Could not connect to inverter")

0 comments on commit bb42674

Please sign in to comment.