示例#1
0
    async def sendUDPMessage(self, message):
        """Send the UDP message to the bulb."""
        connid = hex(int(time() * 10000000))[2:]
        data = None
        # overall 10 sec. for time out
        timeout = 10
        send_interval = 0.5
        max_send_datagrams = int(timeout / send_interval)

        try:
            _LOGGER.debug(
                "[wizlight {}, connid {}] connecting to UDP port with send_interval of {} sec.."
                .format(self.ip, connid, send_interval))
            stream = await asyncio.wait_for(
                asyncio_dgram.connect((self.ip, self.port)), timeout)
            _LOGGER.debug(
                "[wizlight {}, connid {}] listening for response datagram".
                format(self.ip, connid))

            receive_task = asyncio.create_task(
                self.receiveUDPwithTimeout(stream, timeout))

            for i in range(max_send_datagrams):
                _LOGGER.debug(
                    "[wizlight {}, connid {}] sending command datagram {}: {}".
                    format(self.ip, connid, i, message))
                asyncio.create_task(stream.send(bytes(message, "utf-8")))
                done, pending = await asyncio.wait([receive_task],
                                                   timeout=send_interval)
                if done:
                    break

            await receive_task
            data = receive_task.result()

        except asyncio.TimeoutError:
            _LOGGER.debug(
                "[wizlight {}, connid {}] Failed to do UDP call(s) to wiz light - Timeout Error!"
                .format(self.ip, connid),
                exc_info=False,
            )
            raise WizLightTimeOutError("The request to the bulb timed out")
        finally:
            try:
                stream.close()
            except UnboundLocalError:
                raise WizLightConnectionError(
                    "Bulb is offline or IP address is not correct.")

        if data is not None and len(data) is not None:
            resp = json.loads(data.decode())
            if "error" not in resp:
                _LOGGER.debug(
                    "[wizlight {}, connid {}] response received: {}".format(
                        self.ip, connid, resp))
                return resp
            else:
                # exception should be created
                raise ValueError("Can't read response from the bulb. Debug:",
                                 resp)
示例#2
0
文件: sender.py 项目: Pegacraft/wizPy
async def send_udp(ip: str, message: str) -> str:
    """Send the UDP message to the bulb."""
    # overall 10 sec. for time out
    timeout = 2
    send_interval = 0.5
    max_send_datagrams = 2
    port = 38899

    try:
        stream = await asyncio.wait_for(asyncio_dgram.connect((ip, port)),
                                        timeout)
        receive_task = asyncio.create_task(receive_udp(
            stream,
            timeout,
        ))
        i = 0
        while not receive_task.done() and i < max_send_datagrams:
            asyncio.create_task(stream.send(bytes(message, "utf-8")))
            await asyncio.sleep(send_interval)
            i += 1

        await receive_task
        data = receive_task.result()
    finally:
        try:
            stream.close()
        except UnboundLocalError:
            raise ConnectionError(
                "Bulb is offline or IP address is not correct.")
    if data is not None and len(data) is not None:
        return data.decode()
示例#3
0
    async def sendUDPMessage(self,
                             message,
                             timeout=60,
                             send_interval=0.5,
                             max_send_datagrams=100):
        """Send the UDP message to the bulb."""
        connid = hex(int(time() * 10000000))[2:]
        data = None

        try:
            _LOGGER.debug(
                "[wizlight {}, connid {}] connecting to UDP port".format(
                    self.ip, connid))
            stream = await asyncio.wait_for(
                asyncio_dgram.connect((self.ip, self.port)), timeout)
            _LOGGER.debug(
                "[wizlight {}, connid {}] listening for response datagram".
                format(self.ip, connid))

            receive_task = asyncio.create_task(
                self.receiveUDPwithTimeout(stream, timeout))

            i = 0
            while not receive_task.done() and i < max_send_datagrams:
                _LOGGER.debug(
                    "[wizlight {}, connid {}] sending command datagram {}: {}".
                    format(self.ip, connid, i, message))
                asyncio.create_task(stream.send(bytes(message, "utf-8")))
                await asyncio.sleep(send_interval)
                i += 1

            await receive_task
            data = receive_task.result()

        except asyncio.TimeoutError:
            _LOGGER.exception(
                "[wizlight {}, connid {}] Failed to do UDP call(s) to wiz light"
                .format(self.ip, connid),
                exc_info=False,
            )
        finally:
            try:
                stream.close()
            except UnboundLocalError:
                raise WizLightConnectionError(
                    "Bulb is offline or IP address is not correct")

        if data is not None and len(data) is not None:
            resp = json.loads(data.decode())
            if "error" not in resp:
                _LOGGER.debug(
                    "[wizlight {}, connid {}] response received: {}".format(
                        self.ip, connid, resp))
                return resp
            else:
                # exception should be created
                raise ValueError("Can't read response from the bulb. Debug:",
                                 resp)
