Merge branch 'remove-application-prelim-option-state' into 'master'

Remove application prelimary option state

See merge request pycqa/flake8!358
This commit is contained in:
Anthony Sottile 2019-10-01 18:34:25 +00:00
commit 0359533fca
4 changed files with 59 additions and 41 deletions

View file

@ -28,12 +28,12 @@ def get_style_guide(**kwargs):
:class:`StyleGuide`
"""
application = app.Application()
application.parse_preliminary_options_and_args([])
flake8.configure_logging(
application.prelim_opts.verbose, application.prelim_opts.output_file
prelim_opts, prelim_args = application.parse_preliminary_options_and_args(
[]
)
application.make_config_finder()
application.find_plugins()
flake8.configure_logging(prelim_opts.verbose, prelim_opts.output_file)
application.make_config_finder(prelim_opts.append_config, prelim_args)
application.find_plugins(prelim_opts.config, prelim_opts.isolated)
application.register_plugin_options()
application.parse_configuration_and_cli([])
# We basically want application.initialize to be called but with these

View file

@ -5,7 +5,7 @@ import argparse
import logging
import sys
import time
from typing import Dict, List, Optional, Set
from typing import Dict, List, Optional, Set, Tuple
import flake8
from flake8 import checker
@ -51,13 +51,8 @@ class Application(object):
prog="flake8", version=flake8.__version__
)
options.register_default_options(self.option_manager)
#: The preliminary options parsed from CLI before plugins are loaded,
#: into a :class:`argparse.Namespace` instance
self.prelim_opts = None # type: argparse.Namespace
#: The preliminary arguments parsed from CLI before plugins are loaded
self.prelim_args = None # type: List[str]
#: The instance of :class:`flake8.options.config.ConfigFileFinder`
self.config_finder = None
self.config_finder = None # type: config.ConfigFileFinder
#: The :class:`flake8.options.config.LocalPlugins` found in config
self.local_plugins = None # type: config.LocalPlugins
@ -98,7 +93,7 @@ class Application(object):
self.parsed_diff = {} # type: Dict[str, Set[int]]
def parse_preliminary_options_and_args(self, argv):
# type: (List[str]) -> None
# type: (List[str]) -> Tuple[argparse.Namespace, List[str]]
"""Get preliminary options and args from CLI, pre-plugin-loading.
We need to know the values of a few standard options and args now, so
@ -108,10 +103,12 @@ class Application(object):
options; we ignore those for now, they'll be parsed later when we do
real option parsing.
Sets self.prelim_opts and self.prelim_args.
:param list argv:
Command-line arguments passed in directly.
:returns:
Populated namespace and list of remaining argument strings.
:rtype:
(argparse.Namespace, list)
"""
# We haven't found or registered our plugins yet, so let's defer
# printing the version until we aggregate options from config files
@ -138,7 +135,7 @@ class Application(object):
opts, args = self.option_manager.parse_known_args(args)
# parse_known_args includes unknown options as args
args = [a for a in args if not a.startswith("-")]
self.prelim_opts, self.prelim_args = opts, args
return opts, args
def exit(self):
# type: () -> None
@ -155,17 +152,22 @@ class Application(object):
(self.result_count > 0) or self.catastrophic_failure
)
def make_config_finder(self):
"""Make our ConfigFileFinder based on preliminary opts and args."""
def make_config_finder(self, append_config, args):
# type: (List[str], List[str]) -> None
"""Make our ConfigFileFinder based on preliminary opts and args.
:param list append_config:
List of configuration files to be parsed for configuration.
:param list args:
The list of file arguments passed from the CLI.
"""
if self.config_finder is None:
self.config_finder = config.ConfigFileFinder(
self.option_manager.program_name,
self.prelim_args,
self.prelim_opts.append_config,
self.option_manager.program_name, args, append_config
)
def find_plugins(self):
# type: () -> None
def find_plugins(self, config_file, ignore_config_files):
# type: (Optional[str], bool) -> None
"""Find and load the plugins for this application.
If :attr:`check_plugins`, or :attr:`formatting_plugins` are ``None``
@ -173,12 +175,17 @@ class Application(object):
instance. Given the expense of finding plugins (via :mod:`entrypoints`)
we want this to be idempotent and so only update those attributes if
they are ``None``.
:param str config_file:
The optional configuraiton file to override all other configuration
files (i.e., the --config option).
:param bool ignore_config_files:
Determine whether to parse configuration files or not. (i.e., the
--isolated option).
"""
if self.local_plugins is None:
self.local_plugins = config.get_local_plugins(
self.config_finder,
self.prelim_opts.config,
self.prelim_opts.isolated,
self.config_finder, config_file, ignore_config_files
)
sys.path.extend(self.local_plugins.paths)
@ -352,12 +359,12 @@ class Application(object):
"""
# NOTE(sigmavirus24): When updating this, make sure you also update
# our legacy API calls to these same methods.
self.parse_preliminary_options_and_args(argv)
flake8.configure_logging(
self.prelim_opts.verbose, self.prelim_opts.output_file
prelim_opts, prelim_args = self.parse_preliminary_options_and_args(
argv
)
self.make_config_finder()
self.find_plugins()
flake8.configure_logging(prelim_opts.verbose, prelim_opts.output_file)
self.make_config_finder(prelim_opts.append_config, prelim_args)
self.find_plugins(prelim_opts.config, prelim_opts.isolated)
self.register_plugin_options()
self.parse_configuration_and_cli(argv)
self.make_formatter()

View file

@ -92,18 +92,18 @@ def test_returns_specified_plugin(application):
def test_prelim_opts_args(application):
"""Verify we get sensible prelim opts and args."""
application.parse_preliminary_options_and_args(
opts, args = application.parse_preliminary_options_and_args(
['flake8', '--foo', '--verbose', 'src', 'setup.py', '--statistics'])
assert application.prelim_opts.statistics
assert application.prelim_opts.verbose
assert application.prelim_args == ['src', 'setup.py']
assert opts.statistics
assert opts.verbose
assert args == ['src', 'setup.py']
def test_prelim_opts_handles_empty(application):
"""Verify empty argv lists are handled correctly."""
irrelevant_args = ['myexe', '/path/to/foo']
with mock.patch.object(sys, 'argv', irrelevant_args):
application.parse_preliminary_options_and_args([])
opts, args = application.parse_preliminary_options_and_args([])
assert application.prelim_args == []
assert args == []

View file

@ -1,4 +1,6 @@
"""Tests for Flake8's legacy API."""
import argparse
import mock
import pytest
@ -8,17 +10,26 @@ from flake8.formatting import base as formatter
def test_get_style_guide():
"""Verify the methods called on our internal Application."""
prelim_opts = argparse.Namespace(
append_config=[],
config=None,
isolated=False,
output_file=None,
verbose=0,
)
mockedapp = mock.Mock()
mockedapp.prelim_opts.verbose = 0
mockedapp.prelim_opts.output_file = None
mockedapp.parse_preliminary_options_and_args.return_value = (
prelim_opts,
[],
)
with mock.patch('flake8.main.application.Application') as application:
application.return_value = mockedapp
style_guide = api.get_style_guide()
application.assert_called_once_with()
mockedapp.parse_preliminary_options_and_args.assert_called_once_with([])
mockedapp.make_config_finder.assert_called_once_with()
mockedapp.find_plugins.assert_called_once_with()
mockedapp.make_config_finder.assert_called_once_with([], [])
mockedapp.find_plugins.assert_called_once_with(None, False)
mockedapp.register_plugin_options.assert_called_once_with()
mockedapp.parse_configuration_and_cli.assert_called_once_with([])
mockedapp.make_formatter.assert_called_once_with()