Exemplo n.º 1
0
 def print_aldb(service):
     """Print the All-Link Database for a device."""
     # For now this sends logs to the log file.
     # Future direction is to create an INSTEON control panel.
     entity_id = service.data[CONF_ENTITY_ID]
     signal = f"{entity_id}_{SIGNAL_PRINT_ALDB}"
     dispatcher_send(opp, signal)
Exemplo n.º 2
0
    def _frame_received(frame):
        """Run when a Zigbee frame is received.

        Pickles the frame, then encodes it into base64 since it contains
        non JSON serializable binary.
        """
        dispatcher_send(opp, SIGNAL_ZIGBEE_FRAME_RECEIVED, frame)
Exemplo n.º 3
0
    def scan_devices(self, now: datetime | None = None) -> None:
        """Scan for new devices and return a list of found device ids."""
        _LOGGER.debug("Checking devices for FRITZ!Box router %s", self.host)

        consider_home = self._options.get(
            CONF_CONSIDER_HOME, DEFAULT_CONSIDER_HOME.total_seconds()
        )

        new_device = False
        for known_host in self._update_info():
            if not known_host.get("mac"):
                continue

            dev_mac = known_host["mac"]
            dev_name = known_host["name"]
            dev_ip = known_host["ip"]
            dev_home = known_host["status"]

            dev_info = Device(dev_mac, dev_ip, dev_name)

            if dev_mac in self._devices:
                self._devices[dev_mac].update(dev_info, dev_home, consider_home)
            else:
                device = FritzDevice(dev_mac)
                device.update(dev_info, dev_home, consider_home)
                self._devices[dev_mac] = device
                new_device = True

        dispatcher_send(self.opp, self.signal_device_update)
        if new_device:
            dispatcher_send(self.opp, self.signal_device_new)
Exemplo n.º 4
0
    def update(self, status) -> None:
        """Update the iCloud device."""
        self._status = status

        self._status[
            ATTR_ACCOUNT_FETCH_INTERVAL] = self._account.fetch_interval

        device_status = DEVICE_STATUS_CODES.get(self._status[DEVICE_STATUS],
                                                "error")
        self._attrs[ATTR_DEVICE_STATUS] = device_status

        self._battery_status = self._status[DEVICE_BATTERY_STATUS]
        self._attrs[ATTR_BATTERY_STATUS] = self._battery_status
        device_battery_level = self._status.get(DEVICE_BATTERY_LEVEL, 0)
        if self._battery_status != "Unknown" and device_battery_level is not None:
            self._battery_level = int(device_battery_level * 100)
            self._attrs[ATTR_BATTERY] = self._battery_level
            self._attrs[ATTR_LOW_POWER_MODE] = self._status[
                DEVICE_LOW_POWER_MODE]

            if (self._status[DEVICE_LOCATION] and
                    self._status[DEVICE_LOCATION][DEVICE_LOCATION_LATITUDE]):
                location = self._status[DEVICE_LOCATION]
                if self._location is None:
                    dispatcher_send(self._account.opp,
                                    self._account.signal_device_new)
                self._location = location
Exemplo n.º 5
0
 def _start_recovery(self):
     self._wrap_event_flag.clear()
     dispatcher_send(self._opp,
                     service_signal(SERVICE_UPDATE, self._wrap_name))
     self._unsub_recheck = track_time_interval(self._opp,
                                               self._wrap_test_online,
                                               RECHECK_INTERVAL)
Exemplo n.º 6
0
 def poll_device_update(event_time):
     """Update Smarty device."""
     _LOGGER.debug("Updating Smarty device")
     if smarty.update():
         _LOGGER.debug("Update success")
         dispatcher_send(opp, SIGNAL_UPDATE_SMARTY)
     else:
         _LOGGER.debug("Update failed")