示例#4
0
async def raknet_status(host, port):  # Should work on all BE servers
    if port is None:
        port = 19132

    start = perf_counter()

    try:
        stream = await asyncio.wait_for(asyncio_dgram.connect((host, port)),
                                        TIMEOUT)

        #data = b'\x01' + struct.pack('>q', 0) + bytearray.fromhex('00 ff ff 00 fe fe fe fe fd fd fd fd 12 34 56 78')
        await asyncio.wait_for(
            stream.send(
                b'\x01\x00\x00\x00\x00\x00\x00\x00\x00\x00\xff\xff\x00\xfe\xfe\xfe\xfe\xfd\xfd\xfd\xfd\x124Vx'
            ), TIMEOUT)

        data, _ = await asyncio.wait_for(stream.recv(), TIMEOUT)
    except BaseException:
        return DEFAULT
    finally:
        try:
            stream.close()
        except BaseException:
            pass

    latency = round((perf_counter() - start) * 1000, 2)

    data = data[1:]
    name_length = struct.unpack('>H', data[32:34])[0]
    data = data[34:34 + name_length].decode().split(';')

    s_dict = DEFAULT.copy()

    s_dict['online'] = True
    s_dict['players_online'] = int(data[4])
    s_dict['players_max'] = int(data[5])
    s_dict['latency'] = latency
    s_dict['version'] = {
        'brand': data[0],  # string
        'software':
        None,  # string, assumes server is vanilla bc pocketmine + nukkit use query
        'protocol': f'raknet {data[2]}',
        'method': 'raknet'
    }
    s_dict['motd'] = data[1]

    try:
        s_dict['map'] = data[7]
        s_dict['gamemode'] = data[8]
    except IndexError:
        pass

    return s_dict
示例#5
0
    async def infoListener(self):
        print("Listening for info...")
        self.infoStream = await asyncio.wait_for(
            asyncio_dgram.connect((self.bulbIp, self.listenerPort)),
            self.timeout)

        infoData = asyncio.create_task(self.recData(self.infoStream))

        await infoData

        resInfoData = infoData.result()
        self.infoStream.close

        if resInfoData and len(resInfoData):
            return resInfoData.decode()
示例#6
0
  async def async_update(self):
    logger.info("updating " + self._name)
    cypher = encrypt(self._getter + '\0', self._key)

    try:
      sock = await asyncio.wait_for(asyncio_dgram.connect((self._ip, 54321)), 5)
      await asyncio.wait_for(sock.send(cypher), 5)
      cypher, [host, port] = await asyncio.wait_for(sock.recv(), 5)
      message = decrypt(cypher, self._key)
      logger.info("%s -> %s:%s -> %s", self._getter, self._ip, 54321, message)
      self._state = float(message)
    except asyncio.TimeoutError:
      logger.error("Timeout error %s", self._getter)
    except:
      logger.error("Some other arror")
    finally:
      sock.close()
