Add manifest support for homekit discovery (#24225)
* Add manifest support for homekit discovery * Add a space after model check * Update comment
This commit is contained in:
parent
18286dbf4b
commit
3c1cdecb88
7 changed files with 169 additions and 32 deletions
|
@ -1,5 +1,5 @@
|
|||
"""Generate zeroconf file."""
|
||||
from collections import OrderedDict
|
||||
from collections import OrderedDict, defaultdict
|
||||
import json
|
||||
from typing import Dict
|
||||
|
||||
|
@ -13,12 +13,15 @@ To update, run python3 -m script.hassfest
|
|||
|
||||
|
||||
ZEROCONF = {}
|
||||
|
||||
HOMEKIT = {}
|
||||
""".strip()
|
||||
|
||||
|
||||
def generate_and_validate(integrations: Dict[str, Integration]):
|
||||
"""Validate and generate zeroconf data."""
|
||||
service_type_dict = {}
|
||||
service_type_dict = defaultdict(list)
|
||||
homekit_dict = {}
|
||||
|
||||
for domain in sorted(integrations):
|
||||
integration = integrations[domain]
|
||||
|
@ -26,17 +29,30 @@ def generate_and_validate(integrations: Dict[str, Integration]):
|
|||
if not integration.manifest:
|
||||
continue
|
||||
|
||||
service_types = integration.manifest.get('zeroconf')
|
||||
service_types = integration.manifest.get('zeroconf', [])
|
||||
homekit = integration.manifest.get('homekit', {})
|
||||
homekit_models = homekit.get('models', [])
|
||||
|
||||
if not service_types:
|
||||
if not service_types and not homekit_models:
|
||||
continue
|
||||
|
||||
try:
|
||||
with open(str(integration.path / "config_flow.py")) as fp:
|
||||
if ' async_step_zeroconf(' not in fp.read():
|
||||
content = fp.read()
|
||||
uses_discovery_flow = 'register_discovery_flow' in content
|
||||
|
||||
if (service_types and not uses_discovery_flow and
|
||||
' async_step_zeroconf(' not in content):
|
||||
integration.add_error(
|
||||
'zeroconf', 'Config flow has no async_step_zeroconf')
|
||||
continue
|
||||
|
||||
if (homekit_models and not uses_discovery_flow and
|
||||
' async_step_homekit(' not in content):
|
||||
integration.add_error(
|
||||
'zeroconf', 'Config flow has no async_step_homekit')
|
||||
continue
|
||||
|
||||
except FileNotFoundError:
|
||||
integration.add_error(
|
||||
'zeroconf',
|
||||
|
@ -45,16 +61,50 @@ def generate_and_validate(integrations: Dict[str, Integration]):
|
|||
continue
|
||||
|
||||
for service_type in service_types:
|
||||
|
||||
if service_type not in service_type_dict:
|
||||
service_type_dict[service_type] = []
|
||||
|
||||
service_type_dict[service_type].append(domain)
|
||||
|
||||
data = OrderedDict((key, service_type_dict[key])
|
||||
for key in sorted(service_type_dict))
|
||||
for model in homekit_models:
|
||||
# We add a space, as we want to test for it to be model + space.
|
||||
model += " "
|
||||
|
||||
return BASE.format(json.dumps(data, indent=4))
|
||||
if model in homekit_dict:
|
||||
integration.add_error(
|
||||
'zeroconf',
|
||||
'Integrations {} and {} have overlapping HomeKit '
|
||||
'models'.format(domain, homekit_dict[model]))
|
||||
break
|
||||
|
||||
homekit_dict[model] = domain
|
||||
|
||||
# HomeKit models are matched on starting string, make sure none overlap.
|
||||
warned = set()
|
||||
for key in homekit_dict:
|
||||
if key in warned:
|
||||
continue
|
||||
|
||||
# n^2 yoooo
|
||||
for key_2 in homekit_dict:
|
||||
if key == key_2 or key_2 in warned:
|
||||
continue
|
||||
|
||||
if key.startswith(key_2) or key_2.startswith(key):
|
||||
integration.add_error(
|
||||
'zeroconf',
|
||||
'Integrations {} and {} have overlapping HomeKit '
|
||||
'models'.format(homekit_dict[key], homekit_dict[key_2]))
|
||||
warned.add(key)
|
||||
warned.add(key_2)
|
||||
break
|
||||
|
||||
zeroconf = OrderedDict((key, service_type_dict[key])
|
||||
for key in sorted(service_type_dict))
|
||||
homekit = OrderedDict((key, homekit_dict[key])
|
||||
for key in sorted(homekit_dict))
|
||||
|
||||
return BASE.format(
|
||||
json.dumps(zeroconf, indent=4),
|
||||
json.dumps(homekit, indent=4),
|
||||
)
|
||||
|
||||
|
||||
def validate(integrations: Dict[str, Integration], config: Config):
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue