Skip to content

Commit fea4be0

Browse files
authored
Merge pull request #4904 from boegel/det_pypkg_version
prefer using `importlib.metadata` over the deprecated `pkg_resources` in `det_pypkg_version`
2 parents 8e6079e + c01cc59 commit fea4be0

File tree

4 files changed

+52
-13
lines changed

4 files changed

+52
-13
lines changed

.github/workflows/container_tests.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -97,7 +97,7 @@ jobs:
9797
# see https://docs.easybuild.io/en/latest/Containers.html
9898
curl -OL https://raw.githubusercontent.com/easybuilders/easybuild-easyconfigs/develop/easybuild/easyconfigs/b/bzip2/bzip2-1.0.8.eb
9999
export EASYBUILD_CONTAINERPATH=$PWD
100-
export EASYBUILD_CONTAINER_CONFIG='bootstrap=docker,from=ghcr.io/easybuilders/centos-7.9-python3-amd64'
100+
export EASYBUILD_CONTAINER_CONFIG='bootstrap=docker,from=ghcr.io/easybuilders/rockylinux-8.10-amd64'
101101
eb bzip2-1.0.8.eb --containerize --experimental --container-build-image
102102
singularity exec bzip2-1.0.8.sif command -v bzip2 | grep '/app/software/bzip2/1.0.8/bin/bzip2' || (echo "Path to bzip2 '$which_bzip2' is not correct" && exit 1)
103103
singularity exec bzip2-1.0.8.sif bzip2 --help

.github/workflows/container_tests_apptainer.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -91,7 +91,7 @@ jobs:
9191
# see https://docs.easybuild.io/en/latest/Containers.html
9292
curl -OL https://raw.githubusercontent.com/easybuilders/easybuild-easyconfigs/develop/easybuild/easyconfigs/b/bzip2/bzip2-1.0.8.eb
9393
export EASYBUILD_CONTAINERPATH=$PWD
94-
export EASYBUILD_CONTAINER_CONFIG='bootstrap=docker,from=ghcr.io/easybuilders/centos-7.9-python3-amd64'
94+
export EASYBUILD_CONTAINER_CONFIG='bootstrap=docker,from=ghcr.io/easybuilders/rockylinux-8.10-amd64'
9595
export EASYBUILD_CONTAINER_TYPE='apptainer'
9696
eb bzip2-1.0.8.eb --containerize --experimental --container-build-image
9797
apptainer exec bzip2-1.0.8.sif command -v bzip2 | grep '/app/software/bzip2/1.0.8/bin/bzip2' || (echo "Path to bzip2 '$which_bzip2' is not correct" && exit 1)

easybuild/tools/systemtools.py

Lines changed: 36 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -56,11 +56,20 @@
5656
# pkg_resources is provided by the setuptools Python package,
5757
# which we really want to keep as an *optional* dependency
5858
try:
59-
import pkg_resources
59+
# catch & ignore deprecation warning when importing pkg_resources produced by setuptools
60+
with warnings.catch_warnings():
61+
warnings.simplefilter("ignore", UserWarning)
62+
import pkg_resources
6063
HAVE_PKG_RESOURCES = True
6164
except ImportError:
6265
HAVE_PKG_RESOURCES = False
6366

67+
# importlib.metadata only available in Python 3.10+ (which we take into account when using it)
68+
try:
69+
import importlib.metadata
70+
except ImportError:
71+
pass
72+
6473
try:
6574
# only needed on macOS, may not be available on Linux
6675
import ctypes.macholib.dyld
@@ -1467,17 +1476,38 @@ def det_pypkg_version(pkg_name, imported_pkg, import_name=None):
14671476

14681477
version = None
14691478

