From ee8afc91ea39612ed989af77a8009458bf85e966 Mon Sep 17 00:00:00 2001 From: Harvey Lynden Date: Tue, 10 Dec 2024 13:38:43 +0100 Subject: [PATCH] Fix image pattern for FedoraSecondary provider on s390x Updated the image pattern in FedoraSecondaryImageProvider to match the available Fedora image file names for the s390x architecture. This resolves the issue where the vmimage utility could not download the correct image due to a pattern mismatch. Reference: https://github.com/avocado-framework/avocado/issues/6071 Signed-off-by: Harvey Lynden --- avocado/utils/vmimage.py | 14 ++++++++-- selftests/check.py | 2 +- selftests/unit/plugin/vmimage.py | 46 ++++++++++++++++++++++++++++---- selftests/unit/utils/vmimage.py | 22 +++++++++++++-- 4 files changed, 74 insertions(+), 10 deletions(-) diff --git a/avocado/utils/vmimage.py b/avocado/utils/vmimage.py index df3da973b0..8219ef205f 100644 --- a/avocado/utils/vmimage.py +++ b/avocado/utils/vmimage.py @@ -235,7 +235,10 @@ def __init__(self, version="[0-9]+", build="[0-9]+.[0-9]+", arch=DEFAULT_ARCH): self.url_old_images = ( "https://archives.fedoraproject.org/pub/archive/fedora/linux/releases/" ) - self.image_pattern = "Fedora-Cloud-Base-(?P{version})-(?P{build}).(?P{arch}).qcow2$" + if int(self.version) >= 40: + self.image_pattern = "Fedora-Cloud-Base-Generic-(?P{version})-(?P{build}).(?P{arch}).qcow2$" + else: + self.image_pattern = "Fedora-Cloud-Base-(?P{version})-(?P{build}).(?P{arch}).qcow2$" class FedoraSecondaryImageProvider(FedoraImageProviderBase): @@ -254,7 +257,10 @@ def __init__(self, version="[0-9]+", build="[0-9]+.[0-9]+", arch=DEFAULT_ARCH): self.url_old_images = ( "https://archives.fedoraproject.org/pub/archive/fedora-secondary/releases/" ) - self.image_pattern = "Fedora-Cloud-Base-(?P{version})-(?P{build}).(?P{arch}).qcow2$" + if int(self.version) >= 40: + self.image_pattern = "Fedora-Cloud-Base-Generic-(?P{version})-(?P{build}).(?P{arch}).qcow2$" + else: + self.image_pattern = "Fedora-Cloud-Base-(?P{version})-(?P{build}).(?P{arch}).qcow2$" class CentOSImageProvider(ImageProviderBase): @@ -585,6 +591,7 @@ def download(self): cache_dirs = [self.cache_dir] else: cache_dirs = self.cache_dir + LOG.debug("Attempting to download image from URL: %s", self.url) asset_path = asset.Asset( name=self.url, asset_hash=self.checksum, @@ -657,6 +664,9 @@ def from_parameters( :returns: Image instance that can provide the image according to the parameters. """ + # Use the current system architecture if arch is not provided + if arch is None: + arch = DEFAULT_ARCH provider = get_best_provider(name, version, build, arch) if cache_dir is None: diff --git a/selftests/check.py b/selftests/check.py index 456df573e1..9059b120d5 100755 --- a/selftests/check.py +++ b/selftests/check.py @@ -27,7 +27,7 @@ "job-api-check-tmp-directory-exists": 1, "nrunner-interface": 70, "nrunner-requirement": 28, - "unit": 681, + "unit": 682, "jobs": 11, "functional-parallel": 314, "functional-serial": 7, diff --git a/selftests/unit/plugin/vmimage.py b/selftests/unit/plugin/vmimage.py index d664ec2d9a..ecacb6bb16 100644 --- a/selftests/unit/plugin/vmimage.py +++ b/selftests/unit/plugin/vmimage.py @@ -63,6 +63,25 @@ class VMImagePlugin(unittest.TestCase): + def _configure_provider(self, provider_class, expected_images): + """Configure a provider with the correct version information.""" + with unittest.mock.patch.object( + provider_class, "get_version", return_value="30" + ): + provider = provider_class() + provider._best_version = "30" + + # Find matching image config + for image in expected_images: + if image["name"] == provider.name: + provider._best_version = image["mock_version"] + provider.get_version = unittest.mock.Mock( + return_value=image["mock_version"] + ) + break + + return provider + def _get_temporary_dirs_mapping_and_config(self): """ Creates a temporary bogus base data dir @@ -99,20 +118,28 @@ def _create_test_files(self, urlopen_mock): "name": "Fedora", "file": "Fedora-Cloud-Base-{version}-{build}.{arch}.qcow2", "url": FEDORA_PAGE, + "mock_version": "30", }, { "name": "JeOS", "file": "jeos-{version}-{arch}.qcow2.xz", "url": JEOS_PAGE, + "mock_version": "27", }, { "name": "CirrOS", "file": "cirros-{version}-{arch}-disk.img", "url": CIRROS_PAGE, + "mock_version": "0.4.0", }, ] cache_dir = self.mapping.get("cache_dirs")[0] - providers = [provider() for provider in vmimage_util.list_providers()] + + providers = [] + for provider_class in vmimage_util.list_providers(): + + provider = self._configure_provider(provider_class, expected_images) + providers.append(provider) for provider in providers: for image in expected_images: @@ -156,10 +183,19 @@ def test_list_downloaded_images(self): with unittest.mock.patch("avocado.core.data_dir.settings", self.stg): with unittest.mock.patch( "avocado.utils.vmimage.ImageProviderBase.get_version" - ): - images = sorted( - vmimage_plugin.list_downloaded_images(), key=lambda i: i["name"] - ) + ) as mock_base_version: + mock_base_version.return_value = "30" + with unittest.mock.patch( + "avocado.utils.vmimage.FedoraImageProvider.get_image_parameters" + ) as mock_get_params: + mock_get_params.return_value = { + "version": "30", + "build": "1234", + "arch": "x86_64", + } + images = sorted( + vmimage_plugin.list_downloaded_images(), key=lambda i: i["name"] + ) for index, image in enumerate(images): for key in image: self.assertEqual( diff --git a/selftests/unit/utils/vmimage.py b/selftests/unit/utils/vmimage.py index 3bd80ea881..10b11998bc 100644 --- a/selftests/unit/utils/vmimage.py +++ b/selftests/unit/utils/vmimage.py @@ -508,6 +508,7 @@ class FedoraImageProvider(unittest.TestCase): [DIR] 28/ 2019-09-02 20:37 - [DIR] 29/ 2018-10-26 17:27 - [DIR] 30/ 2019-04-26 20:58 - +[DIR] 40/ 2023-04-26 20:58 - [DIR] 7/ 2016-05-21 03:28 - [DIR] 8/ 2016-05-21 02:12 - [DIR] 9/ 2013-04-25 08:48 - @@ -516,14 +517,14 @@ class FedoraImageProvider(unittest.TestCase): """ @unittest.mock.patch("avocado.utils.vmimage.urlopen") - def test_get_image_parameters_match(self, urlopen_mock): + def test_get_image_parameters_match_pre_40(self, urlopen_mock): expected_version = "30" expected_arch = "x86_64" expected_build = "1234" urlread_mocked = unittest.mock.Mock(return_value=self.VERSION_LISTING) urlopen_mock.return_value = unittest.mock.Mock(read=urlread_mocked) provider = vmimage.FedoraImageProvider( - expected_version, expected_build, expected_arch + version=expected_version, build=expected_build, arch=expected_arch ) image = f"Fedora-Cloud-Base-{expected_version}-{expected_build}.{expected_arch}.qcow2" parameters = provider.get_image_parameters(image) @@ -531,6 +532,22 @@ def test_get_image_parameters_match(self, urlopen_mock): self.assertEqual(expected_build, parameters["build"]) self.assertEqual(expected_arch, parameters["arch"]) + @unittest.mock.patch("avocado.utils.vmimage.urlopen") + def test_get_image_parameters_match_post_40(self, urlopen_mock): + expected_version = "40" + expected_arch = "x86_64" + expected_build = "1234" + urlread_mocked = unittest.mock.Mock(return_value=self.VERSION_LISTING) + urlopen_mock.return_value = unittest.mock.Mock(read=urlread_mocked) + provider = vmimage.FedoraImageProvider( + version=expected_version, build=expected_build, arch=expected_arch + ) + image = f"Fedora-Cloud-Base-Generic-{expected_version}-{expected_build}.{expected_arch}.qcow2" + parameters = provider.get_image_parameters(image) + self.assertEqual(expected_version, parameters["version"]) + self.assertEqual(expected_build, parameters["build"]) + self.assertEqual(expected_arch, parameters["arch"]) + @unittest.mock.patch("avocado.utils.vmimage.urlopen") def test_get_image_parameters_not_match(self, urlopen_mock): urlread_mocked = unittest.mock.Mock(return_value=self.VERSION_LISTING) @@ -573,6 +590,7 @@ def test_get_versions(self, urlopen_mock): 28, 29, 30, + 40, 7, 8, 9,