Skip to content

Commit

Permalink
Update aiophyn version and modify the shutoff switch to a valve
Browse files Browse the repository at this point in the history
  • Loading branch information
jordanruthe committed Jan 11, 2024
1 parent 19e6169 commit c3107d6
Show file tree
Hide file tree
Showing 7 changed files with 77 additions and 239 deletions.
2 changes: 1 addition & 1 deletion custom_components/phyn/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -17,7 +17,7 @@

_LOGGER = logging.getLogger(__name__)

PLATFORMS = [Platform.SENSOR, Platform.SWITCH]
PLATFORMS = [Platform.SENSOR, Platform.VALVE]


async def async_setup_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
Expand Down
38 changes: 26 additions & 12 deletions custom_components/phyn/device.py
Original file line number Diff line number Diff line change
Expand Up @@ -8,26 +8,23 @@
from aiophyn.errors import RequestError
from async_timeout import timeout

from .exceptions import HaAuthError, HaCannotConnect

from homeassistant.core import HomeAssistant
from homeassistant.helpers.update_coordinator import DataUpdateCoordinator, UpdateFailed
import homeassistant.util.dt as dt_util

from .exceptions import HaAuthError, HaCannotConnect
from .const import DOMAIN as PHYN_DOMAIN, LOGGER

from .devices.pp import (
PhynFlowState,
PhynDailyUsageSensor,
PhynConsumptionSensor,
PhynCurrentFlowRateSensor,
PhynSwitch,
PhynValve,
PhynTemperatureSensor,
PhynPressureSensor
)

import json


