Skip to content

Commit

Permalink
Tuya upgrades 35, sub_devices bump 6.0.0 etc... (rospogrigio#15)
Browse files Browse the repository at this point in the history
* rewrite add device manually message.

* Add 7000 Port listening and reuse port

* App broadcasting and improve data decrypt

* Add auto protcol in config flow

* and supported protocols in const

* Add node ID to const

* Add settings contexts

* Add support for SubDevices and 3.5[Hope] in pytuya core

* Fix sample template

* clarify CID context

* ADD Tuya const

* add explain error into config_flow

* Clarify Error_values when try to connect!

* Report errors values if happend in core!

* add node_id to common.py

* update config_flow with many changes in PR edit: 1

* remove debug message

* comment

* increase timeout to 8secs.

* revert increase timeout

* typo

* fix a bug when import template [need rewrite dev_config)

* rework on helpers

* update dps function version uses constant versions

* remove duplicated function

* cleansup codes

* Fix unique IDs already exists. solve_issue_1 in PR

* Rework config_flow actions Menu instead of radiobox

* Spaces on Cover Commands Labels

* Rename from `LocalTuya integration` to `Local Tuya`

* rewrite translation to menu init

* remove `CONF ACTION` and adjust `CONF CLOUD`

* add `data_description` en lang to template step

* Fix devices don't comeback after adding new device

* remove unnecessary contect func

* remove unnecessary contect func

* fix entity_category and some cleans

* clean up codes

* cleans up helpers

* for futrue things.

* pump version

* Give Docs when installing new integration.

* cleans up repo
  • Loading branch information
xZetsubou authored Aug 30, 2023
1 parent 813a227 commit cd476b4
Show file tree
Hide file tree
Showing 33 changed files with 850 additions and 727 deletions.
19 changes: 0 additions & 19 deletions .dependabot/config.yml

This file was deleted.

220 changes: 93 additions & 127 deletions README.md

Large diffs are not rendered by default.

50 changes: 16 additions & 34 deletions custom_components/localtuya/__init__.py
Original file line number Diff line number Diff line change
Expand Up @@ -95,7 +95,7 @@ async def _handle_set_dp(event):

await device.set_dp(event.data[CONF_VALUE], event.data[CONF_DP])

def _device_discovered(device):
def _device_discovered(device: TuyaDevice):
"""Update address of device if it has changed."""
device_ip = device["ip"]
device_id = device["gwId"]
Expand Down Expand Up @@ -139,15 +139,14 @@ def _device_discovered(device):
)
new_data[ATTR_UPDATED_AT] = str(int(time.time() * 1000))
hass.config_entries.async_update_entry(entry, data=new_data)
device = hass.data[DOMAIN][TUYA_DEVICES][device_id]
if not device.connected:
device.async_connect()
# No need to do connect task here, when entry updated, it will reconnect. [elif].
# device = hass.data[DOMAIN][TUYA_DEVICES][device_id]
# if not device.connected:
# hass.create_task(device.async_connect())
elif device_id in hass.data[DOMAIN][TUYA_DEVICES]:
# _LOGGER.debug("Device %s found with IP %s", device_id, device_ip)

device = hass.data[DOMAIN][TUYA_DEVICES][device_id]
if not device.connected:
device.async_connect()
hass.create_task(device.async_connect())

def _shutdown(event):
"""Clean up resources when shutting down."""
Expand All @@ -157,7 +156,7 @@ async def _async_reconnect(now):
"""Try connecting to devices not already connected to."""
for device_id, device in hass.data[DOMAIN][TUYA_DEVICES].items():
if not device.connected:
device.async_connect()
hass.create_task(device.async_connect())

async_track_time_interval(hass, _async_reconnect, RECONNECT_INTERVAL)

Expand Down Expand Up @@ -284,55 +283,38 @@ async def setup_entities(device_ids):
)
hass.data[DOMAIN][TUYA_DEVICES][dev_id] = TuyaDevice(hass, entry, dev_id)

await asyncio.gather(
*[
hass.config_entries.async_forward_entry_setup(entry, platform)
for platform in platforms
]
)

for dev_id in device_ids:
hass.data[DOMAIN][TUYA_DEVICES][dev_id].async_connect()

await async_remove_orphan_entities(hass, entry)
await hass.config_entries.async_forward_entry_setups(entry, platforms)

hass.async_create_task(setup_entities(entry.data[CONF_DEVICES].keys()))

await setup_entities(entry.data[CONF_DEVICES].keys())
unsub_listener = entry.add_update_listener(update_listener)

hass.data[DOMAIN][entry.entry_id] = {UNSUB_LISTENER: unsub_listener}

return True


