1 """Config flow for MusicAssistant integration."""
3 from __future__
import annotations
5 from typing
import TYPE_CHECKING, Any
7 from music_assistant_client
import MusicAssistantClient
8 from music_assistant_client.exceptions
import (
11 MusicAssistantClientException,
13 from music_assistant_models.api
import ServerInfoMessage
14 import voluptuous
as vol
22 from .const
import DOMAIN, LOGGER
24 DEFAULT_URL =
"http://mass.local:8095"
25 DEFAULT_TITLE =
"Music Assistant"
29 """Return a schema for the manual step."""
30 default_url = user_input.get(CONF_URL, DEFAULT_URL)
33 vol.Required(CONF_URL, default=default_url): str,
39 """Validate the user input allows us to connect."""
40 async
with MusicAssistantClient(
41 url, aiohttp_client.async_get_clientsession(hass)
44 assert client.server_info
is not None
45 return client.server_info
49 """Handle a config flow for MusicAssistant."""
54 """Set up flow instance."""
55 self.
server_infoserver_info: ServerInfoMessage |
None =
None
58 self, user_input: dict[str, Any] |
None =
None
59 ) -> ConfigFlowResult:
60 """Handle a manual configuration."""
61 errors: dict[str, str] = {}
62 if user_input
is not None:
65 self.hass, user_input[CONF_URL]
68 self.
server_infoserver_info.server_id, raise_on_progress=
False
71 updates={CONF_URL: self.
server_infoserver_info.base_url},
72 reload_on_update=
True,
75 errors[
"base"] =
"cannot_connect"
76 except InvalidServerVersion:
77 errors[
"base"] =
"invalid_server_version"
78 except MusicAssistantClientException:
79 LOGGER.exception(
"Unexpected exception")
80 errors[
"base"] =
"unknown"
96 self, discovery_info: zeroconf.ZeroconfServiceInfo
97 ) -> ConfigFlowResult:
98 """Handle a discovered Mass server.
100 This flow is triggered by the Zeroconf component. It will check if the
101 host is already configured and delegate to the import step if not.
104 if "server_id" not in discovery_info.properties:
108 self.
server_infoserver_info = ServerInfoMessage.from_dict(discovery_info.properties)
111 updates={CONF_URL: self.
server_infoserver_info.base_url},
112 reload_on_update=
True,
116 except CannotConnect:
121 self, user_input: dict[str, Any] |
None =
None
122 ) -> ConfigFlowResult:
123 """Handle user-confirmation of discovered server."""
126 if user_input
is not None:
135 step_id=
"discovery_confirm",
136 description_placeholders={
"url": self.
server_infoserver_info.base_url},
ConfigFlowResult async_step_user(self, dict[str, Any]|None user_input=None)
ConfigFlowResult async_step_discovery_confirm(self, dict[str, Any]|None user_input=None)
ConfigFlowResult async_step_zeroconf(self, zeroconf.ZeroconfServiceInfo discovery_info)
None _abort_if_unique_id_configured(self, dict[str, Any]|None updates=None, bool reload_on_update=True, *str error="already_configured")
None _set_confirm_only(self)
ConfigEntry|None async_set_unique_id(self, str|None unique_id=None, *bool raise_on_progress=True)
ConfigFlowResult async_create_entry(self, *str title, Mapping[str, Any] data, str|None description=None, Mapping[str, str]|None description_placeholders=None, Mapping[str, Any]|None options=None)
ConfigFlowResult async_abort(self, *str reason, Mapping[str, str]|None description_placeholders=None)
ConfigFlowResult async_show_form(self, *str|None step_id=None, vol.Schema|None data_schema=None, dict[str, str]|None errors=None, Mapping[str, str]|None description_placeholders=None, bool|None last_step=None, str|None preview=None)
_FlowResultT async_show_form(self, *str|None step_id=None, vol.Schema|None data_schema=None, dict[str, str]|None errors=None, Mapping[str, str]|None description_placeholders=None, bool|None last_step=None, str|None preview=None)
_FlowResultT async_create_entry(self, *str|None title=None, Mapping[str, Any] data, str|None description=None, Mapping[str, str]|None description_placeholders=None)
_FlowResultT async_abort(self, *str reason, Mapping[str, str]|None description_placeholders=None)
ServerInfoMessage get_server_info(HomeAssistant hass, str url)
vol.Schema get_manual_schema(dict[str, Any] user_input)