class PhynDeviceDataUpdateCoordinator(DataUpdateCoordinator):
"""Phyn device object."""
Expand All @@ -46,6 +43,7 @@ def __init__(
self._device_state: dict[str, Any] = {}
self._rt_device_state: dict[str, Any] = {}
self._water_usage: dict[str, Any] = {}
self._last_known_valve_state: bool = True

if product_code in ['PP1','PP2']:
# Entities for Phyn Plus 1 and Phyn Plus 2
Expand All @@ -56,8 +54,7 @@ def __init__(
PhynConsumptionSensor(self),
PhynTemperatureSensor(self),
PhynPressureSensor(self),

PhynSwitch(self),
PhynValve(self),
]

super().__init__(
Expand Down Expand Up @@ -120,20 +117,26 @@ def current_flow_rate(self) -> float:
if round(self._rt_device_state['flow']['v'], 2) == 0:
return 0.0
return round(self._rt_device_state['flow']['v'], 3)
if "flow" not in self._device_state:
return None
return round(self._device_state["flow"]["mean"], 3)

@property
def current_psi(self) -> float:
"""Return the current pressure in psi."""
if "sensor_data" in self._rt_device_state:
return round(self._rt_device_state['sensor_data']['pressure']['v'], 2)
if "sensor_data" not in self._device_state:
return None
return round(self._device_state["pressure"]["mean"], 2)

@property
def temperature(self) -> float:
"""Return the current temperature in degrees F."""
if "sensor_data" in self._rt_device_state:
return round(self._rt_device_state['sensor_data']['temperature']['v'], 2)
if "sensor_data" not in self._device_state:
return None
return round(self._device_state["temperature"]["mean"], 2)

@property
Expand All @@ -159,14 +162,27 @@ def serial_number(self) -> str:
return self._device_state["serial_number"]

@property
def valve_state(self) -> str:
def valve_open(self) -> bool:
"""Return the valve state for the device."""
if self.valve_changing:
return self._last_known_valve_state
if "sov_state" in self._rt_device_state:
return self._rt_device_state["sov_state"]
self._last_known_valve_state = self._rt_device_state["sov_state"] == "Open"
return self._rt_device_state["sov_state"] == "Open"
if "sov_status" in self._device_state:
return self._device_state["sov_status"]["v"]
self._last_known_valve_state = self._device_state["sov_status"]["v"] == "Open"
return self._device_state["sov_status"]["v"] == "Open"
return None

@property
def valve_changing(self) -> bool:
"""Return the valve changing status"""
if "sov_state" in self._rt_device_state:
return self._rt_device_state["sov_state"] == "Partial"
if "sov_status" in self._device_state:
return self._device_state["sov_status"]["v"] == "Partial"
return False

async def async_setup(self):
"""Setup a new device coordinator"""
LOGGER.debug("Setting up coordinator")
Expand All @@ -191,9 +207,7 @@ async def _update_consumption_data(self, *_) -> None:
LOGGER.debug("Updated Phyn consumption data: %s", self._water_usage)

async def on_device_update(self, device_id, data):
#LOGGER.debug("Received new data: %s" % json.dumps(data, indent=2))
if device_id == self._phyn_device_id:
self._rt_device_state = data
for entity in self.entities:
#LOGGER.debug(f"Updating {entity} ({entity.unique_id}, {entity.entity_id})")
entity.async_write_ha_state()
89 changes: 44 additions & 45 deletions custom_components/phyn/devices/pp.py
Original file line number Diff line number Diff line change
@@ -1,21 +1,17 @@
"""Support for Phyn Plus Water Monitor sensors."""
from __future__ import annotations

from homeassistant.components.binary_sensor import (
BinarySensorEntity,
BinarySensorDeviceClass,
)

from homeassistant.components.sensor import (
SensorDeviceClass,
SensorEntity,
SensorStateClass,
)
from homeassistant.components.switch import SwitchEntity
from homeassistant.core import callback
from homeassistant.config_entries import ConfigEntry
from homeassistant.components.valve import (
ValveDeviceClass,
ValveEntity,
ValveEntityFeature
)
from homeassistant.const import (
PERCENTAGE,
UnitOfPressure,
UnitOfTemperature,
UnitOfVolume,
Expand Down Expand Up @@ -106,54 +102,57 @@ def native_value(self) -> float | None:
"""Return the current flow rate."""
if self._device.current_flow_rate is None:
return None
return round(self._device.current_flow_rate, 1)
return round(self._device.current_flow_rate, 1)


class PhynSwitch(PhynEntity, SwitchEntity):
"""Switch class for the Phyn valve."""
class PhynValve(PhynEntity, ValveEntity):
"""ValveEntity for the Phyn valve."""

def __init__(self, device) -> None:
"""Initialize the Phyn switch."""
"""Initialize the Phyn Valve."""
super().__init__("shutoff_valve", "Shutoff valve", device)
self._state = self._device.valve_state == "Open"

@property
def is_on(self) -> bool:
"""Return True if the valve is open. Keep state for transition"""
if self._device.valve_state == "Partial":
return self._state
self._state = self._device.valve_state == "Open"
return self._state

@property
def icon(self):
"""Return the icon to use for the valve."""
if self.is_on:
return "mdi:valve-open"
return "mdi:valve-closed"

async def async_turn_on(self, **kwargs: Any) -> None:
self._attr_supported_features = ValveEntityFeature(ValveEntityFeature.OPEN | ValveEntityFeature.CLOSE)
self._attr_device_class = ValveDeviceClass.WATER
self._attr_reports_position = False
self._last_known_state: bool = False

async def async_open_valve(self) -> None:
"""Open the valve."""
await self._device.api_client.device.open_valve(self._device.id)
#self._state = True
#self.async_write_ha_state()

async def async_turn_off(self, **kwargs: Any) -> None:
def open_valve(self) -> None:
"""Open the valve."""
raise NotImplementedError()

async def async_close_valve(self) -> None:
"""Close the valve."""
await self._device.api_client.device.close_valve(self._device.id)
#self._state = False
#self.async_write_ha_state()

@callback
def async_update_state(self) -> None:
"""Retrieve the latest valve state and update the state machine."""
self._state = self._device.valve_state == "Open"
self.async_write_ha_state()

async def async_added_to_hass(self) -> None:
"""When entity is added to hass."""
self.async_on_remove(self._device.async_add_listener(self.async_update_state))
def close_valve(self) -> None:
"""Close valve."""
raise NotImplementedError()

@property
def _attr_is_closed(self) -> bool | None:
""" Is the valve closed """
if self._device.valve_open is None:
return None
self._last_known_state = self._device.valve_open
return not self._device.valve_open

@property
def _attr_is_opening(self) -> bool:
""" Is the valve opening """
if self._device.valve_changing and self._device._last_known_valve_state is False:
return True
return False

@property
def _attr_is_closing(self) -> bool:
""" Is the valve closing """
if self._device.valve_changing and self._device._last_known_valve_state is True:
return True
return False


class PhynTemperatureSensor(PhynEntity, SensorEntity):
Expand Down
Loading

0 comments on commit c3107d6

Please sign in to comment.