Exemplo n.º 7
0
    def test_platform(self, mock_setup_component):
        """Test discover platform method."""
        calls = []

        @callback
        def platform_callback(platform, info):
            """Platform callback method."""
            calls.append((platform, info))

        run_callback_threadsafe(
            self.opp.loop,
            discovery.async_listen_platform,
            self.opp,
            "test_component",
            platform_callback,
        ).result()

        discovery.load_platform(
            self.opp,
            "test_component",
            "test_platform",
            "discovery info",
            {"test_component": {}},
        )
        self.opp.block_till_done()
        assert mock_setup_component.called
        assert mock_setup_component.call_args[0] == (
            self.opp,
            "test_component",
            {
                "test_component": {}
            },
        )
        self.opp.block_till_done()

        discovery.load_platform(
            self.opp,
            "test_component_2",
            "test_platform",
            "discovery info",
            {"test_component": {}},
        )
        self.opp.block_till_done()

        assert len(calls) == 1
        assert calls[0] == ("test_platform", "discovery info")

        dispatcher_send(
            self.opp,
            discovery.SIGNAL_PLATFORM_DISCOVERED,
            {
                "service":
                discovery.EVENT_LOAD_PLATFORM.format("test_component")
            },
        )
        self.opp.block_till_done()

        assert len(calls) == 1
Exemplo n.º 8
0
    def _signal_zone_update(self):
        """Signal a zone update.

        Whenever the underlying library does an action against
        a zone, the data for the zone is updated.

        Update a single zone.
        """
        dispatcher_send(self.opp, f"{SIGNAL_ZONE_UPDATE}-{self._zone.zone_id}")
Exemplo n.º 9
0
 def _mqtt_on_disconnect(self, _mqttc, _userdata, result_code: int) -> None:
     """Disconnected callback."""
     self.connected = False
     dispatcher_send(self.opp, MQTT_DISCONNECTED)
     _LOGGER.warning(
         "Disconnected from MQTT server %s:%s (%s)",
         self.conf[CONF_BROKER],
         self.conf[CONF_PORT],
         result_code,
     )
Exemplo n.º 10
0
 def update(self):
     """Update the registered zones."""
     for device in self.devices:
         self.update_sensor("device", device["shortSerialNo"])
     for zone in self.zones:
         self.update_sensor("zone", zone["id"])
     self.data["weather"] = self.tado.getWeather()
     dispatcher_send(
         self.opp,
         SIGNAL_TADO_UPDATE_RECEIVED.format(self.home_id, "weather", "data"),
     )
Exemplo n.º 11
0
    def handle_receive(event):
        """Handle received messages from w800rf32 gateway."""
        # Log event
        if not event.device:
            return
        _LOGGER.debug("Receive W800rf32 event in handle_receive")

        # Get device_type from device_id in opp.data
        device_id = event.device.lower()
        signal = W800RF32_DEVICE.format(device_id)
        dispatcher_send(opp, signal, event)
Exemplo n.º 12
0
    def _signal_thermostat_update(self):
        """Signal a thermostat update.

        Whenever the underlying library does an action against
        a thermostat, the data for the thermostat and all
        connected zone is updated.

        Update all the zones on the thermostat.
        """
        dispatcher_send(
            self.opp,
            f"{SIGNAL_THERMOSTAT_UPDATE}-{self._thermostat.thermostat_id}")
Exemplo n.º 13
0
    def callback_notify(notify):
        """Process NOTIFY message from STB."""
        if notify.ip_address in opp.data[DATA_MEDIAROOM]:
            dispatcher_send(opp, SIGNAL_STB_NOTIFY, notify)
            return

        _LOGGER.debug("Discovered new stb %s", notify.ip_address)
        opp.data[DATA_MEDIAROOM].append(notify.ip_address)
        new_stb = MediaroomDevice(host=notify.ip_address,
                                  device_id=notify.device_uuid,
                                  optimistic=False)
        async_add_entities([new_stb])
Exemplo n.º 14
0
    def capture_image(call):
        """Capture a new image."""
        entity_ids = call.data.get(ATTR_ENTITY_ID)

        target_entities = [
            entity_id for entity_id in opp.data[DOMAIN].entity_ids
            if entity_id in entity_ids
        ]

        for entity_id in target_entities:
            signal = f"abode_camera_capture_{entity_id}"
            dispatcher_send(opp, signal)
