From 75f7f448b14984dba4be4113cf89c8e4370efad7 Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Thu, 19 Feb 2015 07:35:54 -0500 Subject: Don't need this variable --- coverage/control.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 0bbe301..0880786 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -481,7 +481,7 @@ class Coverage(object): file_tracer.source_filename() ) break - except Exception as e: + except Exception: self._warn( "Disabling plugin %r due to an exception:" % ( plugin._coverage_plugin_name -- cgit v1.2.1 From ea1243c8d690d37054a2b681c62b17133741add7 Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Sat, 21 Feb 2015 09:30:58 -0500 Subject: Disable plugins if we can't support them, and show that in debug output. --- coverage/control.py | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 0880786..cb85da1 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -243,7 +243,7 @@ class Coverage(object): # Early warning if we aren't going to be able to support plugins. if self.file_tracers and not self.collector.supports_plugins: - raise CoverageException( + self._warn( "Plugin file tracers (%s) aren't supported with %s" % ( ", ".join( ft._coverage_plugin_name for ft in self.file_tracers @@ -251,6 +251,8 @@ class Coverage(object): self.collector.tracer_name(), ) ) + for plugin in self.file_tracers: + plugin._coverage_enabled = False # Suffixes are a bit tricky. We want to use the data suffix only when # collecting data, not when combining data. So we save it as @@ -1009,15 +1011,20 @@ class Coverage(object): except AttributeError: implementation = "unknown" + file_tracers = [] + for ft in self.file_tracers: + ft_name = ft._coverage_plugin_name + if not ft._coverage_enabled: + ft_name += " (disabled)" + file_tracers.append(ft_name) + info = [ ('version', covmod.__version__), ('coverage', covmod.__file__), ('cover_dir', self.cover_dir), ('pylib_dirs', self.pylib_dirs), ('tracer', self.collector.tracer_name()), - ('file_tracers', [ - ft._coverage_plugin_name for ft in self.file_tracers - ]), + ('file_tracers', file_tracers), ('config_files', self.config.attempted_config_files), ('configs_read', self.config.config_files), ('data_path', self.data.filename), -- cgit v1.2.1 From 4ce67933b19cd067046a55a8100f3a56881858ce Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Sat, 21 Feb 2015 20:40:39 -0500 Subject: Get rid of CodeUnit, FileReporter is the new thing. --- coverage/control.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index cb85da1..a0c21a4 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -989,7 +989,7 @@ class Coverage(object): outfile = open(self.config.xml_output, "w") file_to_close = outfile try: - reporter = XmlReporter(self, self.config) + reporter = XmlReporter(self, self.config, self.file_locator) return reporter.report(morfs, outfile=outfile) except CoverageException: delete_file = True -- cgit v1.2.1 From b376435de2f3a94fcbc2a36b9537265c46b86139 Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Sat, 21 Feb 2015 22:24:50 -0500 Subject: Rename CodeUnit to FileReporter --- coverage/control.py | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index a0c21a4..2db5802 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -24,7 +24,7 @@ from coverage.misc import CoverageException, bool_or_none, join_regex from coverage.misc import file_be_gone, overrides from coverage.monkey import patch_multiprocessing from coverage.plugin import CoveragePlugin, FileReporter -from coverage.python import PythonCodeUnit +from coverage.python import PythonFileReporter from coverage.results import Analysis, Numbers from coverage.summary import SummaryReporter from coverage.xmlreport import XmlReporter @@ -343,7 +343,7 @@ class Coverage(object): def _canonical_dir(self, morf): """Return the canonical directory of the module or file `morf`.""" - morf_filename = PythonCodeUnit(morf, self).filename + morf_filename = PythonFileReporter(morf, self).filename return os.path.split(morf_filename)[0] def _source_for_file(self, filename): @@ -850,7 +850,7 @@ class Coverage(object): ) ) else: - file_reporter = PythonCodeUnit(morf, self) + file_reporter = PythonFileReporter(morf, self) return file_reporter -- cgit v1.2.1 From ae8870bf5732895c1e68c6f64268a775a617f403 Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Sun, 22 Feb 2015 21:55:08 -0500 Subject: Ensure all FileReporter's have a .name attribute --- coverage/control.py | 20 ++++++++++++++------ 1 file changed, 14 insertions(+), 6 deletions(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 2db5802..2c0d9ed 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -18,7 +18,7 @@ from coverage.data import CoverageData from coverage.debug import DebugControl from coverage.files import FileLocator, TreeMatcher, FnmatchMatcher from coverage.files import PathAliases, find_python_files, prep_patterns -from coverage.files import ModuleMatcher +from coverage.files import ModuleMatcher, abs_file from coverage.html import HtmlReporter from coverage.misc import CoverageException, bool_or_none, join_regex from coverage.misc import file_be_gone, overrides @@ -837,12 +837,13 @@ class Coverage(object): plugin = None if isinstance(morf, string_class): - plugin_name = self.data.plugin_data().get(morf) + abs_morf = abs_file(morf) + plugin_name = self.data.plugin_data().get(abs_morf) if plugin_name: plugin = self.plugins.get(plugin_name) if plugin: - file_reporter = plugin.file_reporter(morf) + file_reporter = plugin.file_reporter(abs_morf) if file_reporter is None: raise CoverageException( "Plugin %r did not provide a file reporter for %r." % ( @@ -852,6 +853,13 @@ class Coverage(object): else: file_reporter = PythonFileReporter(morf, self) + # The FileReporter can have a name attribute, but if it doesn't, we'll + # supply it as the relative path to self.filename. + if not hasattr(file_reporter, "name"): + file_reporter.name = self.file_locator.relative_filename( + file_reporter.filename + ) + return file_reporter def _get_file_reporters(self, morfs=None): @@ -889,9 +897,9 @@ class Coverage(object): Each module in `morfs` is listed, with counts of statements, executed statements, missing statements, and a list of lines missed. - `include` is a list of filename patterns. Modules whose filenames - match those patterns will be included in the report. Modules matching - `omit` will not be included in the report. + `include` is a list of filename patterns. Files that match will be + included in the report. Files matching `omit` will not be included in + the report. Returns a float, the total percentage covered. -- cgit v1.2.1 From 08552fe5930212232c17509685f03b2216522aa7 Mon Sep 17 00:00:00 2001 From: Ned Batchelder Date: Thu, 26 Feb 2015 06:34:03 -0500 Subject: Handle exceptions from dynamic_source_filename. This required disabling plugins from the C tracer. --- coverage/control.py | 26 +++++++++++++------------- 1 file changed, 13 insertions(+), 13 deletions(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 2c0d9ed..563925e 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -168,7 +168,7 @@ class Coverage(object): self.omit = self.include = self.source = None self.source_pkgs = self.file_locator = None self.data = self.collector = None - self.plugins = self.file_tracers = None + self.plugins = self.file_tracing_plugins = None self.pylib_dirs = self.cover_dir = None self.data_suffix = self.run_suffix = None self._exclude_re = None @@ -203,10 +203,10 @@ class Coverage(object): # Load plugins self.plugins = Plugins.load_plugins(self.config.plugins, self.config) - self.file_tracers = [] + self.file_tracing_plugins = [] for plugin in self.plugins: if overrides(plugin, "file_tracer", CoveragePlugin): - self.file_tracers.append(plugin) + self.file_tracing_plugins.append(plugin) # _exclude_re is a dict that maps exclusion list names to compiled # regexes. @@ -242,16 +242,17 @@ class Coverage(object): ) # Early warning if we aren't going to be able to support plugins. - if self.file_tracers and not self.collector.supports_plugins: + if self.file_tracing_plugins and not self.collector.supports_plugins: self._warn( "Plugin file tracers (%s) aren't supported with %s" % ( ", ".join( - ft._coverage_plugin_name for ft in self.file_tracers + plugin._coverage_plugin_name + for plugin in self.file_tracing_plugins ), self.collector.tracer_name(), ) ) - for plugin in self.file_tracers: + for plugin in self.file_tracing_plugins: plugin._coverage_enabled = False # Suffixes are a bit tricky. We want to use the data suffix only when @@ -464,15 +465,14 @@ class Coverage(object): # Try the plugins, see if they have an opinion about the file. plugin = None - for plugin in self.file_tracers: + for plugin in self.file_tracing_plugins: if not plugin._coverage_enabled: continue try: file_tracer = plugin.file_tracer(canonical) if file_tracer is not None: - file_tracer._coverage_plugin_name = \ - plugin._coverage_plugin_name + file_tracer._coverage_plugin = plugin disp.trace = True disp.file_tracer = file_tracer if file_tracer.has_dynamic_source_filename(): @@ -1019,12 +1019,12 @@ class Coverage(object): except AttributeError: implementation = "unknown" - file_tracers = [] - for ft in self.file_tracers: + ft_plugins = [] + for ft in self.file_tracing_plugins: ft_name = ft._coverage_plugin_name if not ft._coverage_enabled: ft_name += " (disabled)" - file_tracers.append(ft_name) + ft_plugins.append(ft_name) info = [ ('version', covmod.__version__), @@ -1032,7 +1032,7 @@ class Coverage(object): ('cover_dir', self.cover_dir), ('pylib_dirs', self.pylib_dirs), ('tracer', self.collector.tracer_name()), - ('file_tracers', file_tracers), + ('file_tracing_plugins', ft_plugins), ('config_files', self.config.attempted_config_files), ('configs_read', self.config.config_files), ('data_path', self.data.filename), -- cgit v1.2.1 From 7efd4f50062f750df145102fc07c87fc49599bbe Mon Sep 17 00:00:00 2001 From: Christine Lytwynec Date: Tue, 21 Apr 2015 11:28:13 -0400 Subject: Added ability to combine coverage data files from multiple directories into one file via command line args. --- coverage/control.py | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 563925e..4a9ac72 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -717,7 +717,7 @@ class Coverage(object): self._harvest_data() self.data.write(suffix=data_suffix) - def combine(self): + def combine(self, data_dirs=None): """Combine together a number of similarly-named coverage data files. All coverage data files whose name starts with `data_file` (from the @@ -733,7 +733,7 @@ class Coverage(object): result = paths[0] for pattern in paths[1:]: aliases.add(pattern, result) - self.data.combine_parallel_data(aliases=aliases) + self.data.combine_parallel_data(aliases=aliases, data_dirs=data_dirs) def _harvest_data(self): """Get the collected data and reset the collector. -- cgit v1.2.1 From 161556f47ec6b8f7c0232c21fdbdd7cc25bd3d8e Mon Sep 17 00:00:00 2001 From: Christine Lytwynec Date: Wed, 22 Apr 2015 11:45:55 -0400 Subject: Update docstring and command line help text. --- coverage/control.py | 4 ++++ 1 file changed, 4 insertions(+) (limited to 'coverage/control.py') diff --git a/coverage/control.py b/coverage/control.py index 4a9ac72..2c8d384 100644 --- a/coverage/control.py +++ b/coverage/control.py @@ -724,6 +724,10 @@ class Coverage(object): coverage() constructor) will be read, and combined together into the current measurements. + `data_dirs` is a list of directories from which data files should be + combined. If no list is passed, then the data files from the current + directory will be combined. + """ self._init() aliases = None -- cgit v1.2.1