Skip to content
This repository was archived by the owner on Jun 9, 2023. It is now read-only.
Merged
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
46 changes: 24 additions & 22 deletions aiosenseme/device.py
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,6 @@
import ipaddress
import logging
import random
import time
import traceback
from typing import Any, Callable, Tuple

Expand Down Expand Up @@ -212,7 +211,7 @@ def __init__(

self._data = dict()
self._is_running = False
self._is_connected = False
self._is_connected = asyncio.Event()
self._connection_lost = False
self._endpoint = None
self._listener_task = None
Expand All @@ -221,7 +220,7 @@ def __init__(
self._leftover = ""
self._callbacks = []
self._coroutine_callbacks = []
self._first_update = False
self._first_update = asyncio.Event()

def __eq__(self, other: Any) -> bool:
"""Equals magic method."""
Expand Down Expand Up @@ -323,12 +322,12 @@ def address(self) -> str:
@property
def available(self) -> bool:
"""Return True when device is connected and all parameters have been updated."""
return self._is_connected and self._first_update
return self._is_connected.is_set() and self._first_update.is_set()

@property
def connected(self) -> bool:
"""Return True when device is connected."""
return self._is_connected
return self._is_connected.is_set()

@property
def device_type(self) -> str:
Expand Down Expand Up @@ -630,7 +629,7 @@ async def async_fill_out_info(self) -> bool:
# no proper response is received
line = await asyncio.wait_for(reader.readuntil(b")"), 10)
leftover, _ = self._process_message(leftover + line.decode("utf-8"))
if self._first_update:
if self._first_update.is_set():
return True
except asyncio.TimeoutError:
_LOGGER.debug(
Expand Down Expand Up @@ -691,12 +690,15 @@ async def async_update(self, connection_lost=False, timeout_seconds=10) -> bool:
self._connection_lost = True
if not self._is_running:
self.start()
start = int(time.time())
while not self.available:
await asyncio.sleep(0.1)
if int(time.time()) - start >= timeout_seconds:
return False
return True
try:
await asyncio.wait(
[self._first_update.wait(), self._is_connected.wait()],
timeout=timeout_seconds,
)
except asyncio.TimeoutError:
return False
else:
return True

def _execute_callbacks(self):
"""Run all callbacks to indicate something has changed."""
Expand Down Expand Up @@ -766,15 +768,15 @@ def _process_message(self, line) -> str:
_LOGGER.debug("%s: Param updated: [%s]='%s'", self.name, key, value)
if self.is_fan:
if key == "WINTERMODE;STATE":
if not self._first_update:
self._first_update = True
if not self._first_update.is_set():
self._first_update.set()
_LOGGER.debug("%s: First Update Complete", self.name)
else:
if key == "SNSROCC;TIMEOUT;MIN":
if not self._first_update:
self._first_update = True
if not self._first_update.is_set():
self._first_update.set()
_LOGGER.debug("%s: First Update Complete", self.name)
if self._first_update and key not in SUPPRESS_CALLBACK_PARAMS:
if self._first_update.is_set() and key not in SUPPRESS_CALLBACK_PARAMS:
should_callback = True
# update certain local variables that are not part of data
if key == "FW;NAME":
Expand Down Expand Up @@ -852,14 +854,14 @@ async def _listener(self):
try:
if self._error_count > 10:
_LOGGER.error("%s: Listener task too many errors", self.name)
self._is_connected = False
self._is_connected.clear()
self._updater_task.cancel()
if self._endpoint is not None:
self._endpoint.close()
self._endpoint = None
break
if self._endpoint is None:
self._is_connected = False
self._is_connected.clear()
self._endpoint = SensemeEndpoint()
try:
_LOGGER.debug("%s: Connecting", self.name)
Expand All @@ -871,7 +873,7 @@ async def _listener(self):
_LOGGER.debug("%s: Creating Updater Task", self.name)
self._updater_task = asyncio.create_task(self._updater())
self._error_count = 0
self._is_connected = True
self._is_connected.set()
if self._connection_lost:
_LOGGER.warning(
"%s: Connection to address %s restored",
Expand Down Expand Up @@ -909,8 +911,8 @@ async def _listener(self):
"%s: Connection to address %s lost", self.name, self.address
)
self._data = dict()
self._is_connected = False
self._first_update = False
self._is_connected.clear()
self._first_update.clear()
self._connection_lost = True
self._execute_callbacks() # tell callbacks we disconnected
self._endpoint = None
Expand Down