Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
12 changes: 12 additions & 0 deletions Makefile
Original file line number Diff line number Diff line change
Expand Up @@ -62,8 +62,20 @@ format: install-dev
$(POETRY) run black --extend-exclude test-data/gardenlinux .

lint: install-dev
@echo
@echo "------------------------------------------------------------------------------------------------------------------------"
@echo "--// BLACK //-----------------------------------------------------------------------------------------------------------"
@echo "------------------------------------------------------------------------------------------------------------------------"
$(POETRY) run black --diff --extend-exclude test-data/gardenlinux .
@echo
@echo "------------------------------------------------------------------------------------------------------------------------"
@echo "--// ISORT //-----------------------------------------------------------------------------------------------------------"
@echo "------------------------------------------------------------------------------------------------------------------------"
$(POETRY) run isort --check-only .
@echo
@echo "------------------------------------------------------------------------------------------------------------------------"
@echo "--// PYRIGHT //---------------------------------------------------------------------------------------------------------"
@echo "------------------------------------------------------------------------------------------------------------------------"
$(POETRY) run pyright

security: install-dev
Expand Down
68 changes: 68 additions & 0 deletions src/gardenlinux/distro_version/__init__.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,68 @@
class UnsupportedDistroVersion(Exception):
pass


class NotAPatchRelease(Exception):
pass


def DistroVersion(maybe_distro_version):
version_components = maybe_distro_version.split(".")
if len(version_components) > 3 or len(version_components) < 2:
raise UnsupportedDistroVersion(
f"Unexpected version number format {maybe_distro_version}"
)

if not all(map(lambda x: x.isdigit(), version_components)):
raise UnsupportedDistroVersion(
f"Unexpected version number format {maybe_distro_version}"
)

if len(version_components) == 2:
return LegacyDistroVersion(*(int(c) for c in version_components))
elif len(version_components) == 3:
return SemverDistroVersion(*(int(c) for c in version_components))
else:
raise UnsupportedDistroVersion(
f"Unexpected number of version components: {maybe_distro_version}"
)


class BaseDistroVersion:
major = None
minor = None
patch = None

def is_patch_release(self):
return self.patch and self.patch > 0


class LegacyDistroVersion(BaseDistroVersion):
def __init__(self, major, patch):
self.major = major
self.patch = patch

def __str__(self):
return f"{self.major}.{self.patch}"

def previous_patch_release(self):
if not self.is_patch_release():
raise NotAPatchRelease(f"{self} is not a patch release")

return LegacyDistroVersion(self.major, self.patch - 1)


class SemverDistroVersion(BaseDistroVersion):
def __init__(self, major, minor, patch):
self.major = major
self.minor = minor
self.patch = patch

def __str__(self):
return f"{self.major}.{self.minor}.{self.patch}"

def previous_patch_release(self):
if not self.is_patch_release():
raise NotAPatchRelease(f"{self} is not a patch release")

return SemverDistroVersion(self.major, self.minor, self.patch - 1)
84 changes: 39 additions & 45 deletions src/gardenlinux/github/release_notes/sections.py
Original file line number Diff line number Diff line change
Expand Up @@ -6,6 +6,7 @@
from yaml import SafeLoader

from gardenlinux.constants import GLVD_BASE_URL, REQUESTS_TIMEOUTS
from gardenlinux.distro_version import DistroVersion
from gardenlinux.logger import LoggerSetup

from .deployment_platform.ali_cloud import AliCloud
Expand All @@ -19,7 +20,11 @@
LOGGER = LoggerSetup.get_logger("gardenlinux.github.release_notes", "INFO")

