diff --git a/doc/pipeline_simple_intro.rst b/doc/pipeline_simple_intro.rst index 1a2ff4a5402d0b91cc0426076b31cb6d5b9232e7..62df9e4574a2538f7f06c9814ec9ba3c49046038 100644 --- a/doc/pipeline_simple_intro.rst +++ b/doc/pipeline_simple_intro.rst @@ -290,13 +290,13 @@ The command above is equivalent to the following command:: bob.bio.face.config.baseline.iresnet100 This information can be obtained by either inspecting the ``setup.py`` of the -relevant pacakge or using the following code snippet: +relevant package or using the following code snippet: .. code-block:: python - import pkg_resources + import importlib.metadata - for entry_point in pkg_resources.iter_entry_points("bob.bio.config"): + for entry_point in importlib.metadata.entry_points(group="bob.bio.config"): if entry_point.name not in ("atnt", "iresnet100"): continue print(entry_point) diff --git a/src/bob/bio/base/script/bio.py b/src/bob/bio/base/script/bio.py index 8ff90cd48e62e0be08e72baf783c190bb9108106..db470867b56033c44dded94778aba871f741e0ea 100644 --- a/src/bob/bio/base/script/bio.py +++ b/src/bob/bio/base/script/bio.py @@ -1,13 +1,14 @@ """The main entry for bob.bio (click-based) scripts. """ +import importlib.metadata + import click -import pkg_resources from clapper.click import AliasedGroup from click_plugins import with_plugins -@with_plugins(pkg_resources.iter_entry_points("bob.bio.cli")) +@with_plugins(importlib.metadata.entry_points(group="bob.bio.cli")) @click.group(cls=AliasedGroup) def bio(): """Biometric recognition commands.""" diff --git a/src/bob/bio/base/script/pipeline.py b/src/bob/bio/base/script/pipeline.py index dabadd115b5c98aa0958c823993ae04d635a1659..0022ca9350b1e07d32ca43216cc56d9cbca6e5aa 100644 --- a/src/bob/bio/base/script/pipeline.py +++ b/src/bob/bio/base/script/pipeline.py @@ -1,11 +1,12 @@ +import importlib.metadata + import click -import pkg_resources from clapper.click import AliasedGroup from click_plugins import with_plugins -@with_plugins(pkg_resources.iter_entry_points("bob.bio.pipeline.cli")) +@with_plugins(importlib.metadata.entry_points(group="bob.bio.pipeline.cli")) @click.group(cls=AliasedGroup) def pipeline(): """Available pipelines""" diff --git a/src/bob/bio/base/script/vulnerability.py b/src/bob/bio/base/script/vulnerability.py index 6bdbd2f8f7135541668dee31c1c0c81b18aedfd2..23d43e2149f17865f3dd9983dc891c24292ad56a 100644 --- a/src/bob/bio/base/script/vulnerability.py +++ b/src/bob/bio/base/script/vulnerability.py @@ -1,13 +1,14 @@ """The main entry for bob.vuln """ +import importlib.metadata + import click -import pkg_resources from clapper.click import AliasedGroup from click_plugins import with_plugins -@with_plugins(pkg_resources.iter_entry_points("bob.vuln.cli")) +@with_plugins(importlib.metadata.entry_points(group="bob.vuln.cli")) @click.group(cls=AliasedGroup) def vulnerability(): """Vulnerability analysis related commands.""" diff --git a/src/bob/bio/base/utils/resources.py b/src/bob/bio/base/utils/resources.py index 6393d4a440c5ccecb70c38e772b074e29ff44d6d..378c684a978a63a29d98bbe88388030a872ed28c 100644 --- a/src/bob/bio/base/utils/resources.py +++ b/src/bob/bio/base/utils/resources.py @@ -5,11 +5,13 @@ from __future__ import print_function +import importlib.metadata +import importlib.resources import logging -import os + +from pathlib import Path import clapper.config -import pkg_resources logger = logging.getLogger("bob.bio.base") @@ -95,12 +97,18 @@ def read_config_file(filenames, keyword=None): return getattr(config, keyword) -def _get_entry_points(keyword, strip=[], package_prefix="bob.bio."): +def _get_entry_points( + keyword: str, + strip: list[str] | None = None, + package_prefix: str = "bob.bio.", +) -> list[importlib.metadata.EntryPoint]: """Returns the list of entry points for registered resources with the given keyword.""" + if strip is None: + strip = [] return [ entry_point - for entry_point in pkg_resources.iter_entry_points( - package_prefix + keyword + for entry_point in importlib.metadata.entry_points().select( + group=package_prefix + keyword ) if not entry_point.name.startswith(tuple(strip)) ] @@ -145,7 +153,7 @@ def load_resource( """ # first, look if the resource is a file name - if os.path.isfile(resource): + if Path(resource).is_file(): return read_config_file([resource], keyword) if keyword not in valid_keywords: @@ -174,14 +182,14 @@ def load_resource( index = -1 if preferred_package is not None: for i, p in enumerate(entry_points): - if p.dist.project_name == preferred_package: + if p.dist.metadata["name"] == preferred_package: index = i break if index == -1: # by default, use the first one that is not from bob.bio for i, p in enumerate(entry_points): - if not p.dist.project_name.startswith(package_prefix): + if not p.dist.metadata["name"].startswith(package_prefix): index = i break @@ -189,15 +197,15 @@ def load_resource( logger.debug( "RESOURCES: Using the resource '%s' from '%s', and ignoring the one from '%s'", resource, - entry_points[index].module_name, - entry_points[1 - index].module_name, + entry_points[index].module, + entry_points[1 - index].module, ) return entry_points[index].load() else: logger.warn( "Under the desired name '%s', there are multiple entry points defined, we return the first one: %s", resource, - [entry_point.module_name for entry_point in entry_points], + [entry_point.module for entry_point in entry_points], ) return entry_points[0].load() @@ -241,28 +249,37 @@ def extensions(keywords=valid_keywords, package_prefix="bob.bio."): ) ] return sorted( - list(set(entry_point.dist.project_name for entry_point in entry_points)) + list( + set( + entry_point.dist.metadata["name"] + for entry_point in entry_points + ) + ) ) def resource_keys( - keyword, exclude_packages=[], package_prefix="bob.bio.", strip=["dummy"] + keyword, exclude_packages=None, package_prefix="bob.bio.", strip=None ): """Reads and returns all resources that are registered with the given keyword. Entry points from the given ``exclude_packages`` are ignored.""" + if exclude_packages is None: + exclude_packages = [] + if strip is None: + strip = ["dummy"] ret_list = [ entry_point.name for entry_point in _get_entry_points( keyword, strip=strip, package_prefix=package_prefix ) - if entry_point.dist.project_name not in exclude_packages + if entry_point.dist.metadata["name"] not in exclude_packages ] return sorted(ret_list) def list_resources( keyword, - strip=["dummy"], + strip=None, package_prefix="bob.bio.", verbose=False, packages=None, @@ -273,6 +290,8 @@ def list_resources( "The given keyword '%s' is not valid. Please use one of %s!" % (str(keyword), str(valid_keywords)) ) + if strip is None: + strip = ["dummy"] entry_points = _get_entry_points( keyword, strip, package_prefix=package_prefix @@ -289,29 +308,30 @@ def list_resources( entry_points = [ entry_point for entry_point in entry_points - if entry_point.dist.project_name in packages + if entry_point.dist.metadata["name"] in packages ] for entry_point in sorted( - entry_points, key=lambda p: (p.dist.project_name, p.name) + entry_points, key=lambda p: (p.dist.metadata["name"], p.name) ): - if last_dist != str(entry_point.dist): - retval += "\n- %s @ %s: \n" % ( - str(entry_point.dist), - str(entry_point.dist.location), + if last_dist != f"{entry_point.dist.name} {entry_point.dist.version}": + retval += "\n- %s %s @ %s: \n" % ( + entry_point.dist.name, + entry_point.dist.version, + str(entry_point.dist.locate_file("")), ) - last_dist = str(entry_point.dist) + last_dist = f"{entry_point.dist.name} {entry_point.dist.version}" - if len(entry_point.attrs): + if entry_point.attr is not None: retval += " + %s --> %s: %s\n" % ( entry_point.name + " " * (length - len(entry_point.name)), - entry_point.module_name, - entry_point.attrs[0], + entry_point.module, + entry_point.attr, ) else: retval += " + %s --> %s\n" % ( entry_point.name + " " * (length - len(entry_point.name)), - entry_point.module_name, + entry_point.module, ) if verbose: retval += " ==> " + str(entry_point.load()) + "\n\n" @@ -320,9 +340,11 @@ def list_resources( def database_directories( - strip=["dummy"], replacements=None, package_prefix="bob.bio." + strip=None, replacements=None, package_prefix="bob.bio." ): """Returns a dictionary of original directories for all registered databases.""" + if strip is None: + strip = ["dummy"] entry_points = _get_entry_points( "database", strip, package_prefix=package_prefix ) @@ -364,11 +386,13 @@ def get_resource_filename(resource_name, group): """ # Check if it's already a path - if os.path.exists(resource_name): + if Path(resource_name).exists(): return resource_name # If it's a resource get the path of this resource - resources = [r for r in pkg_resources.iter_entry_points(group)] + resources = [ + r for r in importlib.metadata.entry_points().select(group=group) + ] # if resource_name not in [r.name for r in resources]: # raise ValueError(f"Resource not found: `{resource_name}`") @@ -382,9 +406,9 @@ def get_resource_filename(resource_name, group): # TODO: This get the root path only # I don't know how to get the filename - return ( - pkg_resources.resource_filename( - resource.module_name, resource.module_name.split(".")[-1] + containing, _dot, resource_filename = resource.module.rpartition(".") + return str( + importlib.resources.files(containing).joinpath( + resource_filename + ".py" ) - + ".py" )