From 11a19438cb2c4af35b838c6527d613b5d631501c Mon Sep 17 00:00:00 2001 From: "J. Nick Koston" Date: Mon, 4 Sep 2023 12:56:23 -0500 Subject: [PATCH] Avoid a few calls to fetch loop time (#533) --- aioesphomeapi/_frame_helper/base.py | 6 ++++-- aioesphomeapi/client.py | 4 +++- aioesphomeapi/connection.py | 20 ++++++++++++-------- aioesphomeapi/reconnect_logic.py | 4 +++- 4 files changed, 22 insertions(+), 12 deletions(-) diff --git a/aioesphomeapi/_frame_helper/base.py b/aioesphomeapi/_frame_helper/base.py index 8a53cb9..590dab7 100644 --- a/aioesphomeapi/_frame_helper/base.py +++ b/aioesphomeapi/_frame_helper/base.py @@ -75,8 +75,10 @@ class APIFrameHelper(asyncio.Protocol): async def perform_handshake(self, timeout: float) -> None: """Perform the handshake with the server.""" - handshake_handle = self._loop.call_later( - timeout, self._set_ready_future_exception, asyncio.TimeoutError() + handshake_handle = self._loop.call_at( + self._loop.time() + timeout, + self._set_ready_future_exception, + asyncio.TimeoutError, ) try: await self._ready_future diff --git a/aioesphomeapi/client.py b/aioesphomeapi/client.py index c606a0b..0bf0b14 100644 --- a/aioesphomeapi/client.py +++ b/aioesphomeapi/client.py @@ -649,7 +649,9 @@ class APIClient: ) loop = self._loop - timeout_handle = loop.call_later(timeout, self._handle_timeout, connect_future) + timeout_handle = loop.call_at( + loop.time() + timeout, self._handle_timeout, connect_future + ) timeout_expired = False connect_ok = False try: diff --git a/aioesphomeapi/connection.py b/aioesphomeapi/connection.py index 36f5703..f0bf0e7 100644 --- a/aioesphomeapi/connection.py +++ b/aioesphomeapi/connection.py @@ -396,11 +396,11 @@ class APIConnection: received_name, ) - def _async_schedule_keep_alive(self) -> None: + def _async_schedule_keep_alive(self, now: float) -> None: """Start the keep alive task.""" self._send_pending_ping = True - self._ping_timer = self._loop.call_later( - self._keep_alive_interval, self._async_send_keep_alive + self._ping_timer = self._loop.call_at( + now + self._keep_alive_interval, self._async_send_keep_alive ) def _async_send_keep_alive(self) -> None: @@ -408,14 +408,16 @@ class APIConnection: if not self._is_socket_open: return + now = self._loop.time() + if self._send_pending_ping: self.send_message(PING_REQUEST_MESSAGE) if self._pong_timer is None: # Do not reset the timer if it's already set # since the only thing we want to reset the timer # is if we receive a pong. - self._pong_timer = self._loop.call_later( - self._keep_alive_timeout, self._async_pong_not_received + self._pong_timer = self._loop.call_at( + now + self._keep_alive_timeout, self._async_pong_not_received ) else: # @@ -434,7 +436,7 @@ class APIConnection: self._keep_alive_interval, ) - self._async_schedule_keep_alive() + self._async_schedule_keep_alive(now) def _async_cancel_pong_timer(self) -> None: """Cancel the pong timer.""" @@ -466,7 +468,7 @@ class APIConnection: await self._connect_hello() if login: await self.login(check_connected=False) - self._async_schedule_keep_alive() + self._async_schedule_keep_alive(self._loop.time()) async def connect(self, *, login: bool) -> None: if self._connection_state != ConnectionState.INITIALIZED: @@ -661,7 +663,9 @@ class APIConnection: # We must not await without a finally or # the message could fail to be removed if the # the await is cancelled - timeout_handle = self._loop.call_later(timeout, self._handle_timeout, fut) + timeout_handle = self._loop.call_at( + self._loop.time() + timeout, self._handle_timeout, fut + ) timeout_expired = False try: await fut diff --git a/aioesphomeapi/reconnect_logic.py b/aioesphomeapi/reconnect_logic.py index 49575ac..55f564b 100644 --- a/aioesphomeapi/reconnect_logic.py +++ b/aioesphomeapi/reconnect_logic.py @@ -146,7 +146,9 @@ class ReconnectLogic(zeroconf.RecordUpdateListener): if not delay: self._call_connect_once() return - self._connect_timer = self.loop.call_later(delay, self._call_connect_once) + self._connect_timer = self.loop.call_at( + self.loop.time() + delay, self._call_connect_once + ) def _call_connect_once(self) -> None: """Call the connect logic once.