mirror of
https://github.com/PyCQA/flake8.git
synced 2026-04-15 00:44:44 +00:00
Handle determining plugin versions and names
Since we now treat pep8 checks each as an individual plugin, we need a way to represent pep8 as a single plugin in the version output (like we currently do). As such we need to be a bit wiser in how we tell the OptionManager about plugins and their versions and we only do this for certain plugins.
This commit is contained in:
parent
44d994dab9
commit
abdc957f17
3 changed files with 97 additions and 15 deletions
|
|
@ -282,6 +282,7 @@ class Application(object):
|
||||||
# type: () -> NoneType
|
# type: () -> NoneType
|
||||||
"""Register options provided by plugins to our option manager."""
|
"""Register options provided by plugins to our option manager."""
|
||||||
self.check_plugins.register_options(self.option_manager)
|
self.check_plugins.register_options(self.option_manager)
|
||||||
|
self.check_plugins.register_plugin_versions(self.option_manager)
|
||||||
self.listening_plugins.register_options(self.option_manager)
|
self.listening_plugins.register_options(self.option_manager)
|
||||||
self.formatting_plugins.register_options(self.option_manager)
|
self.formatting_plugins.register_options(self.option_manager)
|
||||||
|
|
||||||
|
|
|
||||||
|
|
@ -167,7 +167,7 @@ class OptionManager(object):
|
||||||
@staticmethod
|
@staticmethod
|
||||||
def format_plugin(plugin_tuple):
|
def format_plugin(plugin_tuple):
|
||||||
"""Convert a plugin tuple into a dictionary mapping name to value."""
|
"""Convert a plugin tuple into a dictionary mapping name to value."""
|
||||||
return dict(zip(["entry", "name", "version"], plugin_tuple))
|
return dict(zip(["name", "version"], plugin_tuple))
|
||||||
|
|
||||||
def add_option(self, *args, **kwargs):
|
def add_option(self, *args, **kwargs):
|
||||||
"""Create and register a new option.
|
"""Create and register a new option.
|
||||||
|
|
@ -213,7 +213,7 @@ class OptionManager(object):
|
||||||
|
|
||||||
def generate_epilog(self):
|
def generate_epilog(self):
|
||||||
"""Create an epilog with the version and name of each of plugin."""
|
"""Create an epilog with the version and name of each of plugin."""
|
||||||
plugin_version_format = '%(name)s(%(entry)s): %(version)s'
|
plugin_version_format = '%(name)s: %(version)s'
|
||||||
self.parser.epilog = 'Installed plugins: ' + self.generate_versions(
|
self.parser.epilog = 'Installed plugins: ' + self.generate_versions(
|
||||||
plugin_version_format
|
plugin_version_format
|
||||||
)
|
)
|
||||||
|
|
@ -229,17 +229,13 @@ class OptionManager(object):
|
||||||
|
|
||||||
return options, xargs
|
return options, xargs
|
||||||
|
|
||||||
def register_plugin(self, entry_point_name, name, version):
|
def register_plugin(self, name, version):
|
||||||
"""Register a plugin relying on the OptionManager.
|
"""Register a plugin relying on the OptionManager.
|
||||||
|
|
||||||
:param str entry_point_name:
|
|
||||||
The name of the entry-point loaded with pkg_resources. For
|
|
||||||
example, if the entry-point looks like: ``C90 = mccabe.Checker``
|
|
||||||
then the ``entry_point_name`` would be ``C90``.
|
|
||||||
:param str name:
|
:param str name:
|
||||||
The name of the checker itself. This will be the ``name``
|
The name of the checker itself. This will be the ``name``
|
||||||
attribute of the class or function loaded from the entry-point.
|
attribute of the class or function loaded from the entry-point.
|
||||||
:param str version:
|
:param str version:
|
||||||
The version of the checker that we're using.
|
The version of the checker that we're using.
|
||||||
"""
|
"""
|
||||||
self.registered_plugins.add((entry_point_name, name, version))
|
self.registered_plugins.add((name, version))
|
||||||
|
|
|
||||||
|
|
@ -18,6 +18,8 @@ __all__ = (
|
||||||
'ReportFormatters',
|
'ReportFormatters',
|
||||||
)
|
)
|
||||||
|
|
||||||
|
NO_GROUP_FOUND = object()
|
||||||
|
|
||||||
|
|
||||||
class Plugin(object):
|
class Plugin(object):
|
||||||
"""Wrap an EntryPoint from setuptools and other logic."""
|
"""Wrap an EntryPoint from setuptools and other logic."""
|
||||||
|
|
@ -36,6 +38,9 @@ class Plugin(object):
|
||||||
self.entry_point = entry_point
|
self.entry_point = entry_point
|
||||||
self._plugin = None
|
self._plugin = None
|
||||||
self._parameters = None
|
self._parameters = None
|
||||||
|
self._group = None
|
||||||
|
self._plugin_name = None
|
||||||
|
self._version = None
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
"""Provide an easy to read description of the current plugin."""
|
"""Provide an easy to read description of the current plugin."""
|
||||||
|
|
@ -43,6 +48,28 @@ class Plugin(object):
|
||||||
self.name, self.entry_point
|
self.name, self.entry_point
|
||||||
)
|
)
|
||||||
|
|
||||||
|
def is_in_a_group(self):
|
||||||
|
"""Determine if this plugin is in a group.
|
||||||
|
|
||||||
|
:returns:
|
||||||
|
True if the plugin is in a group, otherwise False.
|
||||||
|
:rtype:
|
||||||
|
bool
|
||||||
|
"""
|
||||||
|
return self.group() is not None
|
||||||
|
|
||||||
|
def group(self):
|
||||||
|
"""Find and parse the group the plugin is in."""
|
||||||
|
if self._group is None:
|
||||||
|
name = self.name.split('.', 1)
|
||||||
|
if len(name) > 1:
|
||||||
|
self._group = name[0]
|
||||||
|
else:
|
||||||
|
self._group = NO_GROUP_FOUND
|
||||||
|
if self._group is NO_GROUP_FOUND:
|
||||||
|
return None
|
||||||
|
return self._group
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def parameters(self):
|
def parameters(self):
|
||||||
"""List of arguments that need to be passed to the plugin."""
|
"""List of arguments that need to be passed to the plugin."""
|
||||||
|
|
@ -61,8 +88,25 @@ class Plugin(object):
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def version(self):
|
def version(self):
|
||||||
"""Return the version attribute on the plugin."""
|
"""Return the version of the plugin."""
|
||||||
return self.plugin.version
|
if self._version is None:
|
||||||
|
if self.is_in_a_group():
|
||||||
|
self._version = version_for(self)
|
||||||
|
else:
|
||||||
|
self._version = self.plugin.version
|
||||||
|
|
||||||
|
return self._version
|
||||||
|
|
||||||
|
@property
|
||||||
|
def plugin_name(self):
|
||||||
|
"""Return the name of the plugin."""
|
||||||
|
if self._plugin_name is None:
|
||||||
|
if self.is_in_a_group():
|
||||||
|
self._plugin_name = self.group()
|
||||||
|
else:
|
||||||
|
self._plugin_name = self.plugin.name
|
||||||
|
|
||||||
|
return self._plugin_name
|
||||||
|
|
||||||
def execute(self, *args, **kwargs):
|
def execute(self, *args, **kwargs):
|
||||||
r"""Call the plugin with \*args and \*\*kwargs."""
|
r"""Call the plugin with \*args and \*\*kwargs."""
|
||||||
|
|
@ -136,11 +180,6 @@ class Plugin(object):
|
||||||
self.name, optmanager
|
self.name, optmanager
|
||||||
)
|
)
|
||||||
add_options(optmanager)
|
add_options(optmanager)
|
||||||
optmanager.register_plugin(
|
|
||||||
entry_point_name=self.name,
|
|
||||||
name=self.plugin.name,
|
|
||||||
version=self.plugin.version
|
|
||||||
)
|
|
||||||
|
|
||||||
|
|
||||||
class PluginManager(object): # pylint: disable=too-few-public-methods
|
class PluginManager(object): # pylint: disable=too-few-public-methods
|
||||||
|
|
@ -193,6 +232,46 @@ class PluginManager(object): # pylint: disable=too-few-public-methods
|
||||||
for name in self.names:
|
for name in self.names:
|
||||||
yield func(self.plugins[name], *args, **kwargs)
|
yield func(self.plugins[name], *args, **kwargs)
|
||||||
|
|
||||||
|
def versions(self):
|
||||||
|
# () -> (str, str)
|
||||||
|
"""Generate the versions of plugins.
|
||||||
|
|
||||||
|
:returns:
|
||||||
|
Tuples of the plugin_name and version
|
||||||
|
:rtype:
|
||||||
|
tuple
|
||||||
|
"""
|
||||||
|
plugins_seen = set()
|
||||||
|
for entry_point_name in self.names:
|
||||||
|
plugin = self.plugins[entry_point_name]
|
||||||
|
plugin_name = plugin.plugin_name
|
||||||
|
if plugin.plugin_name in plugins_seen:
|
||||||
|
continue
|
||||||
|
plugins_seen.add(plugin_name)
|
||||||
|
yield (plugin_name, plugin.version)
|
||||||
|
|
||||||
|
|
||||||
|
def version_for(plugin):
|
||||||
|
# (Plugin) -> Union[str, NoneType]
|
||||||
|
"""Determine the version of a plugin by it's module.
|
||||||
|
|
||||||
|
:param plugin:
|
||||||
|
The loaded plugin
|
||||||
|
:type plugin:
|
||||||
|
Plugin
|
||||||
|
:returns:
|
||||||
|
version string for the module
|
||||||
|
:rtype:
|
||||||
|
str
|
||||||
|
"""
|
||||||
|
module_name = plugin.plugin.__module__
|
||||||
|
try:
|
||||||
|
module = __import__(module_name)
|
||||||
|
except ImportError:
|
||||||
|
return None
|
||||||
|
|
||||||
|
return getattr(module, '__version__', None)
|
||||||
|
|
||||||
|
|
||||||
class PluginTypeManager(object):
|
class PluginTypeManager(object):
|
||||||
"""Parent class for most of the specific plugin types."""
|
"""Parent class for most of the specific plugin types."""
|
||||||
|
|
@ -264,6 +343,12 @@ class PluginTypeManager(object):
|
||||||
self.plugins_loaded = True
|
self.plugins_loaded = True
|
||||||
return plugins
|
return plugins
|
||||||
|
|
||||||
|
def register_plugin_versions(self, optmanager):
|
||||||
|
"""Register the plugins and their versions with the OptionManager."""
|
||||||
|
self.load_plugins()
|
||||||
|
for (plugin_name, version) in self.manager.versions():
|
||||||
|
optmanager.register_plugin(name=plugin_name, version=version)
|
||||||
|
|
||||||
def register_options(self, optmanager):
|
def register_options(self, optmanager):
|
||||||
"""Register all of the checkers' options to the OptionManager."""
|
"""Register all of the checkers' options to the OptionManager."""
|
||||||
self.load_plugins()
|
self.load_plugins()
|
||||||
|
|
|
||||||
Loading…
Add table
Add a link
Reference in a new issue