Skip to content

Commit

Permalink
Switch to importlib-metadata (#199)
Browse files Browse the repository at this point in the history
Switch to importlib-metadata
  • Loading branch information
nicoddemus committed May 5, 2019
2 parents 4de9e44 + 0706fba commit 8749791
Show file tree
Hide file tree
Showing 5 changed files with 56 additions and 72 deletions.
2 changes: 1 addition & 1 deletion appveyor.yml
Original file line number Diff line number Diff line change
Expand Up @@ -31,7 +31,7 @@ install:
build: false # Not a C# project, build stuff at the test step instead.

test_script:
- C:\Python35\python -m tox
- C:\Python35\Scripts\tox

# We don't deploy anything on tags with AppVeyor, we use Travis instead, so we
# might as well save resources
Expand Down
9 changes: 4 additions & 5 deletions docs/conf.py
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# -*- coding: utf-8 -*-
import pkg_resources
import importlib_metadata


extensions = [
Expand All @@ -20,14 +20,13 @@

# General information about the project.

dist = pkg_resources.get_distribution("pluggy")
project = dist.project_name
project = "pluggy"
copyright = u"2016, Holger Krekel"
author = "Holger Krekel"

release = dist.version
release = importlib_metadata.version(project)
# The short X.Y version.
version = u".".join(dist.version.split(".")[:2])
version = u".".join(release.split(".")[:2])


language = None
Expand Down
50 changes: 29 additions & 21 deletions pluggy/manager.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,6 +3,8 @@
from .hooks import HookImpl, _HookRelay, _HookCaller, normalize_hookimpl_opts
import warnings

import importlib_metadata


def _warn_for_function(warning, function):
warnings.warn_explicit(
Expand All @@ -25,6 +27,23 @@ def __init__(self, plugin, message):
super(Exception, self).__init__(message)


class DistFacade(object):
"""Emulate a pkg_resources Distribution"""

def __init__(self, dist):
self._dist = dist

@property
def project_name(self):
return self.metadata["name"]

def __getattr__(self, attr, default=None):
return getattr(self._dist, attr, default)

def __dir__(self):
return sorted(dir(self._dist) + ["_dist", "project_name"])


class PluginManager(object):
""" Core Pluginmanager class which manages registration
of plugin objects and 1:N hook calling.
Expand Down Expand Up @@ -259,29 +278,18 @@ def load_setuptools_entrypoints(self, group, name=None):
:rtype: int
:return: return the number of loaded plugins by this call.
"""
from pkg_resources import (
iter_entry_points,
DistributionNotFound,
VersionConflict,
)

count = 0
for ep in iter_entry_points(group, name=name):
# is the plugin registered or blocked?
if self.get_plugin(ep.name) or self.is_blocked(ep.name):
continue
try:
for dist in importlib_metadata.distributions():
for ep in dist.entry_points:
if ep.group != group or (name is not None and ep.name != name):
continue
# is the plugin registered or blocked?
if self.get_plugin(ep.name) or self.is_blocked(ep.name):
continue
plugin = ep.load()
except DistributionNotFound:
continue
except VersionConflict as e:
raise PluginValidationError(
plugin=None,
message="Plugin %r could not be loaded: %s!" % (ep.name, e),
)
self.register(plugin, name=ep.name)
self._plugin_distinfo.append((plugin, ep.dist))
count += 1
self.register(plugin, name=ep.name)
self._plugin_distinfo.append((plugin, DistFacade(dist)))
count += 1
return count

def list_plugin_distinfo(self):
Expand Down
1 change: 1 addition & 0 deletions setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ def main():
author_email="holger@merlinux.eu",
url="https://github.com/pytest-dev/pluggy",
python_requires=">=2.7, !=3.0.*, !=3.1.*, !=3.2.*, !=3.3.*",
install_requires=["importlib-metadata>=0.9"],
extras_require={"dev": ["pre-commit", "tox"]},
classifiers=classifiers,
packages=["pluggy"],
Expand Down
66 changes: 21 additions & 45 deletions testing/test_pluginmanager.py
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,7 @@
"""
import pytest
import types
import sys
import importlib_metadata
from pluggy import (
PluginManager,
PluginValidationError,
Expand Down Expand Up @@ -447,64 +447,40 @@ def example_hook():


def test_load_setuptools_instantiation(monkeypatch, pm):
pkg_resources = pytest.importorskip("pkg_resources")
class EntryPoint(object):
name = "myname"
group = "hello"
value = "myname:foo"

def my_iter(group, name=None):
assert group == "hello"
def load(self):
class PseudoPlugin(object):
x = 42

class EntryPoint(object):
name = "myname"
dist = None
return PseudoPlugin()

def load(self):
class PseudoPlugin(object):
x = 42
class Distribution(object):
entry_points = (EntryPoint(),)

return PseudoPlugin()
dist = Distribution()

return iter([EntryPoint()])
def my_distributions():
return (dist,)

monkeypatch.setattr(pkg_resources, "iter_entry_points", my_iter)
monkeypatch.setattr(importlib_metadata, "distributions", my_distributions)
num = pm.load_setuptools_entrypoints("hello")
assert num == 1
plugin = pm.get_plugin("myname")
assert plugin.x == 42
assert pm.list_plugin_distinfo() == [(plugin, None)]
ret = pm.list_plugin_distinfo()
# poor man's `assert ret == [(plugin, mock.ANY)]`
assert len(ret) == 1
assert len(ret[0]) == 2
assert ret[0][0] == plugin
assert ret[0][1]._dist == dist
num = pm.load_setuptools_entrypoints("hello")
assert num == 0 # no plugin loaded by this call


def test_load_setuptools_version_conflict(monkeypatch, pm):
"""Check that we properly handle a VersionConflict problem when loading entry points"""
pkg_resources = pytest.importorskip("pkg_resources")

def my_iter(group, name=None):
assert group == "hello"

class EntryPoint(object):
name = "myname"
dist = None

def load(self):
raise pkg_resources.VersionConflict("Some conflict")

return iter([EntryPoint()])

monkeypatch.setattr(pkg_resources, "iter_entry_points", my_iter)
with pytest.raises(
PluginValidationError,
match="Plugin 'myname' could not be loaded: Some conflict!",
):
pm.load_setuptools_entrypoints("hello")


def test_load_setuptools_not_installed(monkeypatch, pm):
monkeypatch.setitem(sys.modules, "pkg_resources", types.ModuleType("pkg_resources"))

with pytest.raises(ImportError):
pm.load_setuptools_entrypoints("qwe")


def test_add_tracefuncs(he_pm):
out = []

Expand Down

0 comments on commit 8749791

Please sign in to comment.