ha-mcp-dev 8.3.0.dev2372__tar.gz → 8.3.0.dev2377__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.
Files changed (276) hide show
  1. {ha_mcp_dev-8.3.0.dev2372/src/ha_mcp_dev.egg-info → ha_mcp_dev-8.3.0.dev2377}/PKG-INFO +1 -1
  2. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/pyproject.toml +1 -1
  3. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/__init__.py +24 -19
  4. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_search.py +11 -8
  5. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/visibility/enforcement.py +22 -1
  6. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377/src/ha_mcp_dev.egg-info}/PKG-INFO +1 -1
  7. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/LICENSE +0 -0
  8. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/MANIFEST.in +0 -0
  9. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/README.md +0 -0
  10. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/setup.cfg +0 -0
  11. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/__init__.py +0 -0
  12. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/__main__.py +0 -0
  13. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_pypi_marker +0 -0
  14. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_rich_compat.py +0 -0
  15. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/__init__.py +0 -0
  16. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/requirements.txt +0 -0
  17. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/LICENSE +0 -0
  18. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/MANIFEST.sha256 +0 -0
  19. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/VENDORED +0 -0
  20. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/__init__.py +0 -0
  21. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/__main__.py +0 -0
  22. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/__init__.py +0 -0
  23. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/client.py +0 -0
  24. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/connection.py +0 -0
  25. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/messages.py +0 -0
  26. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/router.py +0 -0
  27. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/asyncio/server.py +0 -0
  28. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/auth.py +0 -0
  29. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/cli.py +0 -0
  30. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/client.py +0 -0
  31. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/connection.py +0 -0
  32. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/datastructures.py +0 -0
  33. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/exceptions.py +0 -0
  34. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/extensions/__init__.py +0 -0
  35. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/extensions/base.py +0 -0
  36. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/extensions/permessage_deflate.py +0 -0
  37. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/frames.py +0 -0
  38. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/headers.py +0 -0
  39. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/http11.py +0 -0
  40. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/imports.py +0 -0
  41. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/__init__.py +0 -0
  42. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/auth.py +0 -0
  43. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/client.py +0 -0
  44. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/exceptions.py +0 -0
  45. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/framing.py +0 -0
  46. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/handshake.py +0 -0
  47. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/http.py +0 -0
  48. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/protocol.py +0 -0
  49. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/legacy/server.py +0 -0
  50. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/protocol.py +0 -0
  51. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/proxy.py +0 -0
  52. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/py.typed +0 -0
  53. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/server.py +0 -0
  54. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/streams.py +0 -0
  55. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/__init__.py +0 -0
  56. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/client.py +0 -0
  57. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/connection.py +0 -0
  58. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/messages.py +0 -0
  59. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/router.py +0 -0
  60. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/server.py +0 -0
  61. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/sync/utils.py +0 -0
  62. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/__init__.py +0 -0
  63. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/client.py +0 -0
  64. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/connection.py +0 -0
  65. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/messages.py +0 -0
  66. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/router.py +0 -0
  67. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/server.py +0 -0
  68. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/trio/utils.py +0 -0
  69. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/typing.py +0 -0
  70. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/uri.py +0 -0
  71. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/utils.py +0 -0
  72. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_vendor/websockets/version.py +0 -0
  73. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/_version.py +0 -0
  74. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/auth/__init__.py +0 -0
  75. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/auth/consent_form.py +0 -0
  76. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/auth/oidc_compat.py +0 -0
  77. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/auth/provider.py +0 -0
  78. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/backup_manager.py +0 -0
  79. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/browser_landing.py +0 -0
  80. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/client/__init__.py +0 -0
  81. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/client/rest_client.py +0 -0
  82. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/client/supervisor_client.py +0 -0
  83. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/client/websocket_client.py +0 -0
  84. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/client/websocket_listener.py +0 -0
  85. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/config.py +0 -0
  86. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/__init__.py +0 -0
  87. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/capture.py +0 -0
  88. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/content.py +0 -0
  89. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/paths.py +0 -0
  90. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/provision.py +0 -0
  91. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/dashboard_screenshot/theme_guard.py +0 -0
  92. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/errors.py +0 -0
  93. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/hacs_auto_refresh.py +0 -0
  94. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/llm_exposure.py +0 -0
  95. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/__init__.py +0 -0
  96. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/approval_queue.py +0 -0
  97. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/editing.py +0 -0
  98. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/evaluator.py +0 -0
  99. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/handlers.py +0 -0
  100. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/middleware.py +0 -0
  101. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/model.py +0 -0
  102. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/persistence.py +0 -0
  103. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/policy/value_sources.py +0 -0
  104. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/py.typed +0 -0
  105. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/read_only.py +0 -0
  106. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/redaction.py +0 -0
  107. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/renamed_tools.py +0 -0
  108. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/.claude/settings.json +0 -0
  109. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/.claude-plugin/marketplace.json +0 -0
  110. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/.claude-plugin/plugin.json +0 -0
  111. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/.github/ISSUE_TEMPLATE/skill-rca.md +0 -0
  112. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/.github/pull_request_template.md +0 -0
  113. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/AGENTS.md +0 -0
  114. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/CLAUDE.md +0 -0
  115. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/CONTRIBUTING.md +0 -0
  116. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/LICENSE +0 -0
  117. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/README.md +0 -0
  118. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/SKILL.md +0 -0
  119. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/evals/evals.json +0 -0
  120. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/appdaemon.md +0 -0
  121. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/automation-patterns.md +0 -0
  122. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/blueprint-guide.md +0 -0
  123. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/dashboard-cards.md +0 -0
  124. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/dashboard-guide.md +0 -0
  125. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/device-control.md +0 -0
  126. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/domain-docs.md +0 -0
  127. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/examples.yaml +0 -0
  128. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/helper-selection.md +0 -0
  129. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/safe-refactoring.md +0 -0
  130. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/scenes.md +0 -0
  131. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/template-guidelines.md +0 -0
  132. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/resources/skills-vendor/skills/home-assistant-best-practices/references/yaml-only-integrations.md +0 -0
  133. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/server.py +0 -0
  134. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_advanced.py +0 -0
  135. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_backups.py +0 -0
  136. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_fs.py +0 -0
  137. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_server.py +0 -0
  138. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_theme.py +0 -0
  139. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_handlers_tools.py +0 -0
  140. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_i18n.py +0 -0
  141. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_persistence.py +0 -0
  142. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_supervisor.py +0 -0
  143. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_theme.py +0 -0
  144. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/_tools_meta.py +0 -0
  145. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/README.md +0 -0
  146. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/cs.json +0 -0
  147. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/de.json +0 -0
  148. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/en.json +0 -0
  149. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/eo.json +0 -0
  150. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/es.json +0 -0
  151. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/fr.json +0 -0
  152. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/it.json +0 -0
  153. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/nl.json +0 -0
  154. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/pl.json +0 -0
  155. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/ru.json +0 -0
  156. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/sv.json +0 -0
  157. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/locales/zh-Hans.json +0 -0
  158. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/settings.css +0 -0
  159. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/settings.html +0 -0
  160. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/settings_ui/settings.js +0 -0
  161. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/smoke_test.py +0 -0
  162. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/stdio_settings_sidecar.py +0 -0
  163. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/strict_bps.py +0 -0
  164. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/__init__.py +0 -0
  165. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/auto_backup.py +0 -0
  166. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/backup.py +0 -0
  167. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/best_practice_checker.py +0 -0
  168. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/best_practice_result.py +0 -0
  169. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/best_practice_variables.py +0 -0
  170. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_api.py +0 -0
  171. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_config_entries.py +0 -0
  172. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_config_reads.py +0 -0
  173. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_devices.py +0 -0
  174. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_registries.py +0 -0
  175. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/component_registry_lookup.py +0 -0
  176. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_flow.py +0 -0
  177. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_flow_form.py +0 -0
  178. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_flow_menu.py +0 -0
  179. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_flow_walker.py +0 -0
  180. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_identity.py +0 -0
  181. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_reconfigure.py +0 -0
  182. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/config_entry_reload_watch.py +0 -0
  183. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/device_control.py +0 -0
  184. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/error_log_parsing.py +0 -0
  185. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/hacs_registration.py +0 -0
  186. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/helpers.py +0 -0
  187. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/integration_reconfigure.py +0 -0
  188. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/__init__.py +0 -0
  189. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/base.py +0 -0
  190. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/matter.py +0 -0
  191. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/thread.py +0 -0
  192. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/zigbee.py +0 -0
  193. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/radio/zwave.py +0 -0
  194. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/reference_validator.py +0 -0
  195. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/registry.py +0 -0
  196. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/renamed_tool_middleware.py +0 -0
  197. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/__init__.py +0 -0
  198. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_base.py +0 -0
  199. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_config.py +0 -0
  200. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_deep.py +0 -0
  201. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_entities.py +0 -0
  202. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_fetch.py +0 -0
  203. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_overview.py +0 -0
  204. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_scenes.py +0 -0
  205. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/smart_search/_scoring.py +0 -0
  206. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tool_search_hint_middleware.py +0 -0
  207. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_addons.py +0 -0
  208. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_areas.py +0 -0
  209. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_assist_pipeline.py +0 -0
  210. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_blueprints.py +0 -0
  211. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_bug_report.py +0 -0
  212. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_calendar.py +0 -0
  213. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_camera.py +0 -0
  214. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_categories.py +0 -0
  215. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_code.py +0 -0
  216. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_config_automations.py +0 -0
  217. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_config_dashboards.py +0 -0
  218. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_config_helpers.py +0 -0
  219. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_config_scenes.py +0 -0
  220. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_config_scripts.py +0 -0
  221. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_dashboard_screenshot.py +0 -0
  222. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_dev.py +0 -0
  223. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_energy.py +0 -0
  224. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_entities.py +0 -0
  225. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_filesystem.py +0 -0
  226. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_groups.py +0 -0
  227. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_hacs.py +0 -0
  228. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_history.py +0 -0
  229. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_integrations.py +0 -0
  230. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_labels.py +0 -0
  231. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_radio.py +0 -0
  232. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_registry.py +0 -0
  233. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_resources.py +0 -0
  234. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_security_policy.py +0 -0
  235. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_service.py +0 -0
  236. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_services.py +0 -0
  237. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_system.py +0 -0
  238. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_themes.py +0 -0
  239. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_todo.py +0 -0
  240. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_traces.py +0 -0
  241. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_updates.py +0 -0
  242. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_utility.py +0 -0
  243. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_voice_assistant.py +0 -0
  244. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_yaml_config.py +0 -0
  245. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_yaml_read.py +0 -0
  246. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/tools_zones.py +0 -0
  247. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/util_helpers.py +0 -0
  248. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/tools/validation_middleware.py +0 -0
  249. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/transforms/__init__.py +0 -0
  250. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/transforms/categorized_search.py +0 -0
  251. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/transforms/lite_docstrings.py +0 -0
  252. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/transport_security.py +0 -0
  253. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/update_check.py +0 -0
  254. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/__init__.py +0 -0
  255. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/config_hash.py +0 -0
  256. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/config_write_lock.py +0 -0
  257. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/data_paths.py +0 -0
  258. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/domain_handlers.py +0 -0
  259. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/fuzzy_search.py +0 -0
  260. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/kill_signal_diagnostics.py +0 -0
  261. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/operation_manager.py +0 -0
  262. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/python_sandbox.py +0 -0
  263. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/skill_loader.py +0 -0
  264. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/utils/usage_logger.py +0 -0
  265. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/visibility/__init__.py +0 -0
  266. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/visibility/model.py +0 -0
  267. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/visibility/persistence.py +0 -0
  268. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp/visibility/resolver.py +0 -0
  269. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp_dev.egg-info/SOURCES.txt +0 -0
  270. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp_dev.egg-info/dependency_links.txt +0 -0
  271. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp_dev.egg-info/entry_points.txt +0 -0
  272. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp_dev.egg-info/requires.txt +0 -0
  273. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/src/ha_mcp_dev.egg-info/top_level.txt +0 -0
  274. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/tests/__init__.py +0 -0
  275. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/tests/test_constants.py +0 -0
  276. {ha_mcp_dev-8.3.0.dev2372 → ha_mcp_dev-8.3.0.dev2377}/tests/test_env_manager.py +0 -0
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ha-mcp-dev
3
- Version: 8.3.0.dev2372
3
+ Version: 8.3.0.dev2377
4
4
  Summary: Home Assistant MCP Server - Complete control of Home Assistant through MCP
