Files
esphome/tests/script/test_docker_build.py
T
Jesse Hills b09a5f9e43
CI for docker images / Build docker containers (docker, ubuntu-24.04) (push) Has been cancelled
CI for docker images / Build docker containers (docker, ubuntu-24.04-arm) (push) Has been cancelled
CI for docker images / Build docker containers (ha-addon, ubuntu-24.04) (push) Has been cancelled
CI for docker images / Build docker containers (ha-addon, ubuntu-24.04-arm) (push) Has been cancelled
CI for docker images / Push docker manifest to ghcr.io (push) Has been cancelled
CI for docker images / Push ha-addon manifest to ghcr.io (push) Has been cancelled
CI / Create common environment (push) Has been cancelled
CI / Check pylint (push) Has been cancelled
CI / Run script/ci-custom (push) Has been cancelled
CI / Check import esphome.__main__ time (push) Has been cancelled
CI / Test downstream esphome/device-builder (push) Has been cancelled
CI / Run pytest (macOS-latest, 3.11) (push) Has been cancelled
CI / Run pytest (macOS-latest, 3.14) (push) Has been cancelled
CI / Run pytest (ubuntu-latest, 3.11) (push) Has been cancelled
CI / Run pytest (ubuntu-latest, 3.13) (push) Has been cancelled
CI / Run pytest (ubuntu-latest, 3.14) (push) Has been cancelled
CI / Run pytest (windows-latest, 3.11) (push) Has been cancelled
CI / Run pytest (windows-latest, 3.14) (push) Has been cancelled
CI / Determine which jobs to run (push) Has been cancelled
CI / Run integration tests (${{ matrix.bucket.name }}) (push) Has been cancelled
CI / Run C++ unit tests (push) Has been cancelled
CI / Run CodSpeed benchmarks (push) Has been cancelled
CI / Run script/clang-tidy for ESP8266 (push) Has been cancelled
CI / Run script/clang-tidy for ZEPHYR (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 Arduino (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 IDF (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 IDF 1/3 (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 IDF 2/3 (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 IDF 3/3 (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 C6 (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 P4 (push) Has been cancelled
CI / Run script/clang-tidy for ESP32 S3 (push) Has been cancelled
CI / Test components batch (${{ matrix.components }}) (push) Has been cancelled
CI / Test components with native ESP-IDF (push) Has been cancelled
CI / pre-commit.ci lite (push) Has been cancelled
CI / Build target branch for memory impact (push) Has been cancelled
CI / Build PR branch for memory impact (push) Has been cancelled
CI / Comment memory impact (push) Has been cancelled
CI / CI Status (push) Has been cancelled
[ci] Push branch-tagged docker images to ghcr.io for local testing (#16992)
2026-06-16 13:37:31 +12:00

170 lines
4.5 KiB
Python

"""Unit tests for docker/build.py command generation."""
import importlib.util
from pathlib import Path
import sys
import pytest
_BUILD_PY = Path(__file__).parents[2] / "docker" / "build.py"
_spec = importlib.util.spec_from_file_location("docker_build", _BUILD_PY)
docker_build = importlib.util.module_from_spec(_spec)
_spec.loader.exec_module(docker_build)
def _run(capsys: pytest.CaptureFixture[str], *argv: str) -> list[str]:
"""Run build.py main() in dry-run mode and return the emitted commands."""
full_argv = ["build.py", "--dry-run", *argv]
with pytest.MonkeyPatch.context() as mp:
mp.setattr(sys, "argv", full_argv)
docker_build.main()
out = capsys.readouterr().out
return [line[2:] for line in out.splitlines() if line.startswith("$ ")]
def test_branch_build_pushes_single_ghcr_tag_without_cache_to(
capsys: pytest.CaptureFixture[str],
) -> None:
commands = _run(
capsys,
"--tag",
"my-branch",
"--arch",
"amd64",
"--build-type",
"docker",
"--registry",
"ghcr",
"build",
"--push",
"--no-cache-to",
)
assert len(commands) == 1
cmd = commands[0]
# Custom tag -> only the tag itself, no companion "dev"/"latest" tags
assert "--tag ghcr.io/esphome/esphome-amd64:my-branch" in cmd
assert ":dev" not in cmd
# ghcr only -> no Docker Hub image name
assert "--tag esphome/esphome-amd64:my-branch" not in cmd
# custom tag falls back to the dev cache for reads
assert (
"--cache-from type=registry,ref=ghcr.io/esphome/esphome-amd64:cache-dev" in cmd
)
assert "--push" in cmd
# --no-cache-to must suppress the cache write
assert "--cache-to" not in cmd
def test_branch_manifest_targets_ghcr_only(
capsys: pytest.CaptureFixture[str],
) -> None:
commands = _run(
capsys,
"--tag",
"my-branch",
"--build-type",
"ha-addon",
"--registry",
"ghcr",
"manifest",
)
assert commands == [
"docker buildx imagetools create "
"--tag ghcr.io/esphome/esphome-hassio:my-branch "
"ghcr.io/esphome/esphome-hassio-amd64:my-branch "
"ghcr.io/esphome/esphome-hassio-aarch64:my-branch"
]
def test_release_build_keeps_both_registries_and_cache_to(
capsys: pytest.CaptureFixture[str],
) -> None:
commands = _run(
capsys,
"--tag",
"2025.6.0",
"--arch",
"amd64",
"--build-type",
"docker",
"build",
"--push",
)
cmd = commands[0]
# Default (no --registry) keeps both Docker Hub and ghcr image names
assert "--tag esphome/esphome-amd64:2025.6.0" in cmd
assert "--tag ghcr.io/esphome/esphome-amd64:2025.6.0" in cmd
# Release channel still gets its companion tags
assert "--tag esphome/esphome-amd64:latest" in cmd
# Without --no-cache-to the cache write is preserved
assert (
"--cache-to type=registry,ref=ghcr.io/esphome/esphome-amd64:cache-latest,mode=max"
in cmd
)
def test_build_no_push_omits_push_and_cache(
capsys: pytest.CaptureFixture[str],
) -> None:
commands = _run(
capsys,
"--tag",
"my-branch",
"--arch",
"amd64",
"--build-type",
"docker",
"--registry",
"ghcr",
"build",
)
cmd = commands[0]
assert "--tag ghcr.io/esphome/esphome-amd64:my-branch" in cmd
assert "--push" not in cmd
assert "--cache-to" not in cmd
def test_build_dockerhub_only(capsys: pytest.CaptureFixture[str]) -> None:
commands = _run(
capsys,
"--tag",
"my-branch",
"--arch",
"amd64",
"--build-type",
"docker",
"--registry",
"dockerhub",
"build",
"--push",
)
cmd = commands[0]
assert "--tag esphome/esphome-amd64:my-branch" in cmd
assert "ghcr.io" not in cmd
# Cache reference falls back to Docker Hub when GHCR isn't selected
assert "--cache-from type=registry,ref=esphome/esphome-amd64:cache-dev" in cmd
def test_manifest_dockerhub_only(capsys: pytest.CaptureFixture[str]) -> None:
commands = _run(
capsys,
"--tag",
"my-branch",
"--build-type",
"docker",
"--registry",
"dockerhub",
"manifest",
)
create = commands[0]
assert create.startswith(
"docker buildx imagetools create --tag esphome/esphome:my-branch "
)
assert "ghcr.io" not in create