Exemplo n.º 15
0
    def trigger_automation(call):
        """Trigger an Abode automation."""
        entity_ids = call.data.get(ATTR_ENTITY_ID)

        target_entities = [
            entity_id for entity_id in opp.data[DOMAIN].entity_ids
            if entity_id in entity_ids
        ]

        for entity_id in target_entities:
            signal = f"abode_trigger_automation_{entity_id}"
            dispatcher_send(opp, signal)
Exemplo n.º 16
0
    def _mqtt_on_connect(self, _mqttc, _userdata, _flags,
                         result_code: int) -> None:
        """On connect callback.

        Resubscribe to all topics we were subscribed to and publish birth
        message.
        """
        # pylint: disable=import-outside-toplevel
        import paho.mqtt.client as mqtt

        if result_code != mqtt.CONNACK_ACCEPTED:
            _LOGGER.error(
                "Unable to connect to the MQTT broker: %s",
                mqtt.connack_string(result_code),
            )
            return

        self.connected = True
        dispatcher_send(self.opp, MQTT_CONNECTED)
        _LOGGER.info(
            "Connected to MQTT server %s:%s (%s)",
            self.conf[CONF_BROKER],
            self.conf[CONF_PORT],
            result_code,
        )

        # Group subscriptions to only re-subscribe once for each topic.
        keyfunc = attrgetter("topic")
        for topic, subs in groupby(sorted(self.subscriptions, key=keyfunc),
                                   keyfunc):
            # Re-subscribe with the highest requested qos
            max_qos = max(subscription.qos for subscription in subs)
            self.opp.add_job(self._async_perform_subscription, topic, max_qos)

        if (CONF_BIRTH_MESSAGE in self.conf
                and ATTR_TOPIC in self.conf[CONF_BIRTH_MESSAGE]):

            async def publish_birth_message(birth_message):
                await self._op_started.wait(
                )  # Wait for Open Peer Power to start
                await self._discovery_cooldown(
                )  # Wait for MQTT discovery to cool down
                await self.async_publish(
                    topic=birth_message.topic,
                    payload=birth_message.payload,
                    qos=birth_message.qos,
                    retain=birth_message.retain,
                )

            birth_message = Message(**self.conf[CONF_BIRTH_MESSAGE])
            asyncio.run_coroutine_threadsafe(
                publish_birth_message(birth_message), self.opp.loop)
Exemplo n.º 17
0
 def handle_update_tags_event(self, event):
     """Handle push event from wireless tag manager."""
     _LOGGER.info("Push notification for update arrived: %s", event)
     try:
         tag_id = event.data.get("id")
         mac = event.data.get("mac")
         dispatcher_send(self.opp, SIGNAL_TAG_UPDATE.format(tag_id, mac), event)
     except Exception as ex:  # pylint: disable=broad-except
         _LOGGER.error(
             "Unable to handle tag update event:\
                       %s error: %s",
             str(event),
             str(ex),
         )
Exemplo n.º 18
0
    async def async_create_new_entities(address):
        _LOGGER.debug(
            "Adding new INSTEON device to Open Peer Power with address %s",
            address)
        await devices.async_save(workdir=opp.config.config_dir)
        device = devices[address]
        await device.async_status()
        platforms = get_device_platforms(device)
        for platform in platforms:
            if platform == ON_OFF_EVENTS:
                add_on_off_event_device(opp, device)

            else:
                signal = f"{SIGNAL_ADD_ENTITIES}_{platform}"
                dispatcher_send(opp, signal, {"address": device.address})
