mirror of
https://github.com/home-assistant/core.git
synced 2025-07-13 16:27:08 +00:00
Add default to inputs (#43636)
This commit is contained in:
parent
3767af14f3
commit
8533d9cae0
@ -10,7 +10,13 @@ import voluptuous as vol
|
|||||||
from voluptuous.humanize import humanize_error
|
from voluptuous.humanize import humanize_error
|
||||||
|
|
||||||
from homeassistant import loader
|
from homeassistant import loader
|
||||||
from homeassistant.const import CONF_DOMAIN, CONF_NAME, CONF_PATH, __version__
|
from homeassistant.const import (
|
||||||
|
CONF_DEFAULT,
|
||||||
|
CONF_DOMAIN,
|
||||||
|
CONF_NAME,
|
||||||
|
CONF_PATH,
|
||||||
|
__version__,
|
||||||
|
)
|
||||||
from homeassistant.core import DOMAIN as HA_DOMAIN, HomeAssistant, callback
|
from homeassistant.core import DOMAIN as HA_DOMAIN, HomeAssistant, callback
|
||||||
from homeassistant.exceptions import HomeAssistantError
|
from homeassistant.exceptions import HomeAssistantError
|
||||||
from homeassistant.helpers import placeholder
|
from homeassistant.helpers import placeholder
|
||||||
@ -82,6 +88,11 @@ class Blueprint:
|
|||||||
"""Return blueprint name."""
|
"""Return blueprint name."""
|
||||||
return self.data[CONF_BLUEPRINT][CONF_NAME]
|
return self.data[CONF_BLUEPRINT][CONF_NAME]
|
||||||
|
|
||||||
|
@property
|
||||||
|
def inputs(self) -> dict:
|
||||||
|
"""Return blueprint inputs."""
|
||||||
|
return self.data[CONF_BLUEPRINT][CONF_INPUT]
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def metadata(self) -> dict:
|
def metadata(self) -> dict:
|
||||||
"""Return blueprint metadata."""
|
"""Return blueprint metadata."""
|
||||||
@ -129,9 +140,23 @@ class BlueprintInputs:
|
|||||||
"""Return the inputs."""
|
"""Return the inputs."""
|
||||||
return self.config_with_inputs[CONF_USE_BLUEPRINT][CONF_INPUT]
|
return self.config_with_inputs[CONF_USE_BLUEPRINT][CONF_INPUT]
|
||||||
|
|
||||||
|
@property
|
||||||
|
def inputs_with_default(self):
|
||||||
|
"""Return the inputs and fallback to defaults."""
|
||||||
|
no_input = self.blueprint.placeholders - set(self.inputs)
|
||||||
|
|
||||||
|
inputs_with_default = dict(self.inputs)
|
||||||
|
|
||||||
|
for inp in no_input:
|
||||||
|
blueprint_input = self.blueprint.inputs[inp]
|
||||||
|
if isinstance(blueprint_input, dict) and CONF_DEFAULT in blueprint_input:
|
||||||
|
inputs_with_default[inp] = blueprint_input[CONF_DEFAULT]
|
||||||
|
|
||||||
|
return inputs_with_default
|
||||||
|
|
||||||
def validate(self) -> None:
|
def validate(self) -> None:
|
||||||
"""Validate the inputs."""
|
"""Validate the inputs."""
|
||||||
missing = self.blueprint.placeholders - set(self.inputs)
|
missing = self.blueprint.placeholders - set(self.inputs_with_default)
|
||||||
|
|
||||||
if missing:
|
if missing:
|
||||||
raise MissingPlaceholder(
|
raise MissingPlaceholder(
|
||||||
@ -144,7 +169,9 @@ class BlueprintInputs:
|
|||||||
@callback
|
@callback
|
||||||
def async_substitute(self) -> dict:
|
def async_substitute(self) -> dict:
|
||||||
"""Get the blueprint value with the inputs substituted."""
|
"""Get the blueprint value with the inputs substituted."""
|
||||||
processed = placeholder.substitute(self.blueprint.data, self.inputs)
|
processed = placeholder.substitute(
|
||||||
|
self.blueprint.data, self.inputs_with_default
|
||||||
|
)
|
||||||
combined = {**self.config_with_inputs, **processed}
|
combined = {**self.config_with_inputs, **processed}
|
||||||
# From config_with_inputs
|
# From config_with_inputs
|
||||||
combined.pop(CONF_USE_BLUEPRINT)
|
combined.pop(CONF_USE_BLUEPRINT)
|
||||||
|
@ -3,7 +3,13 @@ from typing import Any
|
|||||||
|
|
||||||
import voluptuous as vol
|
import voluptuous as vol
|
||||||
|
|
||||||
from homeassistant.const import CONF_DOMAIN, CONF_NAME, CONF_PATH, CONF_SELECTOR
|
from homeassistant.const import (
|
||||||
|
CONF_DEFAULT,
|
||||||
|
CONF_DOMAIN,
|
||||||
|
CONF_NAME,
|
||||||
|
CONF_PATH,
|
||||||
|
CONF_SELECTOR,
|
||||||
|
)
|
||||||
from homeassistant.core import callback
|
from homeassistant.core import callback
|
||||||
from homeassistant.helpers import config_validation as cv, selector
|
from homeassistant.helpers import config_validation as cv, selector
|
||||||
|
|
||||||
@ -54,6 +60,7 @@ BLUEPRINT_INPUT_SCHEMA = vol.Schema(
|
|||||||
{
|
{
|
||||||
vol.Optional(CONF_NAME): str,
|
vol.Optional(CONF_NAME): str,
|
||||||
vol.Optional(CONF_DESCRIPTION): str,
|
vol.Optional(CONF_DESCRIPTION): str,
|
||||||
|
vol.Optional(CONF_DEFAULT): cv.match_all,
|
||||||
vol.Optional(CONF_SELECTOR): selector.validate_selector,
|
vol.Optional(CONF_SELECTOR): selector.validate_selector,
|
||||||
}
|
}
|
||||||
)
|
)
|
||||||
|
@ -27,6 +27,26 @@ def blueprint_1():
|
|||||||
)
|
)
|
||||||
|
|
||||||
|
|
||||||
|
@pytest.fixture
|
||||||
|
def blueprint_2():
|
||||||
|
"""Blueprint fixture with default placeholder."""
|
||||||
|
return models.Blueprint(
|
||||||
|
{
|
||||||
|
"blueprint": {
|
||||||
|
"name": "Hello",
|
||||||
|
"domain": "automation",
|
||||||
|
"source_url": "https://github.com/balloob/home-assistant-config/blob/main/blueprints/automation/motion_light.yaml",
|
||||||
|
"input": {
|
||||||
|
"test-placeholder": {"name": "Name", "description": "Description"},
|
||||||
|
"test-placeholder-default": {"default": "test"},
|
||||||
|
},
|
||||||
|
},
|
||||||
|
"example": Placeholder("test-placeholder"),
|
||||||
|
"example-default": Placeholder("test-placeholder-default"),
|
||||||
|
}
|
||||||
|
)
|
||||||
|
|
||||||
|
|
||||||
@pytest.fixture
|
@pytest.fixture
|
||||||
def domain_bps(hass):
|
def domain_bps(hass):
|
||||||
"""Domain blueprints fixture."""
|
"""Domain blueprints fixture."""
|
||||||
@ -134,6 +154,44 @@ def test_blueprint_inputs_validation(blueprint_1):
|
|||||||
inputs.validate()
|
inputs.validate()
|
||||||
|
|
||||||
|
|
||||||
|
def test_blueprint_inputs_default(blueprint_2):
|
||||||
|
"""Test blueprint inputs."""
|
||||||
|
inputs = models.BlueprintInputs(
|
||||||
|
blueprint_2,
|
||||||
|
{"use_blueprint": {"path": "bla", "input": {"test-placeholder": 1}}},
|
||||||
|
)
|
||||||
|
inputs.validate()
|
||||||
|
assert inputs.inputs == {"test-placeholder": 1}
|
||||||
|
assert inputs.inputs_with_default == {
|
||||||
|
"test-placeholder": 1,
|
||||||
|
"test-placeholder-default": "test",
|
||||||
|
}
|
||||||
|
assert inputs.async_substitute() == {"example": 1, "example-default": "test"}
|
||||||
|
|
||||||
|
|
||||||
|
def test_blueprint_inputs_override_default(blueprint_2):
|
||||||
|
"""Test blueprint inputs."""
|
||||||
|
inputs = models.BlueprintInputs(
|
||||||
|
blueprint_2,
|
||||||
|
{
|
||||||
|
"use_blueprint": {
|
||||||
|
"path": "bla",
|
||||||
|
"input": {"test-placeholder": 1, "test-placeholder-default": "custom"},
|
||||||
|
}
|
||||||
|
},
|
||||||
|
)
|
||||||
|
inputs.validate()
|
||||||
|
assert inputs.inputs == {
|
||||||
|
"test-placeholder": 1,
|
||||||
|
"test-placeholder-default": "custom",
|
||||||
|
}
|
||||||
|
assert inputs.inputs_with_default == {
|
||||||
|
"test-placeholder": 1,
|
||||||
|
"test-placeholder-default": "custom",
|
||||||
|
}
|
||||||
|
assert inputs.async_substitute() == {"example": 1, "example-default": "custom"}
|
||||||
|
|
||||||
|
|
||||||
async def test_domain_blueprints_get_blueprint_errors(hass, domain_bps):
|
async def test_domain_blueprints_get_blueprint_errors(hass, domain_bps):
|
||||||
"""Test domain blueprints."""
|
"""Test domain blueprints."""
|
||||||
assert hass.data["blueprint"]["automation"] is domain_bps
|
assert hass.data["blueprint"]["automation"] is domain_bps
|
||||||
|
Loading…
x
Reference in New Issue
Block a user