1470-
if HAVE_PKG_RESOURCES:
1479+
# prefer using importlib.metadata, since pkg_resources is deprecated since setuptools v68.0.0
1480+
# and is scheduled to be removed in November 2025; see also https://github.com/pypa/setuptools/pull/5007
1481+
1482+
raised_error = None
1483+
1484+
# figure out which function to use to determine module/package version,
1485+
# and which error may be raised if the name is unknown
1486+
if check_python_version() >= (3, 10):
1487+
1488+
def _get_version(name):
1489+
return importlib.metadata.version(name)
1490+
1491+
raised_error = importlib.metadata.PackageNotFoundError
1492+
1493+
elif HAVE_PKG_RESOURCES:
1494+
1495+
def _get_version(name):
1496+
return pkg_resources.get_distribution(name).version
1497+
1498+
raised_error = pkg_resources.DistributionNotFound
1499+
1500+
if raised_error is not None:
14711501
if import_name:
14721502
try:
1473-
version = pkg_resources.get_distribution(import_name).version
1474-
except pkg_resources.DistributionNotFound as err:
1503+
version = _get_version(import_name)
1504+
except raised_error as err:
14751505
_log.debug("%s Python package not found: %s", import_name, err)
14761506

14771507
if version is None:
14781508
try:
1479-
version = pkg_resources.get_distribution(pkg_name).version
1480-
except pkg_resources.DistributionNotFound as err:
1509+
version = _get_version(pkg_name)
1510+
except raised_error as err:
14811511
_log.debug("%s Python package not found: %s", pkg_name, err)
14821512

14831513
if version is None:

test/framework/systemtools.py

Lines changed: 14 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -49,11 +49,12 @@
4949
from easybuild.tools.systemtools import CPU_VENDORS, AMD, APM, ARM, CAVIUM, IBM, INTEL
5050
from easybuild.tools.systemtools import MAX_FREQ_FP, PROC_CPUINFO_FP, PROC_MEMINFO_FP
5151
from easybuild.tools.systemtools import check_linked_shared_libs, check_os_dependency, check_python_version
52-
from easybuild.tools.systemtools import det_parallelism, get_avail_core_count, get_cuda_object_dump_raw
53-
from easybuild.tools.systemtools import get_cuda_architectures, get_cpu_arch_name, get_cpu_architecture
54-
from easybuild.tools.systemtools import get_cpu_family, get_cpu_features, get_cpu_model, get_cpu_speed, get_cpu_vendor
55-
from easybuild.tools.systemtools import get_gcc_version, get_glibc_version, get_os_type, get_os_name, get_os_version
56-
from easybuild.tools.systemtools import get_platform_name, get_shared_lib_ext, get_system_info, get_total_memory
52+
from easybuild.tools.systemtools import det_parallelism, det_pypkg_version, get_avail_core_count
53+
from easybuild.tools.systemtools import get_cuda_object_dump_raw, get_cuda_architectures, get_cpu_arch_name
54+
from easybuild.tools.systemtools import get_cpu_architecture, get_cpu_family, get_cpu_features, get_cpu_model
55+
from easybuild.tools.systemtools import get_cpu_speed, get_cpu_vendor, get_gcc_version, get_glibc_version, get_os_type
56+
from easybuild.tools.systemtools import get_os_name, get_os_version, get_platform_name, get_shared_lib_ext
57+
from easybuild.tools.systemtools import get_system_info, get_total_memory
5758
from easybuild.tools.systemtools import find_library_path, locate_solib, pick_dep_version, pick_system_specific_value
5859

5960

@@ -1117,6 +1118,14 @@ def test_pick_dep_version(self):
11171118
error_pattern = r"Unknown value type for version: .* \(1.23\), should be string value"
11181119
self.assertErrorRegex(EasyBuildError, error_pattern, pick_dep_version, 1.23)
11191120

1121+
def test_det_pypkg_version(self):
1122+
"""Test det_pypkg_version function."""
1123+
self.assertIsNone(det_pypkg_version('doesnotexist', 'doesnotexist.foo'))
1124+
1125+
rich_ver = det_pypkg_version('rich', 'rich')
1126+
regex = re.compile(r'^[0-9]+\.[0-9].*')
1127+
self.assertTrue(regex.match(rich_ver), f"Pattern {regex.pattern} should match for: {rich_ver}")
1128+
11201129
def test_pick_system_specific_value(self):
11211130
"""Test pick_system_specific_value function."""
11221131

0 commit comments

Comments
 (0)