Avoid core documentation url hosted elsewhere (#130513)

Co-authored-by: epenet <6771947+epenet@users.noreply.github.com>
Co-authored-by: Franck Nijhof <frenck@frenck.nl>
This commit is contained in:
Joost Lekkerkerker 2025-01-14 13:17:25 +01:00 committed by GitHub
parent 4f796174fd
commit 5e50b11114
No known key found for this signature in database
GPG Key ID: B5690EEEBB952194

View File

@ -27,6 +27,8 @@ DOCUMENTATION_URL_HOST = "www.home-assistant.io"
DOCUMENTATION_URL_PATH_PREFIX = "/integrations/"
DOCUMENTATION_URL_EXCEPTIONS = {"https://www.home-assistant.io/hassio"}
_CORE_DOCUMENTATION_BASE = "https://www.home-assistant.io/integrations"
class NonScaledQualityScaleTiers(StrEnum):
"""Supported manifest quality scales."""
@ -117,19 +119,26 @@ NO_IOT_CLASS = [
]
def documentation_url(value: str) -> str:
def core_documentation_url(value: str) -> str:
"""Validate that a documentation url has the correct path and domain."""
if value in DOCUMENTATION_URL_EXCEPTIONS:
return value
if not value.startswith(_CORE_DOCUMENTATION_BASE):
raise vol.Invalid(
f"Documentation URL does not begin with {_CORE_DOCUMENTATION_BASE}"
)
return value
def custom_documentation_url(value: str) -> str:
"""Validate that a custom integration documentation url is correct."""
parsed_url = urlparse(value)
if parsed_url.scheme != DOCUMENTATION_URL_SCHEMA:
raise vol.Invalid("Documentation url is not prefixed with https")
if parsed_url.netloc == DOCUMENTATION_URL_HOST and not parsed_url.path.startswith(
DOCUMENTATION_URL_PATH_PREFIX
):
if value.startswith(_CORE_DOCUMENTATION_BASE):
raise vol.Invalid(
"Documentation url does not begin with www.home-assistant.io/integrations"
"Documentation URL should point to the custom integration documentation"
)
return value
@ -258,7 +267,7 @@ INTEGRATION_MANIFEST_SCHEMA = vol.Schema(
}
)
],
vol.Required("documentation"): vol.All(vol.Url(), documentation_url),
vol.Required("documentation"): vol.All(vol.Url(), core_documentation_url),
vol.Optional("quality_scale"): vol.In(SUPPORTED_QUALITY_SCALES),
vol.Optional("requirements"): [str],
vol.Optional("dependencies"): [str],
@ -293,6 +302,7 @@ def manifest_schema(value: dict[str, Any]) -> vol.Schema:
CUSTOM_INTEGRATION_MANIFEST_SCHEMA = INTEGRATION_MANIFEST_SCHEMA.extend(
{
vol.Required("documentation"): vol.All(vol.Url(), custom_documentation_url),
vol.Optional("version"): vol.All(str, verify_version),
vol.Optional("issue_tracker"): vol.Url(),
vol.Optional("import_executor"): bool,