OLD | NEW |
| (Empty) |
1 """Reporter foundation for Coverage.""" | |
2 | |
3 import fnmatch, os | |
4 from coverage.codeunit import code_unit_factory | |
5 from coverage.files import prep_patterns | |
6 from coverage.misc import CoverageException, NoSource, NotPython | |
7 | |
8 class Reporter(object): | |
9 """A base class for all reporters.""" | |
10 | |
11 def __init__(self, coverage, config): | |
12 """Create a reporter. | |
13 | |
14 `coverage` is the coverage instance. `config` is an instance of | |
15 CoverageConfig, for controlling all sorts of behavior. | |
16 | |
17 """ | |
18 self.coverage = coverage | |
19 self.config = config | |
20 | |
21 # The code units to report on. Set by find_code_units. | |
22 self.code_units = [] | |
23 | |
24 # The directory into which to place the report, used by some derived | |
25 # classes. | |
26 self.directory = None | |
27 | |
28 def find_code_units(self, morfs): | |
29 """Find the code units we'll report on. | |
30 | |
31 `morfs` is a list of modules or filenames. | |
32 | |
33 """ | |
34 morfs = morfs or self.coverage.data.measured_files() | |
35 file_locator = self.coverage.file_locator | |
36 self.code_units = code_unit_factory(morfs, file_locator) | |
37 | |
38 if self.config.include: | |
39 patterns = prep_patterns(self.config.include) | |
40 filtered = [] | |
41 for cu in self.code_units: | |
42 for pattern in patterns: | |
43 if fnmatch.fnmatch(cu.filename, pattern): | |
44 filtered.append(cu) | |
45 break | |
46 self.code_units = filtered | |
47 | |
48 if self.config.omit: | |
49 patterns = prep_patterns(self.config.omit) | |
50 filtered = [] | |
51 for cu in self.code_units: | |
52 for pattern in patterns: | |
53 if fnmatch.fnmatch(cu.filename, pattern): | |
54 break | |
55 else: | |
56 filtered.append(cu) | |
57 self.code_units = filtered | |
58 | |
59 self.code_units.sort() | |
60 | |
61 def report_files(self, report_fn, morfs, directory=None): | |
62 """Run a reporting function on a number of morfs. | |
63 | |
64 `report_fn` is called for each relative morf in `morfs`. It is called | |
65 as:: | |
66 | |
67 report_fn(code_unit, analysis) | |
68 | |
69 where `code_unit` is the `CodeUnit` for the morf, and `analysis` is | |
70 the `Analysis` for the morf. | |
71 | |
72 """ | |
73 self.find_code_units(morfs) | |
74 | |
75 if not self.code_units: | |
76 raise CoverageException("No data to report.") | |
77 | |
78 self.directory = directory | |
79 if self.directory and not os.path.exists(self.directory): | |
80 os.makedirs(self.directory) | |
81 | |
82 for cu in self.code_units: | |
83 try: | |
84 report_fn(cu, self.coverage._analyze(cu)) | |
85 except NoSource: | |
86 if not self.config.ignore_errors: | |
87 raise | |
88 except NotPython: | |
89 # Only report errors for .py files, and only if we didn't | |
90 # explicitly suppress those errors. | |
91 if cu.should_be_python() and not self.config.ignore_errors: | |
92 raise | |
OLD | NEW |