diff --git a/tests/integration_tests/build/test_gh_release.py b/tests/integration_tests/build/test_gh_release.py new file mode 100644 index 00000000000..da0053ef126 --- /dev/null +++ b/tests/integration_tests/build/test_gh_release.py @@ -0,0 +1,42 @@ +# Copyright 2026 Amazon.com, Inc. or its affiliates. All Rights Reserved. +# SPDX-License-Identifier: Apache-2.0 + +"""Tests for the GitHub release helper.""" + +import importlib +import sys +import tarfile +from pathlib import Path + +TOOLS_DIR = Path(__file__).resolve().parents[3] / "tools" +sys.path.insert(0, str(TOOLS_DIR)) + +gh_release = importlib.import_module("gh_release") + + +def test_build_tarball_excludes_custom_cpu_templates(tmp_path): + """Custom CPU templates are already available in the repository.""" + tag_version = "v1.15.0" + release_dir = tmp_path / f"release-{tag_version}-x86_64" + release_dir.mkdir() + included_assets = [ + f"firecracker-{tag_version}-x86_64", + f"firecracker_spec-{tag_version}.yaml", + f"seccomp-filter-{tag_version}-x86_64.json", + ] + excluded_assets = [ + f"C3-{tag_version}.json", + f"GNR_TO_T2_5.10-{tag_version}.json", + "RELEASE_NOTES", + "SHA256SUMS.sig", + ] + for asset in included_assets + excluded_assets: + (release_dir / asset).write_text("test asset", encoding="utf-8") + + release_tgz = tmp_path / f"firecracker-{tag_version}-x86_64.tgz" + gh_release.build_tarball(release_dir, release_tgz, "x86_64", tag_version) + + with tarfile.open(release_tgz) as tar: + tar_assets = {Path(member.name).name for member in tar.getmembers()} + + assert tar_assets == set(included_assets) diff --git a/tools/gh_release.py b/tools/gh_release.py index ae43c5797d6..d2dba22eacd 100755 --- a/tools/gh_release.py +++ b/tools/gh_release.py @@ -14,10 +14,12 @@ import tarfile from pathlib import Path -from github import Github +CUSTOM_CPU_TEMPLATE_DIR = ( + Path(__file__).resolve().parent.parent / "tests/data/custom_cpu_templates" +) -def build_tarball(release_dir, release_tgz, arch): +def build_tarball(release_dir, release_tgz, arch, tag_version): """Build a release tarball with local assets""" # Do not include signatures in GitHub release since we aren't # making those keys public. @@ -26,7 +28,10 @@ def build_tarball(release_dir, release_tgz, arch): exclude_files = { "RELEASE_NOTES", "SHA256SUMS.sig", - *[f.stem for f in Path("tests/data/custom_cpu_templates").glob("*.json")], + *[ + f"{template_path.stem}-{tag_version}.json" + for template_path in CUSTOM_CPU_TEMPLATE_DIR.glob("*.json") + ], } with tarfile.open(release_tgz, "w:gz") as tar: files = [x for x in release_dir.rglob("*") if x.is_file()] @@ -43,6 +48,9 @@ def build_tarball(release_dir, release_tgz, arch): def github_release(tag_version, repo, github_token): """Create a draft release in GitHub""" + # Import lazily so tarball-building helpers can be tested without PyGithub. + from github import Github # pylint: disable=import-outside-toplevel + prerelease = False assets = [] for arch in ["x86_64", "aarch64"]: @@ -50,7 +58,7 @@ def github_release(tag_version, repo, github_token): # Build tarball release_tgz = Path(f"firecracker-{tag_version}-{arch}.tgz") print(f"Creating release archive {release_tgz} ...") - build_tarball(release_dir, release_tgz, arch) + build_tarball(release_dir, release_tgz, arch, tag_version) print("Done. Archive successfully created. sha256sum result:") sha256sums = release_tgz.with_suffix(release_tgz.suffix + ".sha256.txt") subprocess.run(