IMAGE_IDS_VARIANT_ORDER = ["legacy", "usi", "tpm2_trustedboot"]
IMAGE_IDS_VARIANT_TABLE_NAMES = {"legacy": "Default", "usi": "USI", "tpm2_trustedboot": "TPM2"}
IMAGE_IDS_VARIANT_TABLE_NAMES = {
"legacy": "Default",
"usi": "USI",
"tpm2_trustedboot": "TPM2",
}
IMAGE_IDS_VARIANT_NAMES = {
"legacy": "Default",
"usi": "USI (Unified System Image)",
Expand Down Expand Up @@ -98,41 +103,26 @@ def release_notes_software_components_section(package_list):


def release_notes_compare_package_versions_section(gardenlinux_version, package_list):
version = DistroVersion(gardenlinux_version)
output = ""
version_components = gardenlinux_version.split(".")
# Assumes we always have version numbers like 1443.2
if len(version_components) == 2:
try:
major = int(version_components[0])
patch = int(version_components[1])

if patch > 0:
previous_version = f"{major}.{patch - 1}"

output += (
f"## Changes in Package Versions Compared to {previous_version}\n"
)
output += compare_apt_repo_versions(
previous_version, gardenlinux_version
)
elif patch == 0:
output += f"## Full List of Packages in Garden Linux version {major}\n"
output += "<details><summary>Expand to see full list</summary>\n"
output += "<pre>"
output += "\n"
for entry in package_list.values():
output += f"{entry!r}\n"
output += "</pre>"
output += "\n</details>\n\n"

except ValueError:
LOGGER.error(
f"Could not parse {gardenlinux_version} as the Garden Linux version, skipping version compare section"
)

if version.is_patch_release():
previous_version = f"{version.previous_patch_release()}"

output += f"## Changes in Package Versions Compared to {previous_version}\n"
output += compare_apt_repo_versions(previous_version, gardenlinux_version)
else:
LOGGER.error(
f"Unexpected version number format {gardenlinux_version}, expected format (major is int).(patch is int)"
output += (
f"## Full List of Packages in Garden Linux version {gardenlinux_version}\n"
)
output += "<details><summary>Expand to see full list</summary>\n"
output += "<pre>"
output += "\n"
for entry in package_list.values():
output += f"{entry!r}\n"
output += "</pre>"
output += "\n</details>\n\n"

return output


Expand All @@ -157,16 +147,20 @@ def generate_table_format(grouped_data):
details_content = PLATFORMS[platform].region_details(metadata)
summary_text = PLATFORMS[platform].summary_text(metadata)

download_link = PLATFORMS[platform].artifact_for_flavor(data['flavor'])
download_link = PLATFORMS[platform].artifact_for_flavor(
data["flavor"]
)

variant_display = IMAGE_IDS_VARIANT_TABLE_NAMES[variant]
output += (f"| {variant_display} "
f"| {PLATFORMS[platform].full_name()} "
f"| {arch} "
f"| `{data['flavor']}` "
f"| <details><summary>{summary_text}</summary><br>{details_content}</details> "
f"| <details><summary>Download</summary><br>{download_link}</details> "
"|\n")
output += (
f"| {variant_display} "
f"| {PLATFORMS[platform].full_name()} "
f"| {arch} "
f"| `{data['flavor']}` "
f"| <details><summary>{summary_text}</summary><br>{details_content}</details> "
f"| <details><summary>Download</summary><br>{download_link}</details> "
"|\n"
)

return output

Expand All @@ -181,9 +175,7 @@ def generate_detailed_format(grouped_data):
if variant not in grouped_data:
continue

output += (
f"<details>\n<summary>Variant - {IMAGE_IDS_VARIANT_NAMES[variant]}</summary>\n\n"
)
output += f"<details>\n<summary>Variant - {IMAGE_IDS_VARIANT_NAMES[variant]}</summary>\n\n"
output += f"### Variant - {IMAGE_IDS_VARIANT_NAMES[variant]}\n\n"

for platform in sorted(grouped_data[variant].keys()):
Expand All @@ -205,7 +197,9 @@ def generate_detailed_format(grouped_data):

output += f"- flavor: {data['flavor']}\n"

download_url = PLATFORMS[platform].artifact_for_flavor(data['flavor'], markdown_format=False)
download_url = PLATFORMS[platform].artifact_for_flavor(
data["flavor"], markdown_format=False
)
output += f" download_url: {download_url}\n"

if "regions" in data:
Expand Down
50 changes: 50 additions & 0 deletions tests/distro_version/test_distro_version.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,50 @@
import pytest

from gardenlinux.distro_version import (
DistroVersion,
LegacyDistroVersion,
NotAPatchRelease,
SemverDistroVersion,
UnsupportedDistroVersion,
)


def test_distro_version_unrecognizable_non_numeric_version():
with pytest.raises(UnsupportedDistroVersion):
DistroVersion("garden.linux")


def test_distro_version_unrecognizable_numeric_version():
with pytest.raises(UnsupportedDistroVersion):
DistroVersion("1.2.3.4")
with pytest.raises(UnsupportedDistroVersion):
DistroVersion("1.100.-10")


def test_distro_version_unrecognizable_too_short_version():
with pytest.raises(UnsupportedDistroVersion):
DistroVersion("1")


def test_distro_version_legacy_version_is_parsable():
assert isinstance(DistroVersion("1.2"), LegacyDistroVersion)


def test_distro_version_semver_version_is_parsable():
assert isinstance(DistroVersion("1.2.3"), SemverDistroVersion)


def test_distro_version_patch_release_is_recognized():
assert DistroVersion("1.1").is_patch_release()
assert DistroVersion("1.1.100").is_patch_release()
assert not DistroVersion("1.0").is_patch_release()
assert not DistroVersion("1.0.0").is_patch_release()


def test_distro_version_previous_patch_release_is_recognized():
assert DistroVersion("1.1").previous_patch_release().__str__() == "1.0"
assert DistroVersion("1.1.100").previous_patch_release().__str__() == "1.1.99"
with pytest.raises(NotAPatchRelease):
DistroVersion("1.0").previous_patch_release()
with pytest.raises(NotAPatchRelease):
DistroVersion("1.100.0").previous_patch_release()
Loading
Loading