5
5
  Author-email: Julien <github@qc-h.net>
6
6
  License: MIT
@@ -4,7 +4,7 @@ build-backend = "setuptools.build_meta"
4
4
 
5
5
  [project]
6
6
  name = "ha-mcp-dev"
7
- version = "8.3.0.dev2372"
7
+ version = "8.3.0.dev2377"
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
@@ -20,7 +20,7 @@ from typing import TYPE_CHECKING, Any
20
20
  from starlette.requests import Request
21
21
  from starlette.responses import HTMLResponse, JSONResponse, Response
22
22
 
23
- from .._version import is_running_in_addon
23
+ from .._version import is_embedded, is_running_in_addon
24
24
  from ..transforms import DEFAULT_PINNED_TOOLS
25
25
  from ..utils.data_paths import get_data_dir
26
26
  from ._handlers_advanced import build_advanced_handlers
@@ -524,11 +524,11 @@ def _ingress_only(handler: _SettingsRoute) -> _SettingsRoute:
524
524
 
525
525
 
526
526
  # Mount prefix the settings UI is served under in long-lived HTTP transports
527
- # (Docker / standalone ha-mcp-web / OAuth / the add-on's secret-path mount).
528
- # Recorded by register_settings_routes so ha_get_overview can point users at
529
- # the settings page in modes that have no stdio sidecar URL file to surface
530
- # (issue #1458). Stays None in pure stdio mode, where the sidecar writes
531
- # ~/.ha-mcp/ui.url instead.
527
+ # (Docker / standalone ha-mcp-web). Recorded by register_settings_routes so
528
+ # ha_get_overview can point users at the settings page in modes that have no
529
+ # managed UI entry point or stdio sidecar URL file to surface (issue #1458).
530
+ # Stays None in managed HA deployments and pure stdio mode, where the sidebar /
531
+ # ingress entry point or ~/.ha-mcp/ui.url already provides discovery.
532
532
  _http_settings_prefix: str | None = None