async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry):
"""Unload a config entry."""
async def async_unload_entry(hass: HomeAssistant, entry: ConfigEntry) -> bool:
"""Unloading the Tuya platforms."""
platforms = {}

for dev_id, dev_entry in entry.data[CONF_DEVICES].items():
for entity in dev_entry[CONF_ENTITIES]:
platforms[entity[CONF_PLATFORM]] = True

unload_ok = all(
await asyncio.gather(
*[
hass.config_entries.async_forward_entry_unload(entry, component)
for component in platforms
]
)
)
unload_ok = await hass.config_entries.async_unload_platforms(entry, platforms)

hass.data[DOMAIN][entry.entry_id][UNSUB_LISTENER]()
for dev_id, device in hass.data[DOMAIN][TUYA_DEVICES].items():
if device.connected:
await device.close()

if unload_ok:
hass.data[DOMAIN][entry.entry_id][UNSUB_LISTENER]()
hass.data[DOMAIN][TUYA_DEVICES] = {}

return True
return unload_ok


async def update_listener(hass, config_entry):
async def update_listener(hass: HomeAssistant, config_entry: ConfigEntry):
"""Update listener."""
await hass.config_entries.async_reload(config_entry.entry_id)

Expand Down
23 changes: 14 additions & 9 deletions custom_components/localtuya/common.py
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,9 @@
import time
from datetime import timedelta

from homeassistant.core import HomeAssistant
from homeassistant.config_entries import ConfigEntry

from homeassistant.const import (
CONF_DEVICE_ID,
CONF_DEVICES,
Expand Down Expand Up @@ -31,6 +34,7 @@
ATTR_UPDATED_AT,
CONF_DEFAULT_VALUE,
CONF_ENABLE_DEBUG,
CONF_NODE_ID,
CONF_LOCAL_KEY,
CONF_MODEL,
CONF_PASSIVE_ENTITY,
Expand All @@ -41,6 +45,7 @@
DOMAIN,
TUYA_DEVICES,
DEFAULT_CATEGORIES,
ENTITY_CATEGORY,
)

_LOGGER = logging.getLogger(__name__)
Expand Down Expand Up @@ -83,7 +88,6 @@ async def async_setup_entry(
]

if entities_to_setup:

tuyainterface = hass.data[DOMAIN][TUYA_DEVICES][dev_id]

dps_config_fields = list(get_dps_for_platform(flow_schema))
Expand Down Expand Up @@ -134,7 +138,7 @@ def async_config_entry_by_device_id(hass, device_id):
class TuyaDevice(pytuya.TuyaListener, pytuya.ContextualLogger):
"""Cache wrapper for pytuya.TuyaInterface."""

def __init__(self, hass, config_entry, dev_id):
def __init__(self, hass: HomeAssistant, config_entry: ConfigEntry, dev_id: str):
"""Initialize the cache."""
super().__init__()
self._hass = hass
Expand Down Expand Up @@ -181,7 +185,7 @@ def async_connect(self):
"""Connect to device if not already connected."""
# self.info("async_connect: %d %r %r", self._is_closing, self._connect_task, self._interface)
if not self._is_closing and self._connect_task is None and not self._interface:
self._connect_task = asyncio.create_task(self._make_connection())
self._connect_task = self._hass.create_task(self._make_connection())

async def _make_connection(self):
"""Subscribe localtuya entity events."""
Expand All @@ -194,6 +198,7 @@ async def _make_connection(self):
self._local_key,
float(self._dev_config_entry[CONF_PROTOCOL_VERSION]),
self._dev_config_entry.get(CONF_ENABLE_DEBUG, False),
self._dev_config_entry.get(CONF_NODE_ID, None),
self,
)
self._interface.add_dps_to_request(self.dps_to_request)
Expand Down Expand Up @@ -496,12 +501,12 @@ def entity_category(self) -> str:
# Set Default values for unconfigured devices.
if self.has_config(CONF_PLATFORM):
platform = self._config[CONF_PLATFORM]
if any(platform in i for i in DEFAULT_CATEGORIES["CONTROL"]):
return None
elif any(platform in i for i in DEFAULT_CATEGORIES["CONFIG"]):
return EntityCategory.CONFIG
elif any(platform in i for i in DEFAULT_CATEGORIES["DIAGNOSTIC"]):
return EntityCategory.DIAGNOSTIC
# Call default_category from config_flow to set default values!
# This will be removed after a while, this is only made to convert who came from main integration.
# new users will be forced to choose category from config_flow.
from .config_flow import default_category

return default_category(platform)
return None

def dps(self, dp_index):
Expand Down
Loading

0 comments on commit cd476b4

Please sign in to comment.