mirror of
https://github.com/esphome/esphome.git
synced 2026-08-22 22:26:21 +00:00
Merge branch 'esp8266-native-framework-installer' into esp8266-native-library-backend
# Conflicts: # tests/unit_tests/test_platformio_library.py
This commit is contained in:
@@ -11,6 +11,10 @@ from esphome.framework_helpers import strip_win_long_path_prefix, tool_version_r
|
||||
|
||||
_LOGGER = logging.getLogger(__name__)
|
||||
|
||||
# esphome cv.boolean's spelling tables plus the 1/0 env convention
|
||||
TRUTHY_ENV_STRINGS = frozenset({"1", "true", "yes", "on", "enable"})
|
||||
FALSY_ENV_STRINGS = frozenset({"0", "false", "no", "off", "disable"})
|
||||
|
||||
|
||||
def _ccache_runs(ccache: str) -> bool:
|
||||
"""Return True when the ``ccache`` found on PATH actually runs."""
|
||||
@@ -31,9 +35,9 @@ def parse_enable_env(name: str) -> bool | None:
|
||||
if raw is None:
|
||||
return None
|
||||
lowered = raw.strip().lower()
|
||||
if lowered in ("1", "true", "yes", "on"):
|
||||
if lowered in TRUTHY_ENV_STRINGS:
|
||||
return True
|
||||
if lowered in ("0", "false", "no", "off"):
|
||||
if lowered in FALSY_ENV_STRINGS:
|
||||
return False
|
||||
_LOGGER.warning("Ignoring unrecognized %s=%r; use 1 or 0", name, raw)
|
||||
return None
|
||||
|
||||
@@ -97,3 +97,23 @@ def test_resolve_unrecognized_value_warns_and_probes(
|
||||
assert ccache.resolve_ccache_path() is None
|
||||
mock_probe.assert_called_once()
|
||||
assert "unrecognized ESPHOME_CCACHE_ENABLE" in caplog.text
|
||||
|
||||
|
||||
@pytest.mark.parametrize(
|
||||
("raw", "expected"),
|
||||
[
|
||||
("1", True),
|
||||
("enable", True),
|
||||
("ON", True),
|
||||
("0", False),
|
||||
("disable", False),
|
||||
("Off", False),
|
||||
("maybe", None),
|
||||
],
|
||||
)
|
||||
def test_parse_enable_env_spelling_tables(
|
||||
monkeypatch: pytest.MonkeyPatch, raw: str, expected: bool | None
|
||||
) -> None:
|
||||
"""cv.boolean's spelling tables plus the 1/0 env convention."""
|
||||
monkeypatch.setenv("ESPHOME_CCACHE_ENABLE", raw)
|
||||
assert ccache.parse_enable_env("ESPHOME_CCACHE_ENABLE") is expected
|
||||
|
||||
@@ -603,30 +603,6 @@ def test_lex_build_flags_dangling_flag_does_not_cross_entries(
|
||||
assert "Ignoring trailing '-I'" in caplog.text
|
||||
|
||||
|
||||
def test_split_flag_entry_non_string_is_clean() -> None:
|
||||
"""A dict or number from a third-party manifest fails naming the entry,
|
||||
not with an opaque shlex traceback."""
|
||||
|
||||
with pytest.raises(EsphomeError, match="Malformed build flag"):
|
||||
split_flag_entry({"esp32": ["-DX"]}, "lib x")
|
||||
with pytest.raises(EsphomeError, match="Malformed build flag 5"):
|
||||
split_flag_entry(5, "lib x")
|
||||
|
||||
|
||||
def test_source_kind_map_shape() -> None:
|
||||
"""The kind values the native compile rules key on, and the deliberate
|
||||
AS/ASPP merge (.s and .S both map to asm)."""
|
||||
|
||||
assert set(SOURCE_KIND_FOR_SUFFIX.values()) == {"c", "cxx", "asm"}
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".s"] == "asm"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".S"] == "asm"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".c"] == "c"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".cpp"] == "cxx"
|
||||
# SCons's case-sensitive C++ suffixes: PIO compiles .C as C++
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".C"] == "cxx"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".C++"] == "cxx"
|
||||
|
||||
|
||||
def test_normalize_dependencies_forms(caplog) -> None:
|
||||
"""Every PIO-legal spelling normalizes; unrecognizable entries warn."""
|
||||
from esphome.platformio.library import normalize_dependencies
|
||||
@@ -684,6 +660,54 @@ def test_walk_warns_for_properties_only_depends(
|
||||
assert "declares dependencies via library.properties" in caplog.text
|
||||
|
||||
|
||||
def test_walk_warns_for_nonplatform_invalid_library(
|
||||
tmp_path, monkeypatch, caplog: pytest.LogCaptureFixture
|
||||
) -> None:
|
||||
"""A dependency dropped for any cause other than the routine platform
|
||||
filter is visible in every backend."""
|
||||
_patch_download_with_manifests(
|
||||
monkeypatch,
|
||||
tmp_path,
|
||||
{"esphome/A": {"name": "A", "dependencies": [{"name": "B", "version": "1.0"}]}},
|
||||
)
|
||||
calls = {"n": 0}
|
||||
real = lib.check_library_data
|
||||
|
||||
def flaky(data, platform, framework):
|
||||
calls["n"] += 1
|
||||
if calls["n"] > 1:
|
||||
raise InvalidLibrary("manifest is corrupt")
|
||||
return real(data, platform, framework)
|
||||
|
||||
monkeypatch.setattr(lib, "check_library_data", flaky)
|
||||
convert_libraries([Library("esphome/A", None, None)], _backend())
|
||||
assert "Skipping dependency B of esphome/A: manifest is corrupt" in caplog.text
|
||||
|
||||
|
||||
def test_split_flag_entry_non_string_is_clean() -> None:
|
||||
"""A dict or number from a third-party manifest fails naming the entry,
|
||||
not with an opaque shlex traceback."""
|
||||
|
||||
with pytest.raises(EsphomeError, match="Malformed build flag"):
|
||||
split_flag_entry({"esp32": ["-DX"]}, "lib x")
|
||||
with pytest.raises(EsphomeError, match="Malformed build flag 5"):
|
||||
split_flag_entry(5, "lib x")
|
||||
|
||||
|
||||
def test_source_kind_map_shape() -> None:
|
||||
"""The kind values the native compile rules key on, and the deliberate
|
||||
AS/ASPP merge (.s and .S both map to asm)."""
|
||||
|
||||
assert set(SOURCE_KIND_FOR_SUFFIX.values()) == {"c", "cxx", "asm"}
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".s"] == "asm"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".S"] == "asm"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".c"] == "c"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".cpp"] == "cxx"
|
||||
# SCons's case-sensitive C++ suffixes: PIO compiles .C as C++
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".C"] == "cxx"
|
||||
assert SOURCE_KIND_FOR_SUFFIX[".C++"] == "cxx"
|
||||
|
||||
|
||||
def test_versionless_platform_filtered_dependency_stays_quiet(
|
||||
tmp_path, monkeypatch, caplog: pytest.LogCaptureFixture
|
||||
) -> None:
|
||||
@@ -743,30 +767,6 @@ def test_versionless_dependency_without_provider_warns(
|
||||
)
|
||||
|
||||
|
||||
def test_walk_warns_for_nonplatform_invalid_library(
|
||||
tmp_path, monkeypatch, caplog: pytest.LogCaptureFixture
|
||||
) -> None:
|
||||
"""A dependency dropped for any cause other than the routine platform
|
||||
filter is visible in every backend."""
|
||||
_patch_download_with_manifests(
|
||||
monkeypatch,
|
||||
tmp_path,
|
||||
{"esphome/A": {"name": "A", "dependencies": [{"name": "B", "version": "1.0"}]}},
|
||||
)
|
||||
calls = {"n": 0}
|
||||
real = lib.check_library_data
|
||||
|
||||
def flaky(data, platform, framework):
|
||||
calls["n"] += 1
|
||||
if calls["n"] > 1:
|
||||
raise InvalidLibrary("manifest is corrupt")
|
||||
return real(data, platform, framework)
|
||||
|
||||
monkeypatch.setattr(lib, "check_library_data", flaky)
|
||||
convert_libraries([Library("esphome/A", None, None)], _backend())
|
||||
assert "Skipping dependency B of esphome/A: manifest is corrupt" in caplog.text
|
||||
|
||||
|
||||
def test_versionless_owner_qualified_dependency_warns_despite_provides(
|
||||
tmp_path, monkeypatch, caplog: pytest.LogCaptureFixture
|
||||
) -> None:
|
||||
|
||||
Reference in New Issue
Block a user