ha-mcp-dev 7.10.0.dev774__tar.gz → 7.10.0.dev776__tar.gz
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- {ha_mcp_dev-7.10.0.dev774/src/ha_mcp_dev.egg-info → ha_mcp_dev-7.10.0.dev776}/PKG-INFO +1 -1
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/pyproject.toml +1 -1
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/websocket_client.py +72 -13
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_entities.py +80 -26
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776/src/ha_mcp_dev.egg-info}/PKG-INFO +1 -1
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/LICENSE +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/MANIFEST.in +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/README.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/setup.cfg +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/__main__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/_pypi_marker +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/_version.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/auth/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/auth/consent_form.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/auth/provider.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/backup_manager.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/rest_client.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/supervisor_client.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/websocket_listener.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/config.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/capture.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/provision.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/errors.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/approval_queue.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/evaluator.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/handlers.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/middleware.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/model.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/persistence.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/policy/value_sources.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/py.typed +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/read_only.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/.claude/settings.json +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/.claude-plugin/marketplace.json +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/.claude-plugin/plugin.json +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/.github/ISSUE_TEMPLATE/skill-rca.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/.github/pull_request_template.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/AGENTS.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/CLAUDE.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/CONTRIBUTING.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/LICENSE +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/README.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/SKILL.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/evals/evals.json +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/appdaemon.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/automation-patterns.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/dashboard-cards.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/dashboard-guide.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/device-control.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/domain-docs.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/examples.yaml +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/helper-selection.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/safe-refactoring.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/scenes.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/template-guidelines.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/yaml-only-integrations.md +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/server.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/settings_ui/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/settings_ui/settings.css +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/settings_ui/settings.html +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/settings_ui/settings.js +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/smoke_test.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/stdio_settings_sidecar.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/auto_backup.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/backup.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/best_practice_checker.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/config_entry_flow.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/device_control.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/enhanced.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/helpers.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/base.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/matter.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/thread.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/zigbee.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/radio/zwave.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/reference_validator.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/registry.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_base.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_config.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_deep.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_fetch.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_overview.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_scenes.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_scoring.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tool_search_hint_middleware.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_addons.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_areas.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_blueprints.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_bug_report.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_calendar.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_camera.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_categories.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_code.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_automations.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_dashboards.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_helpers.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_scenes.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_scripts.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_dashboard_screenshot.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_energy.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_entities.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_filesystem.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_groups.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_hacs.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_history.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_integrations.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_labels.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_mcp_component.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_radio.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_registry.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_resources.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_search.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_service.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_services.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_system.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_themes.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_todo.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_traces.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_updates.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_utility.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_voice_assistant.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_yaml_config.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_zones.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/util_helpers.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/validation_middleware.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transforms/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transforms/categorized_search.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transforms/lite_docstrings.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transport_security.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/update_check.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/config_hash.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/data_paths.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/domain_handlers.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/fuzzy_search.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/kill_signal_diagnostics.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/operation_manager.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/python_sandbox.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/skill_loader.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/usage_logger.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/visibility/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/visibility/model.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/visibility/persistence.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/visibility/resolver.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/SOURCES.txt +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/dependency_links.txt +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/entry_points.txt +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/requires.txt +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/top_level.txt +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/tests/__init__.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/tests/test_constants.py +0 -0
- {ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/tests/test_env_manager.py +0 -0
|
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
|
|
|
4
4
|
|
|
5
5
|
[project]
|
|
6
6
|
name = "ha-mcp-dev"
|
|
7
|
-
version = "7.10.0.
|
|
7
|
+
version = "7.10.0.dev776"
|
|
8
8
|
description = "Home Assistant MCP Server - Complete control of Home Assistant through MCP"
|
|
9
9
|
readme = "README.md"
|
|
10
10
|
# Upper bound widened to <3.15 so the package installs on Home Assistant's
|
|
@@ -30,6 +30,15 @@ from .rest_client import (
|
|
|
30
30
|
|
|
31
31
|
logger = logging.getLogger(__name__)
|
|
32
32
|
|
|
33
|
+
# Matches the Supervisor's own Core-connection receive limit
|
|
34
|
+
# (MAX_MESSAGE_SIZE_FROM_CORE in home-assistant/supervisor, see supervisor
|
|
35
|
+
# issue #4392). On the add-on path frames above that limit die at the
|
|
36
|
+
# Supervisor proxy anyway, so a larger client-side cap adds nothing there.
|
|
37
|
+
# Registry list responses scale with entity count and arrive as ONE frame
|
|
38
|
+
# (the HA WebSocket API has no pagination); a ~6.4k-entity instance
|
|
39
|
+
# overflowed the previous 20MB cap (#1721).
|
|
40
|
+
MAX_WS_MESSAGE_BYTES = 64 * 1024 * 1024
|
|
41
|
+
|
|
33
42
|
|
|
34
43
|
class WebSocketConnectionState:
|
|
35
44
|
"""Encapsulates mutable state used by the WebSocket client."""
|
|
@@ -109,20 +118,43 @@ class WebSocketConnectionState:
|
|
|
109
118
|
"""Retrieve and remove an authentication message if present."""
|
|
110
119
|
return self._auth_messages.pop(message_type, None)
|
|
111
120
|
|
|
112
|
-
def reset_connection(self) -> None:
|
|
113
|
-
"""Reset connection-specific state while preserving handlers.
|
|
121
|
+
def reset_connection(self, close_reason: str | None = None) -> None:
|
|
122
|
+
"""Reset connection-specific state while preserving handlers.
|
|
123
|
+
|
|
124
|
+
Args:
|
|
125
|
+
close_reason: Human-readable description of why the connection
|
|
126
|
+
went away (e.g. a close code/reason pair), included in the
|
|
127
|
+
error surfaced to any request still awaiting a response.
|
|
128
|
+
"""
|
|
114
129
|
self.connected = False
|
|
115
130
|
self.authenticated = False
|
|
116
131
|
self._message_id = 0
|
|
117
132
|
|
|
133
|
+
# ``future.cancel()`` makes awaiters see ``asyncio.CancelledError``,
|
|
134
|
+
# a BaseException that skips every ``except Exception`` handler in
|
|
135
|
+
# the tool layer and reaches the MCP SDK, which treats it as a
|
|
136
|
+
# client-initiated cancellation, suppresses the response entirely,
|
|
137
|
+
# and leaves the MCP client hanging until its own timeout (#1721).
|
|
138
|
+
# ``set_exception`` with a normal exception propagates through
|
|
139
|
+
# ``except Exception`` as expected instead.
|
|
140
|
+
message = (
|
|
141
|
+
"WebSocket connection to Home Assistant closed while waiting for a response"
|
|
142
|
+
)
|
|
143
|
+
if close_reason:
|
|
144
|
+
message = f"{message} ({close_reason})"
|
|
145
|
+
|
|
118
146
|
for future in self._pending_requests.values():
|
|
119
147
|
if not future.done():
|
|
120
|
-
future
|
|
148
|
+
# A fresh instance per future: sharing one exception object
|
|
149
|
+
# across multiple ``set_exception`` calls means the second
|
|
150
|
+
# raise attaches a traceback to an exception already
|
|
151
|
+
# associated with another future's stack.
|
|
152
|
+
future.set_exception(HomeAssistantConnectionError(message))
|
|
121
153
|
self._pending_requests.clear()
|
|
122
154
|
|
|
123
155
|
for future in self._event_responses.values():
|
|
124
156
|
if not future.done():
|
|
125
|
-
future.
|
|
157
|
+
future.set_exception(HomeAssistantConnectionError(message))
|
|
126
158
|
self._event_responses.clear()
|
|
127
159
|
|
|
128
160
|
# Drop any subscription queues — readers wake on the close signal
|
|
@@ -144,9 +176,9 @@ class WebSocketConnectionState:
|
|
|
144
176
|
"""Mark the socket as authenticated and ready for commands."""
|
|
145
177
|
self.authenticated = True
|
|
146
178
|
|
|
147
|
-
def mark_disconnected(self) -> None:
|
|
179
|
+
def mark_disconnected(self, close_reason: str | None = None) -> None:
|
|
148
180
|
"""Reset connection state when the socket is closed."""
|
|
149
|
-
self.reset_connection()
|
|
181
|
+
self.reset_connection(close_reason)
|
|
150
182
|
|
|
151
183
|
@property
|
|
152
184
|
def is_ready(self) -> bool:
|
|
@@ -293,9 +325,7 @@ class HomeAssistantWebSocketClient:
|
|
|
293
325
|
ping_timeout=10,
|
|
294
326
|
additional_headers={"Authorization": f"Bearer {self.token}"},
|
|
295
327
|
ssl=ssl_ctx,
|
|
296
|
-
|
|
297
|
-
# (e.g., HACS repository list can be 2MB+)
|
|
298
|
-
max_size=20 * 1024 * 1024,
|
|
328
|
+
max_size=MAX_WS_MESSAGE_BYTES,
|
|
299
329
|
)
|
|
300
330
|
self._state.mark_connected()
|
|
301
331
|
|
|
@@ -390,6 +420,11 @@ class HomeAssistantWebSocketClient:
|
|
|
390
420
|
"""Background task to handle incoming WebSocket messages."""
|
|
391
421
|
if not self.websocket:
|
|
392
422
|
raise Exception("WebSocket not connected")
|
|
423
|
+
# None means a clean exit (the async-for loop simply ended); the
|
|
424
|
+
# except blocks below fill this in so pending futures — and the
|
|
425
|
+
# log — carry *why* the connection went away instead of a bare
|
|
426
|
+
# "WebSocket connection closed" that gave no lead on #1721.
|
|
427
|
+
close_reason: str | None = None
|
|
393
428
|
try:
|
|
394
429
|
async for message in self.websocket:
|
|
395
430
|
try:
|
|
@@ -400,12 +435,30 @@ class HomeAssistantWebSocketClient:
|
|
|
400
435
|
logger.error(f"Invalid JSON received: {e}")
|
|
401
436
|
except Exception as e:
|
|
402
437
|
logger.error(f"Error processing message: {e}")
|
|
403
|
-
except websockets.exceptions.ConnectionClosed:
|
|
404
|
-
|
|
438
|
+
except websockets.exceptions.ConnectionClosed as e:
|
|
439
|
+
# Prefer the frame we received (the peer closed on us); fall
|
|
440
|
+
# back to the frame we sent (we failed the connection
|
|
441
|
+
# ourselves, e.g. an over-max_size frame produces a sent
|
|
442
|
+
# Close(1009, ...) with no frame received at all).
|
|
443
|
+
close = e.rcvd if e.rcvd is not None else e.sent
|
|
444
|
+
if close is not None:
|
|
445
|
+
verb = "received" if e.rcvd is not None else "sent"
|
|
446
|
+
close_reason = f"{verb} close code {close.code}"
|
|
447
|
+
if close.reason:
|
|
448
|
+
close_reason = f"{close_reason} ({close.reason})"
|
|
449
|
+
else:
|
|
450
|
+
close_reason = "connection dropped without a close frame"
|
|
451
|
+
|
|
452
|
+
log_message = f"WebSocket connection closed ({close_reason})"
|
|
453
|
+
if close is None or close.code not in (1000, 1001):
|
|
454
|
+
logger.warning(log_message)
|
|
455
|
+
else:
|
|
456
|
+
logger.info(log_message)
|
|
405
457
|
except Exception as e:
|
|
458
|
+
close_reason = str(e)
|
|
406
459
|
logger.error(f"WebSocket message handler error: {e}")
|
|
407
460
|
finally:
|
|
408
|
-
self._state.mark_disconnected()
|
|
461
|
+
self._state.mark_disconnected(close_reason)
|
|
409
462
|
|
|
410
463
|
async def _process_message(self, data: dict[str, Any]) -> None:
|
|
411
464
|
"""Process incoming WebSocket message."""
|
|
@@ -649,9 +702,15 @@ class HomeAssistantWebSocketClient:
|
|
|
649
702
|
result_response = await asyncio.wait_for(
|
|
650
703
|
result_future, timeout=wait_timeout
|
|
651
704
|
)
|
|
652
|
-
except
|
|
705
|
+
except BaseException:
|
|
653
706
|
self.cancel_pending_response(message_id)
|
|
654
707
|
self.cancel_event_response(message_id)
|
|
708
|
+
# A connection drop fails BOTH futures via reset_connection;
|
|
709
|
+
# only result_future gets awaited on this path, so retrieve
|
|
710
|
+
# event_future's exception too or asyncio logs an ERROR-level
|
|
711
|
+
# "Future exception was never retrieved" when it is GC'd.
|
|
712
|
+
if event_future.done() and not event_future.cancelled():
|
|
713
|
+
event_future.exception()
|
|
655
714
|
raise
|
|
656
715
|
|
|
657
716
|
if not result_response.get("success"):
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_entities.py
RENAMED
|
@@ -12,6 +12,11 @@ from ._base import _SearchBase
|
|
|
12
12
|
|
|
13
13
|
logger = logging.getLogger(__name__)
|
|
14
14
|
|
|
15
|
+
# Bounds the per-frame response size of config/entity_registry/get_entries
|
|
16
|
+
# (extended entries, ~1KB typical each) so alias enrichment can't produce an
|
|
17
|
+
# over-cap WebSocket frame on large instances (#1721).
|
|
18
|
+
_GET_ENTRIES_CHUNK_SIZE = 500
|
|
19
|
+
|
|
15
20
|
|
|
16
21
|
class EntitySearchMixin(_SearchBase):
|
|
17
22
|
"""``smart_entity_search`` and ``get_entities_by_area`` plus helpers."""
|
|
@@ -144,41 +149,89 @@ class EntitySearchMixin(_SearchBase):
|
|
|
144
149
|
|
|
145
150
|
async def _fetch_entity_aliases(
|
|
146
151
|
self, survivor_ids: list[str]
|
|
147
|
-
) -> dict[str, list[str]]:
|
|
152
|
+
) -> tuple[dict[str, list[str]], list[str]]:
|
|
148
153
|
"""Batch-fetch full registry entries for aliases.
|
|
149
154
|
|
|
150
155
|
``config/entity_registry/list`` deliberately omits ``aliases``;
|
|
151
|
-
``get_entries`` includes them.
|
|
152
|
-
|
|
156
|
+
``get_entries`` includes them. Survivors are split into
|
|
157
|
+
``_GET_ENTRIES_CHUNK_SIZE``-sized chunks fetched concurrently: a
|
|
158
|
+
bounded number of round-trips (one per chunk), not N+1 fan-out, and
|
|
159
|
+
each response frame stays bounded regardless of instance size.
|
|
160
|
+
Enrichment is best-effort per chunk — one chunk failing does not
|
|
161
|
+
drop aliases fetched by the others; failures are reported in the
|
|
162
|
+
returned warnings so the caller can tell "no aliases exist" apart
|
|
163
|
+
from "the alias fetch failed".
|
|
164
|
+
|
|
165
|
+
Returns:
|
|
166
|
+
``(aliases_map, warnings)`` — warnings has one entry when any
|
|
167
|
+
chunk failed, empty otherwise.
|
|
153
168
|
"""
|
|
154
169
|
aliases_map: dict[str, list[str]] = {}
|
|
155
170
|
if not survivor_ids:
|
|
156
|
-
return aliases_map
|
|
157
|
-
|
|
158
|
-
|
|
159
|
-
|
|
160
|
-
|
|
161
|
-
|
|
162
|
-
|
|
163
|
-
|
|
164
|
-
|
|
165
|
-
|
|
166
|
-
|
|
167
|
-
|
|
168
|
-
|
|
171
|
+
return aliases_map, []
|
|
172
|
+
|
|
173
|
+
chunks: list[list[str]] = [
|
|
174
|
+
survivor_ids[i : i + _GET_ENTRIES_CHUNK_SIZE]
|
|
175
|
+
for i in range(0, len(survivor_ids), _GET_ENTRIES_CHUNK_SIZE)
|
|
176
|
+
]
|
|
177
|
+
responses: list[Any] = await asyncio.gather(
|
|
178
|
+
*(
|
|
179
|
+
self.client.send_websocket_message(
|
|
180
|
+
{
|
|
181
|
+
"type": "config/entity_registry/get_entries",
|
|
182
|
+
"entity_ids": chunk,
|
|
183
|
+
}
|
|
184
|
+
)
|
|
185
|
+
for chunk in chunks
|
|
186
|
+
),
|
|
187
|
+
return_exceptions=True,
|
|
188
|
+
)
|
|
189
|
+
|
|
190
|
+
failed_chunks = 0
|
|
191
|
+
for chunk, entries_resp in zip(chunks, responses, strict=True):
|
|
192
|
+
# Same convention as _fetch_search_entities: a captured
|
|
193
|
+
# CancelledError means the surrounding task is being torn
|
|
194
|
+
# down — propagate it instead of degrading to a warning.
|
|
195
|
+
if isinstance(entries_resp, asyncio.CancelledError):
|
|
196
|
+
raise entries_resp
|
|
197
|
+
if isinstance(entries_resp, BaseException):
|
|
198
|
+
failed_chunks += 1
|
|
169
199
|
logger.warning(
|
|
170
|
-
"alias_enrichment_failed: get_entries
|
|
171
|
-
"
|
|
172
|
-
len(
|
|
200
|
+
"alias_enrichment_failed: get_entries chunk of %d entities "
|
|
201
|
+
"raised (err=%r)",
|
|
202
|
+
len(chunk),
|
|
173
203
|
entries_resp,
|
|
174
204
|
)
|
|
175
|
-
|
|
176
|
-
|
|
177
|
-
|
|
178
|
-
|
|
179
|
-
|
|
205
|
+
continue
|
|
206
|
+
try:
|
|
207
|
+
if isinstance(entries_resp, dict) and entries_resp.get("success"):
|
|
208
|
+
for eid, entry in (entries_resp.get("result", {}) or {}).items():
|
|
209
|
+
if isinstance(entry, dict):
|
|
210
|
+
aliases_map[eid] = entry.get("aliases", []) or []
|
|
211
|
+
else:
|
|
212
|
+
failed_chunks += 1
|
|
213
|
+
logger.warning(
|
|
214
|
+
"alias_enrichment_failed: get_entries returned non-success "
|
|
215
|
+
"for a chunk of %d entities (resp=%r)",
|
|
216
|
+
len(chunk),
|
|
217
|
+
entries_resp,
|
|
218
|
+
)
|
|
219
|
+
except (KeyError, TypeError, AttributeError) as alias_err:
|
|
220
|
+
failed_chunks += 1
|
|
221
|
+
logger.warning(
|
|
222
|
+
"alias_enrichment_failed: malformed payload for a chunk of "
|
|
223
|
+
"%d entities (err=%r)",
|
|
224
|
+
len(chunk),
|
|
225
|
+
alias_err,
|
|
226
|
+
)
|
|
227
|
+
warnings: list[str] = []
|
|
228
|
+
if failed_chunks:
|
|
229
|
+
warnings.append(
|
|
230
|
+
f"Alias enrichment incomplete: {failed_chunks} of {len(chunks)} "
|
|
231
|
+
"entity-registry lookups failed; alias-based matches may be "
|
|
232
|
+
"missing from these results."
|
|
180
233
|
)
|
|
181
|
-
return aliases_map
|
|
234
|
+
return aliases_map, warnings
|
|
182
235
|
|
|
183
236
|
async def _fetch_search_entities(
|
|
184
237
|
self, domain_filter: str | None, include_hidden: bool
|
|
@@ -223,7 +276,8 @@ class EntitySearchMixin(_SearchBase):
|
|
|
223
276
|
survivor_ids, survivor_states = self._filter_hidden_entities(
|
|
224
277
|
entities, registry_slim, include_hidden, visibility_hidden
|
|
225
278
|
)
|
|
226
|
-
aliases_map = await self._fetch_entity_aliases(survivor_ids)
|
|
279
|
+
aliases_map, alias_warnings = await self._fetch_entity_aliases(survivor_ids)
|
|
280
|
+
visibility_warnings = [*visibility_warnings, *alias_warnings]
|
|
227
281
|
|
|
228
282
|
# Enrich with aliases + hidden_by for the fuzzy layer. Shallow copy +
|
|
229
283
|
# private-prefixed keys so downstream consumers that round-trip these
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/supervisor_client.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/client/websocket_listener.py
RENAMED
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/__init__.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/capture.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/dashboard_screenshot/provision.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/AGENTS.md
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/CLAUDE.md
RENAMED
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/LICENSE
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/resources/skills-vendor/README.md
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/best_practice_checker.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/reference_validator.py
RENAMED
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/__init__.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_base.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_config.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_deep.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_fetch.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_overview.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_scenes.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/smart_search/_scoring.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_automations.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_dashboards.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_helpers.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_scenes.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_config_scripts.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_dashboard_screenshot.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_integrations.py
RENAMED
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_mcp_component.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/tools_voice_assistant.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/tools/validation_middleware.py
RENAMED
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transforms/categorized_search.py
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/transforms/lite_docstrings.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp/utils/kill_signal_diagnostics.py
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/dependency_links.txt
RENAMED
|
File without changes
|
{ha_mcp_dev-7.10.0.dev774 → ha_mcp_dev-7.10.0.dev776}/src/ha_mcp_dev.egg-info/entry_points.txt
RENAMED
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|
|
File without changes
|