533
533
 
534
534
 
@@ -539,8 +539,8 @@ def get_http_settings_prefix() -> str | None:
539
539
  long-lived HTTP server *and* advertising is enabled. ``ha_get_overview``
540
540
  reads it to hint at the settings page when there is no stdio sidecar URL to
541
541
  hand the user. It is None when the mount is deliberately not advertised
542
- (OAuth/OIDC dedicated-secret mode) — use :func:`is_http_settings_mounted`,
543
- not this, to tell HTTP from the stdio sidecar.
542
+ (managed HA or OAuth/OIDC dedicated-secret mode) — use
543
+ :func:`is_http_settings_mounted`, not this, to tell HTTP from the sidecar.
544
544
  """
545
545
  return _http_settings_prefix
546
546
 
@@ -594,12 +594,18 @@ def register_settings_routes(
594
594
  non-add-on mode, the function logs a warning and registers
595
595
  nothing rather than expose the routes publicly.
596
596
  advertise_prefix: When True (default), record the secret-path mount in
597
- ``_http_settings_prefix`` so ``ha_get_overview`` can hint at the
598
- settings URL. OAuth/OIDC modes pass False: there the settings UI
599
- sits under a *dedicated* secret path that must never be handed to
600
- MCP clients (GHSA-mx64-982r-65vg), so the mount happens but the
601
- prefix is not recorded.
597
+ ``_http_settings_prefix`` for unmanaged HTTP deployments so
598
+ ``ha_get_overview`` can hint at the settings URL. The managed app
599
+ (add-on) and embedded deployments never record it because Home Assistant
600
+ supplies their settings entry points. OAuth/OIDC callers pass False
601
+ because they use a dedicated settings secret.
602
602
  """