示例#7
0
    async def connect(self, name: str, host: str, port: int = 22023, gameVersion: tuple = None) -> None:
        """
        Connects to the given server via UDP and starts listening for data on success

        Args:
            name (str): Name which will be displayed in Among Us
            host (str): Host/address of the server to connect to
            port (int): Port of the server to connect to, defaults to 22023
            gameVersion (tuple): The version of the game running on the server

        Raises:
            Exception: Something went wrong, never happened while testing
        """
        self._sequence_ids = {}
        self.net_ids = dotdict({})
        self.host, self.port, self.name, self.gameVersion = host, port, name, gameVersion
        try:
            self.socket = await asyncio.wait_for(
                asyncio_dgram.connect((host, port)), timeout=self.connectTimeout / 1000
            )
        except asyncio.TimeoutError:
            logging.debug("Timeout when connecting to the server...")
            self.result = ConnectionException(
                f"Timeout connecting to {host}:{port}", DisconnectReason.Timeout
            )
            await self.disconnect(True)
        except Exception as e:
            logger.exception(e)
            raise
        else:
            logger.info(f"Connected to {host}:{port} [{self.region}]")
            await self.send(
                HelloPacket.create(gameVersion=gameVersion, name=self.name)
            )
            self.closed = False
            self._reader_task = asyncio.create_task(self._reader())
            try:
                await asyncio.wait_for(
                    self.wait_until_ready(), timeout=self.recvTimeout / 1000
                )
            except asyncio.TimeoutError:
                self.result = ConnectionException(
                    "Timed out waiting for messages", DisconnectReason.Timeout
                )
                await self.disconnect(True)
示例#8
0
async def async_setup_platform(hass, config, add_entities, discovery_info=None):
  """Set up the sensor platform."""
  entities = []
  for k, v in config.items():
    if k == 'hosts':
      for h in v:
        host = {}
        for p, r in h.items():
          host[p] = r

        supported = []
        try:
          key = unhexlify(host['key'])
          cypher = encrypt('(discovery)\0', key)
          sock = await asyncio.wait_for(asyncio_dgram.connect((host['ip'], 54321)), 5)
          await asyncio.wait_for(sock.send(cypher), 5)
          cypher, [source_host, port] = await asyncio.wait_for(sock.recv(), 5)
          message = decrypt(cypher, key)
          logger.info("discover -> %s:%s -> %s", host['ip'], 54321, message)
          supported = sexpdata.loads(message)
        except:
          logger.exception("Failed to init device %s", host['ip'])

        if 'temperature-read' in supported:
          entities.append(HHGSensor("hhg_" + host['ip'] + '_temperature', host['ip'], host['key'], '(temperature-read)', TEMP_CELSIUS, DEVICE_CLASS_TEMPERATURE))

        if 'humidity-read' in supported:
          entities.append(HHGSensor("hhg_" + host['ip'] + '_humidity', host['ip'], host['key'], '(humidity-read)', UNIT_PERCENTAGE, DEVICE_CLASS_HUMIDITY))

        if 'light-read' in supported:
          entities.append(HHGSensor("hhg_" + host['ip'] + '_light', host['ip'], host['key'], '(light-read)', 'lx', DEVICE_CLASS_ILLUMINANCE))

        if 'co2-read' in supported:
          entities.append(HHGSensor("hhg_" + host['ip'] + '_co2', host['ip'], host['key'], '(co2-read)', CONCENTRATION_PARTS_PER_MILLION, 'air_quality'))

        if 'tvoc-read' in supported:
          entities.append(HHGSensor("hhg_" + host['ip'] + '_tvoc', host['ip'], host['key'], '(tvoc-read)', CONCENTRATION_PARTS_PER_MILLION, 'air_quality'))
        
  logger.info(entities)
  add_entities(entities)
示例#9
0
    async def sendCommand(self, message):
        # message = r'{"method":' + message + r',"params":{}}'
        maxTries = 100
        sleepInterval = 0.5
        dataStream = await asyncio.wait_for(
            asyncio_dgram.connect((self.bulbIp, self.bulbPort)), self.timeout)

        receive = asyncio.create_task(self.recData(dataStream))

        i = 0
        while not receive.done() and i < maxTries:
            asyncio.create_task(dataStream.send(bytes(message, "utf-8")))
            await asyncio.sleep(0.5)
            i += 1

        await receive
        resData = receive.result()

        dataStream.close

        if resData and len(resData):
            return resData.decode()
示例#10
0
 async def connect(self, addr, timeout=3):
     self.timeout = timeout
     conn = asyncio_dgram.connect((addr[0], addr[1]))
     self.stream = await asyncio.wait_for(conn, timeout=self.timeout)