Skip to content

Commit

Permalink
Update sensor.py (#257)
Browse files Browse the repository at this point in the history
* Update sensor.py

Added Monthly Generation sensor (Total Yield)

Added Energy Throughput sensor (This is number of kWh's the battery has seen in throughput, it is the principal metric for the FoxESS warranty of batteries)

* Update README.md

update to include Energy Generated Month (Total yield monthly) and Energy Throughput (Battery Energy throughput)
  • Loading branch information
FozzieUK1 authored Jun 18, 2024
1 parent 74277ef commit 451f03b
Show file tree
Hide file tree
Showing 2 changed files with 88 additions and 2 deletions.
2 changes: 2 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -118,6 +118,8 @@ T Power | kW
T Volt | V
Reactive Power | kVar
Energy Generated | kWh
Energy Generated Month | kWh
Energy Throughput | kWh
Grid Consumption | kWh
FeedIn | kWh
Solar | kWh
Expand Down
88 changes: 86 additions & 2 deletions custom_components/foxess/sensor.py
Original file line number Diff line number Diff line change
Expand Up @@ -68,7 +68,7 @@
METHOD_GET = "GET"
DEFAULT_ENCODING = "UTF-8"
USER_AGENT = "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36"
DEFAULT_TIMEOUT = 90 # increase the size of inherited timeout, the API is a bit slow
DEFAULT_TIMEOUT = 65 # increase the size of inherited timeout, the API is a bit slow

ATTR_DEVICE_SN = "deviceSN"
ATTR_PLANTNAME = "plantName"
Expand Down Expand Up @@ -279,6 +279,7 @@ async def async_update_data():
FoxESSBatMinSoC(coordinator, name, deviceID),
FoxESSBatMinSoConGrid(coordinator, name, deviceID),
FoxESSSolarPower(coordinator, name, deviceID),
FoxESSEnergyThroughput(coordinator, name, deviceID),
FoxESSEnergySolar(coordinator, name, deviceID),
FoxESSInverter(coordinator, name, deviceID),
FoxESSPowerString(coordinator, name, deviceID, "Generation Power", "-generation-power", "generationPower"),
Expand All @@ -288,6 +289,7 @@ async def async_update_data():
FoxESSPowerString(coordinator, name, deviceID, "Bat Charge Power", "bat-charge-power", "batChargePower"),
FoxESSPowerString(coordinator, name, deviceID, "Load Power", "load-power", "loadsPower"),
FoxESSEnergyGenerated(coordinator, name, deviceID),
FoxESSEnergyGeneratedMonth(coordinator, name, deviceID),
FoxESSEnergyGridConsumption(coordinator, name, deviceID),
FoxESSEnergyFeedin(coordinator, name, deviceID),
FoxESSEnergyBatCharge(coordinator, name, deviceID),
Expand Down Expand Up @@ -538,7 +540,19 @@ async def getReportDailyGeneration(hass, allData, apiKey, deviceSN, deviceID):
_LOGGER.debug(f"OA Daily Generation Report data, today has no value: {parsed} set to 0")
else:
allData["reportDailyGeneration"]["value"] = parsed['today']
_LOGGER.debug(f"OA Daily Generation Report data: {parsed} and todays value {parsed['today']} ")
_LOGGER.debug(f"OA Daily Generation Report data: todays value {parsed['today']} ")
if "month" not in parsed:
allData["reportDailyGeneration"]["month"] = 0
_LOGGER.debug(f"OA Daily Generation Report data, month has no value: {parsed} set to 0")
else:
allData["reportDailyGeneration"]["month"] = parsed['month']
_LOGGER.debug(f"OA Daily Generation Report data: month value {parsed['month']} ")
if "cumulative" not in parsed:
allData["reportDailyGeneration"]["cumulative"] = 0
_LOGGER.debug(f"OA Daily Generation Report data, cumulative has no value: {parsed} set to 0")
else:
allData["reportDailyGeneration"]["cumulative"] = parsed['cumulative']
_LOGGER.debug(f"OA Daily Generation Report data: cumulative value {parsed['cumulative']} ")
return False
else:
_LOGGER.debug(f"OA Daily Generation Report Bad Response: {response} "+ restOAgen.data)
Expand Down Expand Up @@ -869,6 +883,76 @@ def native_value(self) -> str | None:
return energygenerated
return None

class FoxESSEnergyGeneratedMonth(CoordinatorEntity, SensorEntity):

_attr_state_class: SensorStateClass = SensorStateClass.TOTAL_INCREASING
_attr_device_class = SensorDeviceClass.ENERGY
_attr_native_unit_of_measurement = UnitOfEnergy.KILO_WATT_HOUR

def __init__(self, coordinator, name, deviceID):
super().__init__(coordinator=coordinator)
_LOGGER.debug("Initiating Entity - Energy Generated Month")
self._attr_name = name+" - Energy Generated Month"
self._attr_unique_id = deviceID+"energy-generated-month"
self.status = namedtuple(
"status",
[
ATTR_DATE,
ATTR_TIME,
],
)

@property
def native_value(self) -> str | None:
if "month" not in self.coordinator.data["reportDailyGeneration"]:
_LOGGER.debug("reportDailyGeneration month None")
else:
if self.coordinator.data["reportDailyGeneration"]["month"] == 0:
energygenerated = 0
else:
energygenerated = self.coordinator.data["reportDailyGeneration"]["month"]
if energygenerated > 0:
energygenerated = round(energygenerated,3)
else:
energygenerated = 0
return energygenerated
return None

class FoxESSEnergyThroughput(CoordinatorEntity, SensorEntity):

_attr_state_class: SensorStateClass = SensorStateClass.TOTAL_INCREASING
_attr_device_class = SensorDeviceClass.ENERGY
_attr_native_unit_of_measurement = UnitOfEnergy.KILO_WATT_HOUR

def __init__(self, coordinator, name, deviceID):
super().__init__(coordinator=coordinator)
_LOGGER.debug("Initiating Entity - Energy Throughput")
self._attr_name = name+" - Energy Throughput"
self._attr_unique_id = deviceID+"energy-throughput"
self.status = namedtuple(
"status",
[
ATTR_DATE,
ATTR_TIME,
],
)

@property
def native_value(self) -> str | None:
if "energyThroughput" not in self.coordinator.data["raw"]:
_LOGGER.debug("raw Energy Throughput None")
else:
if self.coordinator.data["raw"]["energyThroughput"] == 0:
energygenerated = 0
else:
energygenerated = self.coordinator.data["raw"]["energyThroughput"]
if energygenerated > 0:
energygenerated = round(energygenerated,3)
else:
energygenerated = 0
return energygenerated
return None


class FoxESSEnergyGridConsumption(CoordinatorEntity, SensorEntity):

Expand Down

0 comments on commit 451f03b

Please sign in to comment.