603
+ global _http_settings_mounted, _http_settings_prefix
604
+
605
+ # Never let a rejected or non-advertised registration inherit another
606
+ # server's credential-bearing hint.
607
+ _http_settings_prefix = None
608
+
603
609
  handlers = build_settings_handlers(server)
604
610
  secret_prefix = secret_path.rstrip("/") if secret_path else ""
605
611
  if secret_prefix and ("{" in secret_prefix or "}" in secret_prefix):
@@ -627,7 +633,6 @@ def register_settings_routes(
627
633
  # Past this point at least one HTTP mount happens (add-on root and/or the
628
634
  # secret path). Record that so consumers can distinguish HTTP from the stdio
629
635
  # sidecar even when the prefix itself is not advertised (advertise_prefix=False).
630
- global _http_settings_mounted
631
636
  _http_settings_mounted = True
632
637
 
633
638
  # Every route this function mounts except the add-on-only root mount is defined
@@ -705,10 +710,10 @@ def register_settings_routes(
705
710
  # need the same secret to reach the UI as they do for the MCP
706
711
  # endpoint.
707
712
  _mount(secret_prefix)
708
- if advertise_prefix:
713
+ if advertise_prefix and not is_addon and not is_embedded():
709
714
  # Record the mount so ha_get_overview can point users at the
710
- # settings page in HTTP transports that have no stdio sidecar URL
711
- # file (#1458). Suppressed in OAuth/OIDC modes, where the dedicated
712
- # secret path must not leak to MCP clients (GHSA-mx64-982r-65vg).
713
- global _http_settings_prefix
715
+ # settings page in unmanaged HTTP transports that have no stdio
716
+ # sidecar URL file (#1458). The managed app (add-on) and embedded deployments
717
+ # already have Home Assistant settings entry points; OAuth/OIDC
718
+ # callers suppress their dedicated settings secret explicitly.
714
719
  _http_settings_prefix = secret_prefix
@@ -3396,7 +3396,7 @@ class SearchTools:
3396
3396
  "tool_discovery, settings_url, settings_url_hint, "
3397
3397
  "read_only_mode, read_only_mode_hint, ha_mcp_update. Note: "
3398
3398
  "``settings_url`` (stdio mode), ``settings_url_hint`` "
3399
- "(HTTP/Docker/OAuth mode), the ``read_only_mode`` / "
3399
+ "(standalone HTTP/Docker mode), the ``read_only_mode`` / "
3400
3400
  "``read_only_mode_hint`` pair (only while Read Only Mode "
3401
3401
  "is on), and ``ha_mcp_update`` (when an update check applies) "
3402
3402
  "are emitted regardless of ``fields=`` projection so the "
@@ -3430,10 +3430,11 @@ class SearchTools:
3430
3430
  minimize the response) but only when the sidecar URL file
3431
3431
  actually exists.
3432
3432
 
3433
- In HTTP / Docker / OAuth modes there is no sidecar URL file and the
3434
- server can't know its externally reachable host, so the response
3435
- instead carries a ``settings_url_hint`` string telling the user where
3436
- the page is mounted and to read the full URL from the startup logs.
3433
+ In standalone HTTP / Docker modes, when an HTTP settings prefix is
3434
+ advertised, there is no sidecar URL file and the server can't know its
3435
+ externally reachable host. The response instead carries a
3436
+ ``settings_url_hint`` string telling the user where the page is mounted
3437
+ and how to find or construct the full URL.
3437
3438
  Hand whichever of the two fields is present to the user.
3438
3439
 
3439
3440
  The response also carries an ``ha_mcp_update`` object
@@ -3512,7 +3513,7 @@ class SearchTools:
3512
3513
  if sidecar_url:
3513
3514
  projected["settings_url"] = sidecar_url
3514
3515
  else:
3515
- # No stdio sidecar URL file. In HTTP / Docker / OAuth modes hint at
3516
+ # No stdio sidecar URL file. In standalone HTTP / Docker modes hint at
3516
3517
  # the page (and startup-log URL) instead of guessing a wrong absolute URL
3517
3518
  # when bound to 0.0.0.0 (issue #1458).
3518
3519
  from ..settings_ui import get_http_settings_prefix
@@ -3524,8 +3525,10 @@ class SearchTools:
3524
3525
  "The settings page (enable/disable/pin tools, feature "
3525
3526
  "flags, advanced settings, backups, tool-approval) is "
3526
3527
  f"served at '{settings_path}' on this MCP server. Find the "
3527
- "full URL in the ha-mcp startup logs, or append it to the "
3528
- "base URL your client connects to."
3528
+ "full URL in the ha-mcp startup logs. For a direct connection, "
3529
+ "use the MCP endpoint's scheme, host, and port with this "
3530
+ "settings path (replace the endpoint path rather than "
3531
+ "appending to it)."
3529
3532
  )
