Home Assistant Unofficial Reference 2024.12.1
sensor.py
Go to the documentation of this file.
1 """Definition and setup of the Omnilogic Sensors for Home Assistant."""
2 
3 from typing import Any
4 
5 from homeassistant.components.sensor import SensorDeviceClass, SensorEntity
6 from homeassistant.config_entries import ConfigEntry
7 from homeassistant.const import (
8  CONCENTRATION_PARTS_PER_MILLION,
9  PERCENTAGE,
10  UnitOfElectricPotential,
11  UnitOfMass,
12  UnitOfTemperature,
13  UnitOfVolume,
14 )
15 from homeassistant.core import HomeAssistant
16 from homeassistant.helpers.entity_platform import AddEntitiesCallback
17 
18 from .common import check_guard
19 from .const import COORDINATOR, DEFAULT_PH_OFFSET, DOMAIN, PUMP_TYPES
20 from .coordinator import OmniLogicUpdateCoordinator
21 from .entity import OmniLogicEntity
22 
23 
25  hass: HomeAssistant, entry: ConfigEntry, async_add_entities: AddEntitiesCallback
26 ) -> None:
27  """Set up the sensor platform."""
28 
29  coordinator: OmniLogicUpdateCoordinator = hass.data[DOMAIN][entry.entry_id][
30  COORDINATOR
31  ]
32  entities = []
33 
34  for item_id, item in coordinator.data.items():
35  id_len = len(item_id)
36  item_kind = item_id[-2]
37  entity_settings = SENSOR_TYPES.get((id_len, item_kind))
38 
39  if not entity_settings:
40  continue
41 
42  for entity_setting in entity_settings:
43  entity_classes: dict[str, type] = entity_setting["entity_classes"]
44  for state_key, entity_class in entity_classes.items():
45  if check_guard(state_key, item, entity_setting):
46  continue
47 
48  entity = entity_class(
49  coordinator=coordinator,
50  state_key=state_key,
51  name=entity_setting["name"],
52  kind=entity_setting["kind"],
53  item_id=item_id,
54  device_class=entity_setting["device_class"],
55  icon=entity_setting["icon"],
56  unit=entity_setting["unit"],
57  )
58 
59  entities.append(entity)
60 
61  async_add_entities(entities)
62 
63 
65  """Defines an Omnilogic sensor entity."""
66 
67  def __init__(
68  self,
69  coordinator: OmniLogicUpdateCoordinator,
70  kind: str,
71  name: str,
72  device_class: SensorDeviceClass | None,
73  icon: str,
74  unit: str,
75  item_id: tuple,
76  state_key: str,
77  ) -> None:
78  """Initialize Entities."""
79  super().__init__(
80  coordinator=coordinator,
81  kind=kind,
82  name=name,
83  item_id=item_id,
84  icon=icon,
85  )
86 
87  backyard_id = item_id[:2]
88  unit_type = coordinator.data[backyard_id].get("Unit-of-Measurement")
89 
90  self._unit_type_unit_type = unit_type
91  self._attr_device_class_attr_device_class = device_class
92  self._attr_native_unit_of_measurement_attr_native_unit_of_measurement = unit
93  self._state_key_state_key = state_key
94 
95 
97  """Define an OmniLogic Temperature (Air/Water) Sensor."""
98 
99  @property
100  def native_value(self):
101  """Return the state for the temperature sensor."""
102  sensor_data = self.coordinator.data[self._item_id_item_id][self._state_key_state_key]
103 
104  hayward_state = sensor_data
105  hayward_unit_of_measure = UnitOfTemperature.FAHRENHEIT
106  state = sensor_data
107 
108  if self._unit_type_unit_type_unit_type == "Metric":
109  hayward_state = round((int(hayward_state) - 32) * 5 / 9, 1)
110  hayward_unit_of_measure = UnitOfTemperature.CELSIUS
111 
112  if int(sensor_data) == -1:
113  hayward_state = None
114  state = None
115 
116  self._attrs["hayward_temperature"] = hayward_state
117  self._attrs["hayward_unit_of_measure"] = hayward_unit_of_measure
118 
119  self._attr_native_unit_of_measurement_attr_native_unit_of_measurement_attr_native_unit_of_measurement = UnitOfTemperature.FAHRENHEIT
120 
121  return state
122 
123 
125  """Define an OmniLogic Pump Speed Sensor."""
126 
127  @property
128  def native_value(self):
129  """Return the state for the pump speed sensor."""
130 
131  pump_type = PUMP_TYPES[
132  self.coordinator.data[self._item_id_item_id].get(
133  "Filter-Type", self.coordinator.data[self._item_id_item_id].get("Type", {})
134  )
135  ]
136  pump_speed = self.coordinator.data[self._item_id_item_id][self._state_key_state_key]
137 
138  if pump_type == "VARIABLE":
139  self._attr_native_unit_of_measurement_attr_native_unit_of_measurement_attr_native_unit_of_measurement = PERCENTAGE
140  state = pump_speed
141  elif pump_type == "DUAL":
142  self._attr_native_unit_of_measurement_attr_native_unit_of_measurement_attr_native_unit_of_measurement = None
143  if pump_speed == 0:
144  state = "off"
145  elif pump_speed == self.coordinator.data[self._item_id_item_id].get(
146  "Min-Pump-Speed"
147  ):
148  state = "low"
149  elif pump_speed == self.coordinator.data[self._item_id_item_id].get(
150  "Max-Pump-Speed"
151  ):
152  state = "high"
153 
154  self._attrs["pump_type"] = pump_type
155 
156  return state
157 
158 
160  """Define an OmniLogic Salt Level Sensor."""
161 
162  @property
163  def native_value(self):
164  """Return the state for the salt level sensor."""
165 
166  salt_return = self.coordinator.data[self._item_id_item_id][self._state_key_state_key]
167 
168  if self._unit_type_unit_type_unit_type == "Metric":
169  salt_return = round(int(salt_return) / 1000, 2)
171  f"{UnitOfMass.GRAMS}/{UnitOfVolume.LITERS}"
172  )
173 
174  return salt_return
175 
176 
178  """Define an OmniLogic Chlorinator Sensor."""
179 
180  @property
181  def native_value(self):
182  """Return the state for the chlorinator sensor."""
183  return self.coordinator.data[self._item_id_item_id][self._state_key_state_key]
184 
185 
187  """Define an OmniLogic pH Sensor."""
188 
189  @property
190  def native_value(self):
191  """Return the state for the pH sensor."""
192 
193  ph_state = self.coordinator.data[self._item_id_item_id][self._state_key_state_key]
194 
195  if ph_state == 0:
196  ph_state = None
197  else:
198  ph_state = float(ph_state) + float(
199  self.coordinator.config_entry.options.get(
200  "ph_offset", DEFAULT_PH_OFFSET
201  )
202  )
203 
204  return ph_state
205 
206 
208  """Define an OmniLogic ORP Sensor."""
209 
210  def __init__(
211  self,
212  coordinator: OmniLogicUpdateCoordinator,
213  state_key: str,
214  name: str,
215  kind: str,
216  item_id: tuple,
217  device_class: SensorDeviceClass | None,
218  icon: str,
219  unit: str,
220  ) -> None:
221  """Initialize the sensor."""
222  super().__init__(
223  coordinator=coordinator,
224  kind=kind,
225  name=name,
226  device_class=device_class,
227  icon=icon,
228  unit=unit,
229  item_id=item_id,
230  state_key=state_key,
231  )
232 
233  @property
234  def native_value(self):
235  """Return the state for the ORP sensor."""
236 
237  orp_state = int(self.coordinator.data[self._item_id_item_id][self._state_key_state_key])
238 
239  if orp_state == -1:
240  orp_state = None
241 
242  return orp_state
243 
244 
245 SENSOR_TYPES: dict[tuple[int, str], list[dict[str, Any]]] = {
246  (2, "Backyard"): [
247  {
248  "entity_classes": {"airTemp": OmniLogicTemperatureSensor},
249  "name": "Air Temperature",
250  "kind": "air_temperature",
251  "device_class": SensorDeviceClass.TEMPERATURE,
252  "icon": None,
253  "unit": UnitOfTemperature.FAHRENHEIT,
254  "guard_condition": [{}],
255  },
256  ],
257  (4, "BOWS"): [
258  {
259  "entity_classes": {"waterTemp": OmniLogicTemperatureSensor},
260  "name": "Water Temperature",
261  "kind": "water_temperature",
262  "device_class": SensorDeviceClass.TEMPERATURE,
263  "icon": None,
264  "unit": UnitOfTemperature.FAHRENHEIT,
265  "guard_condition": [{}],
266  },
267  ],
268  (6, "Filter"): [
269  {
270  "entity_classes": {"filterSpeed": OmniLogicPumpSpeedSensor},
271  "name": "Speed",
272  "kind": "filter_pump_speed",
273  "device_class": None,
274  "icon": "mdi:speedometer",
275  "unit": PERCENTAGE,
276  "guard_condition": [
277  {"Filter-Type": "FMT_SINGLE_SPEED"},
278  ],
279  },
280  ],
281  (6, "Pumps"): [
282  {
283  "entity_classes": {"pumpSpeed": OmniLogicPumpSpeedSensor},
284  "name": "Pump Speed",
285  "kind": "pump_speed",
286  "device_class": None,
287  "icon": "mdi:speedometer",
288  "unit": PERCENTAGE,
289  "guard_condition": [
290  {"Type": "PMP_SINGLE_SPEED"},
291  ],
292  },
293  ],
294  (6, "Chlorinator"): [
295  {
296  "entity_classes": {"Timed-Percent": OmniLogicChlorinatorSensor},
297  "name": "Setting",
298  "kind": "chlorinator",
299  "device_class": None,
300  "icon": "mdi:gauge",
301  "unit": PERCENTAGE,
302  "guard_condition": [
303  {
304  "Shared-Type": "BOW_SHARED_EQUIPMENT",
305  "status": "0",
306  },
307  {
308  "operatingMode": "2",
309  },
310  ],
311  },
312  {
313  "entity_classes": {"avgSaltLevel": OmniLogicSaltLevelSensor},
314  "name": "Salt Level",
315  "kind": "salt_level",
316  "device_class": None,
317  "icon": "mdi:gauge",
318  "unit": CONCENTRATION_PARTS_PER_MILLION,
319  "guard_condition": [
320  {
321  "Shared-Type": "BOW_SHARED_EQUIPMENT",
322  "status": "0",
323  },
324  ],
325  },
326  ],
327  (6, "CSAD"): [
328  {
329  "entity_classes": {"ph": OmniLogicPHSensor},
330  "name": "pH",
331  "kind": "csad_ph",
332  "device_class": None,
333  "icon": "mdi:gauge",
334  "unit": "pH",
335  "guard_condition": [
336  {"ph": ""},
337  ],
338  },
339  {
340  "entity_classes": {"orp": OmniLogicORPSensor},
341  "name": "ORP",
342  "kind": "csad_orp",
343  "device_class": None,
344  "icon": "mdi:gauge",
345  "unit": UnitOfElectricPotential.MILLIVOLT,
346  "guard_condition": [
347  {"orp": ""},
348  ],
349  },
350  ],
351 }
None __init__(self, OmniLogicUpdateCoordinator coordinator, str state_key, str name, str kind, tuple item_id, SensorDeviceClass|None device_class, str icon, str unit)
Definition: sensor.py:220
None __init__(self, OmniLogicUpdateCoordinator coordinator, str kind, str name, SensorDeviceClass|None device_class, str icon, str unit, tuple item_id, str state_key)
Definition: sensor.py:77
web.Response get(self, web.Request request, str config_key)
Definition: view.py:88
def check_guard(state_key, item, entity_setting)
Definition: common.py:4
None async_setup_entry(HomeAssistant hass, ConfigEntry entry, AddEntitiesCallback async_add_entities)
Definition: sensor.py:26