]> crepu.dev Git - config.git/blame - djavu-asus/elpy/rpc-venv/lib/python3.11/site-packages/setuptools/command/test.py
Actualizado el Readme
[config.git] / djavu-asus / elpy / rpc-venv / lib / python3.11 / site-packages / setuptools / command / test.py
CommitLineData
53e6db90
DC
1import os
2import operator
3import sys
4import contextlib
5import itertools
6import unittest
7from distutils.errors import DistutilsError, DistutilsOptionError
8from distutils import log
9from unittest import TestLoader
10
11from pkg_resources import (
12 resource_listdir,
13 resource_exists,
14 normalize_path,
15 working_set,
16 evaluate_marker,
17 add_activation_listener,
18 require,
19)
20from .._importlib import metadata
21from setuptools import Command
22from setuptools.extern.more_itertools import unique_everseen
23from setuptools.extern.jaraco.functools import pass_none
24
25
26class ScanningLoader(TestLoader):
27 def __init__(self):
28 TestLoader.__init__(self)
29 self._visited = set()
30
31 def loadTestsFromModule(self, module, pattern=None):
32 """Return a suite of all tests cases contained in the given module
33
34 If the module is a package, load tests from all the modules in it.
35 If the module has an ``additional_tests`` function, call it and add
36 the return value to the tests.
37 """
38 if module in self._visited:
39 return None
40 self._visited.add(module)
41
42 tests = []
43 tests.append(TestLoader.loadTestsFromModule(self, module))
44
45 if hasattr(module, "additional_tests"):
46 tests.append(module.additional_tests())
47
48 if hasattr(module, '__path__'):
49 for file in resource_listdir(module.__name__, ''):
50 if file.endswith('.py') and file != '__init__.py':
51 submodule = module.__name__ + '.' + file[:-3]
52 else:
53 if resource_exists(module.__name__, file + '/__init__.py'):
54 submodule = module.__name__ + '.' + file
55 else:
56 continue
57 tests.append(self.loadTestsFromName(submodule))
58
59 if len(tests) != 1:
60 return self.suiteClass(tests)
61 else:
62 return tests[0] # don't create a nested suite for only one return
63
64
65# adapted from jaraco.classes.properties:NonDataProperty
66class NonDataProperty:
67 def __init__(self, fget):
68 self.fget = fget
69
70 def __get__(self, obj, objtype=None):
71 if obj is None:
72 return self
73 return self.fget(obj)
74
75
76class test(Command):
77 """Command to run unit tests after in-place build"""
78
79 description = "run unit tests after in-place build (deprecated)"
80
81 user_options = [
82 ('test-module=', 'm', "Run 'test_suite' in specified module"),
83 (
84 'test-suite=',
85 's',
86 "Run single test, case or suite (e.g. 'module.test_suite')",
87 ),
88 ('test-runner=', 'r', "Test runner to use"),
89 ]
90
91 def initialize_options(self):
92 self.test_suite = None
93 self.test_module = None
94 self.test_loader = None
95 self.test_runner = None
96
97 def finalize_options(self):
98
99 if self.test_suite and self.test_module:
100 msg = "You may specify a module or a suite, but not both"
101 raise DistutilsOptionError(msg)
102
103 if self.test_suite is None:
104 if self.test_module is None:
105 self.test_suite = self.distribution.test_suite
106 else:
107 self.test_suite = self.test_module + ".test_suite"
108
109 if self.test_loader is None:
110 self.test_loader = getattr(self.distribution, 'test_loader', None)
111 if self.test_loader is None:
112 self.test_loader = "setuptools.command.test:ScanningLoader"
113 if self.test_runner is None:
114 self.test_runner = getattr(self.distribution, 'test_runner', None)
115
116 @NonDataProperty
117 def test_args(self):
118 return list(self._test_args())
119
120 def _test_args(self):
121 if not self.test_suite:
122 yield 'discover'
123 if self.verbose:
124 yield '--verbose'
125 if self.test_suite:
126 yield self.test_suite
127
128 def with_project_on_sys_path(self, func):
129 """
130 Backward compatibility for project_on_sys_path context.
131 """
132 with self.project_on_sys_path():
133 func()
134
135 @contextlib.contextmanager
136 def project_on_sys_path(self, include_dists=[]):
137 self.run_command('egg_info')
138
139 # Build extensions in-place
140 self.reinitialize_command('build_ext', inplace=1)
141 self.run_command('build_ext')
142
143 ei_cmd = self.get_finalized_command("egg_info")
144
145 old_path = sys.path[:]
146 old_modules = sys.modules.copy()
147
148 try:
149 project_path = normalize_path(ei_cmd.egg_base)
150 sys.path.insert(0, project_path)
151 working_set.__init__()
152 add_activation_listener(lambda dist: dist.activate())
153 require('%s==%s' % (ei_cmd.egg_name, ei_cmd.egg_version))
154 with self.paths_on_pythonpath([project_path]):
155 yield
156 finally:
157 sys.path[:] = old_path
158 sys.modules.clear()
159 sys.modules.update(old_modules)
160 working_set.__init__()
161
162 @staticmethod
163 @contextlib.contextmanager
164 def paths_on_pythonpath(paths):
165 """
166 Add the indicated paths to the head of the PYTHONPATH environment
167 variable so that subprocesses will also see the packages at
168 these paths.
169
170 Do this in a context that restores the value on exit.
171 """
172 nothing = object()
173 orig_pythonpath = os.environ.get('PYTHONPATH', nothing)
174 current_pythonpath = os.environ.get('PYTHONPATH', '')
175 try:
176 prefix = os.pathsep.join(unique_everseen(paths))
177 to_join = filter(None, [prefix, current_pythonpath])
178 new_path = os.pathsep.join(to_join)
179 if new_path:
180 os.environ['PYTHONPATH'] = new_path
181 yield
182 finally:
183 if orig_pythonpath is nothing:
184 os.environ.pop('PYTHONPATH', None)
185 else:
186 os.environ['PYTHONPATH'] = orig_pythonpath
187
188 @staticmethod
189 def install_dists(dist):
190 """
191 Install the requirements indicated by self.distribution and
192 return an iterable of the dists that were built.
193 """
194 ir_d = dist.fetch_build_eggs(dist.install_requires)
195 tr_d = dist.fetch_build_eggs(dist.tests_require or [])
196 er_d = dist.fetch_build_eggs(
197 v
198 for k, v in dist.extras_require.items()
199 if k.startswith(':') and evaluate_marker(k[1:])
200 )
201 return itertools.chain(ir_d, tr_d, er_d)
202
203 def run(self):
204 self.announce(
205 "WARNING: Testing via this command is deprecated and will be "
206 "removed in a future version. Users looking for a generic test "
207 "entry point independent of test runner are encouraged to use "
208 "tox.",
209 log.WARN,
210 )
211
212 installed_dists = self.install_dists(self.distribution)
213
214 cmd = ' '.join(self._argv)
215 if self.dry_run:
216 self.announce('skipping "%s" (dry run)' % cmd)
217 return
218
219 self.announce('running "%s"' % cmd)
220
221 paths = map(operator.attrgetter('location'), installed_dists)
222 with self.paths_on_pythonpath(paths):
223 with self.project_on_sys_path():
224 self.run_tests()
225
226 def run_tests(self):
227 test = unittest.main(
228 None,
229 None,
230 self._argv,
231 testLoader=self._resolve_as_ep(self.test_loader),
232 testRunner=self._resolve_as_ep(self.test_runner),
233 exit=False,
234 )
235 if not test.result.wasSuccessful():
236 msg = 'Test failed: %s' % test.result
237 self.announce(msg, log.ERROR)
238 raise DistutilsError(msg)
239
240 @property
241 def _argv(self):
242 return ['unittest'] + self.test_args
243
244 @staticmethod
245 @pass_none
246 def _resolve_as_ep(val):
247 """
248 Load the indicated attribute value, called, as a as if it were
249 specified as an entry point.
250 """
251 return metadata.EntryPoint(value=val, name=None, group=None).load()()