3530
3533
 
3531
3534
  # Surface Read Only Mode after projection so the flag survives any
@@ -49,6 +49,7 @@ import logging
49
49
  import re
50
50
  import time
51
51
  from collections.abc import Callable
52
+ from contextvars import ContextVar
52
53
  from typing import TYPE_CHECKING, Any, NoReturn
53
54
 
54
55
  from fastmcp.exceptions import ToolError
@@ -72,6 +73,10 @@ if TYPE_CHECKING:
72
73
 
73
74
  logger = logging.getLogger(__name__)
74
75
 
76
+ _config_load_warning_emitted: ContextVar[bool | None] = ContextVar(
77
+ "visibility_config_load_warning_emitted", default=None
78
+ )
79
+
75
80
  # The resolved hidden set is cached with a short TTL so a burst of tool calls
76
81
  # does not re-fetch the registry each time; a config edit invalidates it sooner
77
82
  # (the cache is keyed on the hide dimensions), so the ~30s window only applies to
@@ -353,6 +358,10 @@ class _VisibilityEnforcementBase(Middleware):
353
358
  loaded successfully — for the common non-enforce install that preserves
354
359
  availability, and for an enforce install it preserves the boundary.
355
360
  With no good load ever, fail CLOSED like PolicyMiddleware does.