Exemplo n.º 19
0
    def update(self, now=None):
        """Get the latest data from iperf3."""
        if self.protocol == "udp":
            # UDP only have 1 way attribute
            result = self._run_test(ATTR_DOWNLOAD)
            self.data[ATTR_DOWNLOAD] = self.data[ATTR_UPLOAD] = getattr(
                result, "Mbps", None)
            self.data[ATTR_VERSION] = getattr(result, "version", None)
        else:
            result = self._run_test(ATTR_DOWNLOAD)
            self.data[ATTR_DOWNLOAD] = getattr(result, "received_Mbps", None)
            self.data[ATTR_VERSION] = getattr(result, "version", None)
            self.data[ATTR_UPLOAD] = getattr(self._run_test(ATTR_UPLOAD),
                                             "sent_Mbps", None)

        dispatcher_send(self._opp, DATA_UPDATED, self.host)
Exemplo n.º 20
0
    def update(self):
        """Get the latest data from Transmission instance."""
        try:
            self.data = self._api.session_stats()
            self._torrents = self._api.get_torrents()
            self._session = self._api.get_session()

            self.check_completed_torrent()
            self.check_started_torrent()
            self.check_removed_torrent()
            _LOGGER.debug("Torrent Data for %s Updated", self.host)

            self.available = True
        except TransmissionError:
            self.available = False
            _LOGGER.error("Unable to connect to Transmission client %s",
                          self.host)
        dispatcher_send(self.opp, self.signal_update)
Exemplo n.º 21
0
 def handle_binary_event(self, event):
     """Handle push notifications for binary (on/off) events."""
     _LOGGER.info("Push notification for binary event arrived: %s", event)
     try:
         tag_id = event.data.get("id")
         event_type = event.data.get("type")
         mac = event.data.get("mac")
         dispatcher_send(
             self.opp,
             SIGNAL_BINARY_EVENT_UPDATE.format(tag_id, event_type, mac),
             event,
         )
     except Exception as ex:  # pylint: disable=broad-except
         _LOGGER.error(
             "Unable to handle tag binary event:\
                       %s error: %s",
             str(event),
             str(ex),
         )
Exemplo n.º 22
0
def discover_chromecast(opp: OpenPeerPower, device_info):
    """Discover a Chromecast."""

    info = ChromecastInfo(
        services=device_info.services,
        uuid=device_info.uuid,
        model_name=device_info.model_name,
        friendly_name=device_info.friendly_name,
        is_audio_group=device_info.port != DEFAULT_PORT,
    )

    if info.uuid is None:
        _LOGGER.error("Discovered chromecast without uuid %s", info)
        return

    info = info.fill_out_missing_chromecast_info()
    _LOGGER.debug("Discovered new or updated chromecast %s", info)

    dispatcher_send(opp, SIGNAL_CAST_DISCOVERED, info)
Exemplo n.º 23
0
 def command(self, *args, **kwargs):
     """amcrest.Http.command wrapper to catch errors."""
     try:
         ret = super().command(*args, **kwargs)
     except LoginError as ex:
         with self._wrap_lock:
             was_online = self.available
             was_login_err = self._wrap_login_err
             self._wrap_login_err = True
         if not was_login_err:
             _LOGGER.error("%s camera offline: Login error: %s",
                           self._wrap_name, ex)
         if was_online:
             self._start_recovery()
         raise
     except AmcrestError:
         with self._wrap_lock:
             was_online = self.available
             errs = self._wrap_errors = self._wrap_errors + 1
             offline = not self.available
         _LOGGER.debug("%s camera errs: %i", self._wrap_name, errs)
         if was_online and offline:
             _LOGGER.error("%s camera offline: Too many errors",
                           self._wrap_name)
             self._start_recovery()
         raise
     with self._wrap_lock:
         was_offline = not self.available
         self._wrap_errors = 0
         self._wrap_login_err = False
     if was_offline:
         self._unsub_recheck()
         self._unsub_recheck = None
         _LOGGER.error("%s camera back online", self._wrap_name)
         self._wrap_event_flag.set()
         dispatcher_send(self._opp,
                         service_signal(SERVICE_UPDATE, self._wrap_name))
     return ret
