[psram] Make schema extractable with per-variant options (#16949)

Co-authored-by: J. Nick Koston <nick@koston.org>
This commit is contained in:
Jesse Hills
2026-06-15 19:55:21 +12:00
parent 94b248527d
commit 32ab3abd7c
8 changed files with 158 additions and 15 deletions

View File

@@ -97,6 +97,54 @@ def test_psram_configuration_valid_supported_variants(
FINAL_VALIDATE_SCHEMA(config)
def test_psram_applies_single_mode_default(
set_core_config: SetCoreConfigCallable,
) -> None:
"""On a single-mode variant the omitted mode/speed fall back to defaults."""
set_core_config(
PlatformFramework.ESP32_IDF,
platform_data={KEY_VARIANT: VARIANT_ESP32},
full_config={CONF_ESPHOME: {}},
)
from esphome.components.psram import CONFIG_SCHEMA
config = CONFIG_SCHEMA({})
assert config["mode"] == "quad"
assert config["speed"] == "40MHZ"
assert config["disabled"] is False
assert config["ignore_not_found"] is True
def test_psram_requires_mode_on_multi_mode_variant(
set_core_config: SetCoreConfigCallable,
) -> None:
"""A variant with multiple modes requires an explicit mode selection."""
set_core_config(
PlatformFramework.ESP32_IDF,
platform_data={KEY_VARIANT: VARIANT_ESP32S3},
full_config={CONF_ESPHOME: {}},
)
from esphome.components.psram import CONFIG_SCHEMA
with pytest.raises(cv.Invalid, match=r"requires PSRAM mode selection"):
CONFIG_SCHEMA({})
def test_psram_rejects_mode_invalid_for_variant(
set_core_config: SetCoreConfigCallable,
) -> None:
"""A mode not supported by the active variant is rejected by the schema."""
set_core_config(
PlatformFramework.ESP32_IDF,
platform_data={KEY_VARIANT: VARIANT_ESP32},
full_config={CONF_ESPHOME: {}},
)
from esphome.components.psram import CONFIG_SCHEMA
with pytest.raises(cv.Invalid, match=r"Unknown value 'octal'"):
CONFIG_SCHEMA({"mode": "octal"})
def _setup_psram_final_validation_test(
esp32_config: dict,
set_core_config: SetCoreConfigCallable,

View File

@@ -0,0 +1,5 @@
# Config-only: the ESP32-S3 supports both quad and octal. The compile test uses
# octal; this exercises the other branch of the per-variant mode enum (quad) and
# lets speed fall back to its 40MHz default.
psram:
mode: quad

View File

@@ -0,0 +1,4 @@
# Config-only: with no options the single-mode ESP32 resolves mode -> quad and
# speed -> 40MHz from the per-variant defaults. Compiling adds no signal here,
# so this only runs through `esphome config`.
psram:

View File

@@ -0,0 +1,4 @@
# Config-only: the ESP32-P4 has a distinct value set (hex mode, 20/100/200MHz).
# With no options it resolves mode -> hex and speed -> 20MHz, exercising the
# P4-specific default branch of the per-variant enums.
psram:

View File

@@ -139,6 +139,28 @@ def test_convert_walks_callable_schema_extractor() -> None:
assert "foo" in config_var["schema"]["config_vars"]
def test_convert_emits_variant_enum() -> None:
"""A per-variant enum is dumped with each value tagged by its variants."""
from esphome.components.esp32 import (
VARIANT_ESP32,
VARIANT_ESP32S3,
variant_filtered_enum,
)
validator = variant_filtered_enum(
{VARIANT_ESP32: ("quad",), VARIANT_ESP32S3: ("quad", "octal")},
lower=True,
)
config_var: dict = {}
_bls.convert(validator, config_var, "/test")
assert config_var["type"] == "enum"
assert config_var["values"] == {
"quad": {"variants": [VARIANT_ESP32, VARIANT_ESP32S3]},
"octal": {"variants": [VARIANT_ESP32S3]},
}
def test_convert_keys_emits_heuristic_sensitive_marker() -> None:
converted: dict = {}
_bls.convert_keys(converted, {cv.Optional("password"): cv.string}, "/root")