361
+
362
+ Each half diagnoses a distinct config-load failure. A context-local
363
+ marker suppresses only the second traceback when both halves fail during
364
+ the same call.
356
365
  """
357
366
  config: VisibilityConfig | None
358
367
  try:
@@ -369,12 +378,15 @@ class _VisibilityEnforcementBase(Middleware):
369
378
  )
370
379
  else:
371
380
  outcome = "failing closed"
372
- if tool_name != _REPORT_ISSUE_TOOL or emit_report_issue_diagnostic:
381
+ warning_emitted = _config_load_warning_emitted.get()
382
+ if warning_emitted is not True:
373
383
  logger.warning(
374
384
  "visibility enforce: config load failed; %s",
375
385
  outcome,
376
386
  exc_info=True,
377
387
  )
388
+ if warning_emitted is not None:
389
+ _config_load_warning_emitted.set(True)
378
390
  # ``ha_report_issue`` is an unconditional diagnostic escape hatch while
379
391
  # the toggle is off, not only a registry-failure fallback. A missing or
380
392
  # corrupt first config load follows that safe default; a last-known-good
@@ -423,6 +435,15 @@ class VisibilityInboundEnforcement(_VisibilityEnforcementBase):
423
435
 
424
436
  async def on_call_tool(
425
437
  self, context: MiddlewareContext, call_next: CallNext
438
+ ) -> Any:
439
+ token = _config_load_warning_emitted.set(False)
440
+ try:
441
+ return await self._on_call_tool(context, call_next)
442
+ finally:
443
+ _config_load_warning_emitted.reset(token)
444
+
445
+ async def _on_call_tool(
446
+ self, context: MiddlewareContext, call_next: CallNext
426
447
  ) -> Any:
427
448
  name = context.message.name
428
449
  args = context.message.arguments or {}
@@ -1,6 +1,6 @@
1
1
  Metadata-Version: 2.4
2
2
  Name: ha-mcp-dev
3
- Version: 8.3.0.dev2372
3
+ Version: 8.3.0.dev2377
4
4
  Summary: Home Assistant MCP Server - Complete control of Home Assistant through MCP
5
5
  Author-email: Julien <github@qc-h.net>
6
6
  License: MIT