1
0
mirror of https://github.com/home-assistant/core.git synced 2026-05-08 17:49:37 +01:00
Files
core/homeassistant/components/hassio/addon_panel.py
T
2026-01-21 14:59:13 +02:00

90 lines
2.9 KiB
Python

"""Implement the Ingress Panel feature for Hass.io Add-ons."""
from http import HTTPStatus
import logging
from typing import Any
from aiohttp import web
from homeassistant.components import frontend
from homeassistant.components.http import HomeAssistantView
from homeassistant.const import ATTR_ICON
from homeassistant.core import HomeAssistant
from .const import ATTR_ADMIN, ATTR_ENABLE, ATTR_PANELS, ATTR_TITLE
from .handler import HassIO, HassioAPIError
_LOGGER = logging.getLogger(__name__)
async def async_setup_addon_panel(hass: HomeAssistant, hassio: HassIO) -> None:
"""Add-on Ingress Panel setup."""
hassio_addon_panel = HassIOAddonPanel(hass, hassio)
hass.http.register_view(hassio_addon_panel)
# If panels are exists
if not (panels := await hassio_addon_panel.get_panels()):
return
# Register available panels
for addon, data in panels.items():
if not data[ATTR_ENABLE]:
continue
# _register_panel never suspends and is only
# a coroutine because it would be a breaking change
# to make it a normal function
_register_panel(hass, addon, data)
class HassIOAddonPanel(HomeAssistantView):
"""Hass.io view to handle base part."""
name = "api:hassio_push:panel"
url = "/api/hassio_push/panel/{addon}"
def __init__(self, hass: HomeAssistant, hassio: HassIO) -> None:
"""Initialize WebView."""
self.hass = hass
self.hassio = hassio
async def post(self, request: web.Request, addon: str) -> web.Response:
"""Handle new add-on panel requests."""
panels = await self.get_panels()
# Panel exists for add-on slug
if addon not in panels or not panels[addon][ATTR_ENABLE]:
_LOGGER.error("Panel is not enable for %s", addon)
return web.Response(status=HTTPStatus.BAD_REQUEST)
data = panels[addon]
# Register panel
_register_panel(self.hass, addon, data)
return web.Response()
async def delete(self, request: web.Request, addon: str) -> web.Response:
"""Handle remove add-on panel requests."""
frontend.async_remove_panel(self.hass, addon)
return web.Response()
async def get_panels(self) -> dict:
"""Return panels add-on info data."""
try:
data = await self.hassio.get_ingress_panels()
return data[ATTR_PANELS]
except HassioAPIError as err:
_LOGGER.error("Can't read panel info: %s", err)
return {}
def _register_panel(hass: HomeAssistant, addon: str, data: dict[str, Any]):
"""Init coroutine to register the panel."""
frontend.async_register_built_in_panel(
hass,
"app",
frontend_url_path=addon,
sidebar_title=data[ATTR_TITLE],
sidebar_icon=data[ATTR_ICON],
require_admin=data[ATTR_ADMIN],
config={"addon": addon},
)