Exemplo n.º 24
0
def _monitor_events(opp, name, api, event_codes):
    event_codes = set(event_codes)
    while True:
        api.available_flag.wait()
        try:
            for code, payload in api.event_actions("All", retries=5):
                event_data = {
                    "camera": name,
                    "event": code,
                    "payload": payload
                }
                opp.bus.fire("amcrest", event_data)
                if code in event_codes:
                    signal = service_signal(SERVICE_EVENT, name, code)
                    start = any(
                        str(key).lower() == "action"
                        and str(val).lower() == "start"
                        for key, val in payload.items())
                    _LOGGER.debug("Sending signal: '%s': %s", signal, start)
                    dispatcher_send(opp, signal, start)
        except AmcrestError as error:
            _LOGGER.warning("Error while processing events from %s camera: %r",
                            name, error)
Exemplo n.º 25
0
    def update(self, now: datetime.datetime | None = None) -> None:
        """Request new Sonos favorites from a speaker."""
        new_favorites = None
        discovered = self.opp.data[DATA_SONOS].discovered

        for uid, speaker in discovered.items():
            try:
                new_favorites = speaker.soco.music_library.get_sonos_favorites(
                )
            except SoCoException as err:
                _LOGGER.warning("Error requesting favorites from %s: %s",
                                speaker.soco, err)
            else:
                # Prefer this SoCo instance next update
                discovered.move_to_end(uid, last=False)
                break

        if new_favorites is None:
            _LOGGER.error("Could not reach any speakers to update favorites")
            return

        self._favorites = []
        for fav in new_favorites:
            try:
                # exclude non-playable favorites with no linked resources
                if fav.reference.resources:
                    self._favorites.append(fav)
            except SoCoException as ex:
                # Skip unknown types
                _LOGGER.error("Unhandled favorite '%s': %s", fav.title, ex)
        _LOGGER.debug(
            "Cached %s favorites for household %s",
            len(self._favorites),
            self.household_id,
        )
        dispatcher_send(self.opp,
                        f"{SONOS_HOUSEHOLD_UPDATED}-{self.household_id}")
Exemplo n.º 26
0
    def update_sensor(self, sensor_type, sensor):
        """Update the internal data from Tado."""
        _LOGGER.debug("Updating %s %s", sensor_type, sensor)
        try:
            if sensor_type == "device":
                data = self.tado.getDeviceInfo(sensor)
                if (
                    INSIDE_TEMPERATURE_MEASUREMENT
                    in data["characteristics"]["capabilities"]
                ):
                    data[TEMP_OFFSET] = self.tado.getDeviceInfo(sensor, TEMP_OFFSET)
            elif sensor_type == "zone":
                data = self.tado.getZoneState(sensor)
            else:
                _LOGGER.debug("Unknown sensor: %s", sensor_type)
                return
        except RuntimeError:
            _LOGGER.error(
                "Unable to connect to Tado while updating %s %s",
                sensor_type,
                sensor,
            )
            return

        self.data[sensor_type][sensor] = data

        _LOGGER.debug(
            "Dispatching update to %s %s %s: %s",
            self.home_id,
            sensor_type,
            sensor,
            data,
        )
        dispatcher_send(
            self.opp,
            SIGNAL_TADO_UPDATE_RECEIVED.format(self.home_id, sensor_type, sensor),
        )
Exemplo n.º 27
0
 def signal_update() -> None:
     """Signal updates to data."""
     dispatcher_send(opp, UPDATE_SIGNAL, url)
Exemplo n.º 28
0
 def update(self):
     """Update device properties and send data updated signal."""
     self._update_properties()
     dispatcher_send(self._opp, DATA_UPDATED.format(self._host))
Exemplo n.º 29
0
 def _initialize_device(self):
     self._get_capabilities()
     self._initialized = True
     dispatcher_send(self._opp, DEVICE_INITIALIZED.format(self._host))
Exemplo n.º 30
0
 def _remove_entity(self, external_id):
     """Remove entity."""
     dispatcher_send(self._opp, f"ign_sismologia_delete_{external_id}")