From 4a1802d00e9132885e6f44adad2405a366aa7389 Mon Sep 17 00:00:00 2001 From: Rogier van Staveren Date: Sat, 26 Oct 2024 15:00:02 +0200 Subject: [PATCH] Implement and use readuntil to read from stream --- benqprojector/benqconnection.py | 22 ++++++++++++++++++++++ benqprojector/benqprojector.py | 6 +++++- 2 files changed, 27 insertions(+), 1 deletion(-) diff --git a/benqprojector/benqconnection.py b/benqprojector/benqconnection.py index 5791fc5..2f3bf6d 100644 --- a/benqprojector/benqconnection.py +++ b/benqprojector/benqconnection.py @@ -118,6 +118,28 @@ async def readline(self) -> bytes: except TimeoutError: return b"" + async def readuntil(self, separator=b'\n'): + """ + Read data until separator is found. + """ + if self._reader.at_eof(): + return b"" + + try: + return await asyncio.wait_for( + self._reader.readuntil(separator), timeout=self._read_timeout + ) + except asyncio.IncompleteReadError as ex: + logger.exception("Incomplete read") + if ex.partial is not None: + return ex.partial + return b"" + except ConnectionError as ex: + await self.close() + raise BenQConnectionError(ex.strerror) from ex + except TimeoutError: + return b"" + async def write(self, data: bytes) -> int: """ Output the given string over the connection. diff --git a/benqprojector/benqprojector.py b/benqprojector/benqprojector.py index efe126f..ebb3682 100644 --- a/benqprojector/benqprojector.py +++ b/benqprojector/benqprojector.py @@ -165,6 +165,7 @@ class BenQProjector(ABC): connection = None has_prompt = None + _separator = b"\n" _init: bool = True _has_to_wait_for_prompt = True @@ -335,6 +336,9 @@ async def connect(self, loop=None, interval: float = None) -> bool: if self.has_prompt is None: self.has_prompt = await self._detect_prompt() + if self.has_prompt is False: + self._separator = b'#' + power = None try: power = await self._send_command("pow") @@ -707,7 +711,7 @@ async def _read_response(self) -> str: response = b"" last_response = datetime.now() while True: - _response = await self.connection.readline() + _response = await self.connection.readuntil(self._separator) if len(_response) > 0: response += _response if any(c in _response for c in END_OF_RESPONSE):