From 797d036a2481abf6261dbcc3003268ccfac610f7 Mon Sep 17 00:00:00 2001 From: kdmukai <934746+kdmukai@users.noreply.github.com> Date: Sat, 27 Dec 2025 11:02:29 -0600 Subject: [PATCH] Add `is_release_image` and related test --- src/seedsigner/helpers/version.py | 33 +++++++++++++ src/seedsigner/views/settings_views.py | 6 +-- tests/test_version.py | 64 ++++++++++++++++++++++++++ 3 files changed, 99 insertions(+), 4 deletions(-) diff --git a/src/seedsigner/helpers/version.py b/src/seedsigner/helpers/version.py index 17e75cc7..7bdaf358 100644 --- a/src/seedsigner/helpers/version.py +++ b/src/seedsigner/helpers/version.py @@ -142,6 +142,39 @@ class Version(Singleton): return cls.get_instance()._version_timestamp + @classmethod + def is_release_image(cls) -> bool: + """ + Returns True if all of the following are true: + * We're running in SeedSigner OS. + * `version_fork` is the main "seedsigner" repo. + * `version_name` corresponds to a "clean" semantic version tag. + * e.g. "v0.8.5" but not "v0.8.5-rc1". + """ + if Settings.HOSTNAME != Settings.SEEDSIGNER_OS: + return False + + fork = cls.get_version_fork() + if not fork or fork.lower() != "seedsigner": + return False + + version = cls.get_version_name() + # Even though our release tags in git do not include "v", at this point in the + # code the "v" will already be prepended to `version_name` if it is a semantic + # version tag. If "v" is prepended to future release tags, logic further up the + # chain will already gracefully handle it. + if not version or not version.startswith("v"): + return False + + # Is it a clean semantic version? + version = version[1:] # strip the "v" prefix + for part in version.split("."): + if not part.isnumeric(): + return False + + return True + + @classmethod @not_allowed_in_seedsigner_os def override_data(cls, **kwargs): diff --git a/src/seedsigner/views/settings_views.py b/src/seedsigner/views/settings_views.py index 1c7fcc13..a8adb46f 100644 --- a/src/seedsigner/views/settings_views.py +++ b/src/seedsigner/views/settings_views.py @@ -333,10 +333,8 @@ class VersionView(View): version_fork = Version.get_version_fork() short_commit_hash = Version.get_short_commit_hash() - print(f"{version_fork=}, {short_commit_hash=}") - - if version_fork and version_fork.lower() == "seedsigner": - # Don't display fork name or commit hash for the main repo + if Version.is_release_image(): + # Don't display fork name or commit hash for release images version_fork = None short_commit_hash = None diff --git a/tests/test_version.py b/tests/test_version.py index 7530563e..3f7cff37 100644 --- a/tests/test_version.py +++ b/tests/test_version.py @@ -353,6 +353,10 @@ class TestVersionUtils_GithubActions(VersionBaseTest): with pytest.raises(Exception): VersionUtils.get_version_name() + # Github Actions CI logic should gracefully handle missing SHA data, even + # if it's an impossible / unlikely scenario. + assert VersionUtils.get_short_commit_hash() is None + def test_is_github_actions_ci(self): """ @@ -1010,6 +1014,66 @@ class TestVersion(VersionBaseTest): Version.get_version_timestamp() == TEST__VERSION_TIMESTAMP + def test_is_release_image(self): + """ + Should return True if the heuristic checks indicate this is a release image. + """ + self.write_test_version_file() + + def change_version_data(changes_dict): + # Can only call override_data() when NOT in SeedSigner OS; temporarily patch + # it out. + with patch("seedsigner.models.settings.Settings.HOSTNAME", "not-seedsigner-os"): + Version.override_data(**changes_dict) + + # Must be running in SeedSigner OS + with patch("seedsigner.models.settings.Settings.HOSTNAME", "not-seedsigner-os"): + assert Version.is_release_image() is False + + with patch("seedsigner.models.settings.Settings.HOSTNAME", Settings.SEEDSIGNER_OS): + # Not from the main repo + for fork_name in [ + "some-fork", + "AnotherRepo", + "seedsigner-someone_else", + "seedsigner123" + ]: + change_version_data({ + VersionUtils.VERSIONFILE_ATTR__FORK: fork_name, + }) + assert Version.is_release_image() is False + + # Reset to the main repo + change_version_data({ + VersionUtils.VERSIONFILE_ATTR__FORK: "SeedSigner", + }) + + # Non-semantic version names + for version_name in [ + "some-branch-name", + "dev", + "name.with.dots", + "version_1_2_3", + "v1.hah.fooled.you", + "v1.2.3-rc1", # only fully "clean" semantic versions count as releases + ]: + change_version_data({ + VersionUtils.VERSIONFILE_ATTR__NAME: version_name, + }) + assert Version.is_release_image() is False + + # Semantic versions pass + for version_name in [ + "v0.8.5", + "v1.0", + "v10.20.30", + ]: + change_version_data({ + VersionUtils.VERSIONFILE_ATTR__NAME: version_name, + }) + assert Version.is_release_image() is True + + def test_override_data(self, mock_popen: Mock): """ Test that we can override the version data via the Version.override_version_data()