python (3.11.7)
1 import unittest
2
3 import gc
4 import sys
5 import weakref
6 from unittest.test.support import LoggingResult, TestEquality
7
8
9 ### Support code for Test_TestSuite
10 ################################################################
11
12 class ESC[4;38;5;81mTest(ESC[4;38;5;149mobject):
13 class ESC[4;38;5;81mFoo(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
14 def test_1(self): pass
15 def test_2(self): pass
16 def test_3(self): pass
17 def runTest(self): pass
18
19 def _mk_TestSuite(*names):
20 return unittest.TestSuite(Test.Foo(n) for n in names)
21
22 ################################################################
23
24
25 class ESC[4;38;5;81mTest_TestSuite(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase, ESC[4;38;5;149mTestEquality):
26
27 ### Set up attributes needed by inherited tests
28 ################################################################
29
30 # Used by TestEquality.test_eq
31 eq_pairs = [(unittest.TestSuite(), unittest.TestSuite())
32 ,(unittest.TestSuite(), unittest.TestSuite([]))
33 ,(_mk_TestSuite('test_1'), _mk_TestSuite('test_1'))]
34
35 # Used by TestEquality.test_ne
36 ne_pairs = [(unittest.TestSuite(), _mk_TestSuite('test_1'))
37 ,(unittest.TestSuite([]), _mk_TestSuite('test_1'))
38 ,(_mk_TestSuite('test_1', 'test_2'), _mk_TestSuite('test_1', 'test_3'))
39 ,(_mk_TestSuite('test_1'), _mk_TestSuite('test_2'))]
40
41 ################################################################
42 ### /Set up attributes needed by inherited tests
43
44 ### Tests for TestSuite.__init__
45 ################################################################
46
47 # "class TestSuite([tests])"
48 #
49 # The tests iterable should be optional
50 def test_init__tests_optional(self):
51 suite = unittest.TestSuite()
52
53 self.assertEqual(suite.countTestCases(), 0)
54 # countTestCases() still works after tests are run
55 suite.run(unittest.TestResult())
56 self.assertEqual(suite.countTestCases(), 0)
57
58 # "class TestSuite([tests])"
59 # ...
60 # "If tests is given, it must be an iterable of individual test cases
61 # or other test suites that will be used to build the suite initially"
62 #
63 # TestSuite should deal with empty tests iterables by allowing the
64 # creation of an empty suite
65 def test_init__empty_tests(self):
66 suite = unittest.TestSuite([])
67
68 self.assertEqual(suite.countTestCases(), 0)
69 # countTestCases() still works after tests are run
70 suite.run(unittest.TestResult())
71 self.assertEqual(suite.countTestCases(), 0)
72
73 # "class TestSuite([tests])"
74 # ...
75 # "If tests is given, it must be an iterable of individual test cases
76 # or other test suites that will be used to build the suite initially"
77 #
78 # TestSuite should allow any iterable to provide tests
79 def test_init__tests_from_any_iterable(self):
80 def tests():
81 yield unittest.FunctionTestCase(lambda: None)
82 yield unittest.FunctionTestCase(lambda: None)
83
84 suite_1 = unittest.TestSuite(tests())
85 self.assertEqual(suite_1.countTestCases(), 2)
86
87 suite_2 = unittest.TestSuite(suite_1)
88 self.assertEqual(suite_2.countTestCases(), 2)
89
90 suite_3 = unittest.TestSuite(set(suite_1))
91 self.assertEqual(suite_3.countTestCases(), 2)
92
93 # countTestCases() still works after tests are run
94 suite_1.run(unittest.TestResult())
95 self.assertEqual(suite_1.countTestCases(), 2)
96 suite_2.run(unittest.TestResult())
97 self.assertEqual(suite_2.countTestCases(), 2)
98 suite_3.run(unittest.TestResult())
99 self.assertEqual(suite_3.countTestCases(), 2)
100
101 # "class TestSuite([tests])"
102 # ...
103 # "If tests is given, it must be an iterable of individual test cases
104 # or other test suites that will be used to build the suite initially"
105 #
106 # Does TestSuite() also allow other TestSuite() instances to be present
107 # in the tests iterable?
108 def test_init__TestSuite_instances_in_tests(self):
109 def tests():
110 ftc = unittest.FunctionTestCase(lambda: None)
111 yield unittest.TestSuite([ftc])
112 yield unittest.FunctionTestCase(lambda: None)
113
114 suite = unittest.TestSuite(tests())
115 self.assertEqual(suite.countTestCases(), 2)
116 # countTestCases() still works after tests are run
117 suite.run(unittest.TestResult())
118 self.assertEqual(suite.countTestCases(), 2)
119
120 ################################################################
121 ### /Tests for TestSuite.__init__
122
123 # Container types should support the iter protocol
124 def test_iter(self):
125 test1 = unittest.FunctionTestCase(lambda: None)
126 test2 = unittest.FunctionTestCase(lambda: None)
127 suite = unittest.TestSuite((test1, test2))
128
129 self.assertEqual(list(suite), [test1, test2])
130
131 # "Return the number of tests represented by the this test object.
132 # ...this method is also implemented by the TestSuite class, which can
133 # return larger [greater than 1] values"
134 #
135 # Presumably an empty TestSuite returns 0?
136 def test_countTestCases_zero_simple(self):
137 suite = unittest.TestSuite()
138
139 self.assertEqual(suite.countTestCases(), 0)
140
141 # "Return the number of tests represented by the this test object.
142 # ...this method is also implemented by the TestSuite class, which can
143 # return larger [greater than 1] values"
144 #
145 # Presumably an empty TestSuite (even if it contains other empty
146 # TestSuite instances) returns 0?
147 def test_countTestCases_zero_nested(self):
148 class ESC[4;38;5;81mTest1(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
149 def test(self):
150 pass
151
152 suite = unittest.TestSuite([unittest.TestSuite()])
153
154 self.assertEqual(suite.countTestCases(), 0)
155
156 # "Return the number of tests represented by the this test object.
157 # ...this method is also implemented by the TestSuite class, which can
158 # return larger [greater than 1] values"
159 def test_countTestCases_simple(self):
160 test1 = unittest.FunctionTestCase(lambda: None)
161 test2 = unittest.FunctionTestCase(lambda: None)
162 suite = unittest.TestSuite((test1, test2))
163
164 self.assertEqual(suite.countTestCases(), 2)
165 # countTestCases() still works after tests are run
166 suite.run(unittest.TestResult())
167 self.assertEqual(suite.countTestCases(), 2)
168
169 # "Return the number of tests represented by the this test object.
170 # ...this method is also implemented by the TestSuite class, which can
171 # return larger [greater than 1] values"
172 #
173 # Make sure this holds for nested TestSuite instances, too
174 def test_countTestCases_nested(self):
175 class ESC[4;38;5;81mTest1(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
176 def test1(self): pass
177 def test2(self): pass
178
179 test2 = unittest.FunctionTestCase(lambda: None)
180 test3 = unittest.FunctionTestCase(lambda: None)
181 child = unittest.TestSuite((Test1('test2'), test2))
182 parent = unittest.TestSuite((test3, child, Test1('test1')))
183
184 self.assertEqual(parent.countTestCases(), 4)
185 # countTestCases() still works after tests are run
186 parent.run(unittest.TestResult())
187 self.assertEqual(parent.countTestCases(), 4)
188 self.assertEqual(child.countTestCases(), 2)
189
190 # "Run the tests associated with this suite, collecting the result into
191 # the test result object passed as result."
192 #
193 # And if there are no tests? What then?
194 def test_run__empty_suite(self):
195 events = []
196 result = LoggingResult(events)
197
198 suite = unittest.TestSuite()
199
200 suite.run(result)
201
202 self.assertEqual(events, [])
203
204 # "Note that unlike TestCase.run(), TestSuite.run() requires the
205 # "result object to be passed in."
206 def test_run__requires_result(self):
207 suite = unittest.TestSuite()
208
209 try:
210 suite.run()
211 except TypeError:
212 pass
213 else:
214 self.fail("Failed to raise TypeError")
215
216 # "Run the tests associated with this suite, collecting the result into
217 # the test result object passed as result."
218 def test_run(self):
219 events = []
220 result = LoggingResult(events)
221
222 class ESC[4;38;5;81mLoggingCase(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
223 def run(self, result):
224 events.append('run %s' % self._testMethodName)
225
226 def test1(self): pass
227 def test2(self): pass
228
229 tests = [LoggingCase('test1'), LoggingCase('test2')]
230
231 unittest.TestSuite(tests).run(result)
232
233 self.assertEqual(events, ['run test1', 'run test2'])
234
235 # "Add a TestCase ... to the suite"
236 def test_addTest__TestCase(self):
237 class ESC[4;38;5;81mFoo(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
238 def test(self): pass
239
240 test = Foo('test')
241 suite = unittest.TestSuite()
242
243 suite.addTest(test)
244
245 self.assertEqual(suite.countTestCases(), 1)
246 self.assertEqual(list(suite), [test])
247 # countTestCases() still works after tests are run
248 suite.run(unittest.TestResult())
249 self.assertEqual(suite.countTestCases(), 1)
250
251 # "Add a ... TestSuite to the suite"
252 def test_addTest__TestSuite(self):
253 class ESC[4;38;5;81mFoo(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
254 def test(self): pass
255
256 suite_2 = unittest.TestSuite([Foo('test')])
257
258 suite = unittest.TestSuite()
259 suite.addTest(suite_2)
260
261 self.assertEqual(suite.countTestCases(), 1)
262 self.assertEqual(list(suite), [suite_2])
263 # countTestCases() still works after tests are run
264 suite.run(unittest.TestResult())
265 self.assertEqual(suite.countTestCases(), 1)
266
267 # "Add all the tests from an iterable of TestCase and TestSuite
268 # instances to this test suite."
269 #
270 # "This is equivalent to iterating over tests, calling addTest() for
271 # each element"
272 def test_addTests(self):
273 class ESC[4;38;5;81mFoo(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
274 def test_1(self): pass
275 def test_2(self): pass
276
277 test_1 = Foo('test_1')
278 test_2 = Foo('test_2')
279 inner_suite = unittest.TestSuite([test_2])
280
281 def gen():
282 yield test_1
283 yield test_2
284 yield inner_suite
285
286 suite_1 = unittest.TestSuite()
287 suite_1.addTests(gen())
288
289 self.assertEqual(list(suite_1), list(gen()))
290
291 # "This is equivalent to iterating over tests, calling addTest() for
292 # each element"
293 suite_2 = unittest.TestSuite()
294 for t in gen():
295 suite_2.addTest(t)
296
297 self.assertEqual(suite_1, suite_2)
298
299 # "Add all the tests from an iterable of TestCase and TestSuite
300 # instances to this test suite."
301 #
302 # What happens if it doesn't get an iterable?
303 def test_addTest__noniterable(self):
304 suite = unittest.TestSuite()
305
306 try:
307 suite.addTests(5)
308 except TypeError:
309 pass
310 else:
311 self.fail("Failed to raise TypeError")
312
313 def test_addTest__noncallable(self):
314 suite = unittest.TestSuite()
315 self.assertRaises(TypeError, suite.addTest, 5)
316
317 def test_addTest__casesuiteclass(self):
318 suite = unittest.TestSuite()
319 self.assertRaises(TypeError, suite.addTest, Test_TestSuite)
320 self.assertRaises(TypeError, suite.addTest, unittest.TestSuite)
321
322 def test_addTests__string(self):
323 suite = unittest.TestSuite()
324 self.assertRaises(TypeError, suite.addTests, "foo")
325
326 def test_function_in_suite(self):
327 def f(_):
328 pass
329 suite = unittest.TestSuite()
330 suite.addTest(f)
331
332 # when the bug is fixed this line will not crash
333 suite.run(unittest.TestResult())
334
335 def test_remove_test_at_index(self):
336 if not unittest.BaseTestSuite._cleanup:
337 raise unittest.SkipTest("Suite cleanup is disabled")
338
339 suite = unittest.TestSuite()
340
341 suite._tests = [1, 2, 3]
342 suite._removeTestAtIndex(1)
343
344 self.assertEqual([1, None, 3], suite._tests)
345
346 def test_remove_test_at_index_not_indexable(self):
347 if not unittest.BaseTestSuite._cleanup:
348 raise unittest.SkipTest("Suite cleanup is disabled")
349
350 suite = unittest.TestSuite()
351 suite._tests = None
352
353 # if _removeAtIndex raises for noniterables this next line will break
354 suite._removeTestAtIndex(2)
355
356 def assert_garbage_collect_test_after_run(self, TestSuiteClass):
357 if not unittest.BaseTestSuite._cleanup:
358 raise unittest.SkipTest("Suite cleanup is disabled")
359
360 class ESC[4;38;5;81mFoo(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
361 def test_nothing(self):
362 pass
363
364 test = Foo('test_nothing')
365 wref = weakref.ref(test)
366
367 suite = TestSuiteClass([wref()])
368 suite.run(unittest.TestResult())
369
370 del test
371
372 # for the benefit of non-reference counting implementations
373 gc.collect()
374
375 self.assertEqual(suite._tests, [None])
376 self.assertIsNone(wref())
377
378 def test_garbage_collect_test_after_run_BaseTestSuite(self):
379 self.assert_garbage_collect_test_after_run(unittest.BaseTestSuite)
380
381 def test_garbage_collect_test_after_run_TestSuite(self):
382 self.assert_garbage_collect_test_after_run(unittest.TestSuite)
383
384 def test_basetestsuite(self):
385 class ESC[4;38;5;81mTest(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestCase):
386 wasSetUp = False
387 wasTornDown = False
388 @classmethod
389 def setUpClass(cls):
390 cls.wasSetUp = True
391 @classmethod
392 def tearDownClass(cls):
393 cls.wasTornDown = True
394 def testPass(self):
395 pass
396 def testFail(self):
397 fail
398 class ESC[4;38;5;81mModule(ESC[4;38;5;149mobject):
399 wasSetUp = False
400 wasTornDown = False
401 @staticmethod
402 def setUpModule():
403 Module.wasSetUp = True
404 @staticmethod
405 def tearDownModule():
406 Module.wasTornDown = True
407
408 Test.__module__ = 'Module'
409 sys.modules['Module'] = Module
410 self.addCleanup(sys.modules.pop, 'Module')
411
412 suite = unittest.BaseTestSuite()
413 suite.addTests([Test('testPass'), Test('testFail')])
414 self.assertEqual(suite.countTestCases(), 2)
415
416 result = unittest.TestResult()
417 suite.run(result)
418 self.assertFalse(Module.wasSetUp)
419 self.assertFalse(Module.wasTornDown)
420 self.assertFalse(Test.wasSetUp)
421 self.assertFalse(Test.wasTornDown)
422 self.assertEqual(len(result.errors), 1)
423 self.assertEqual(len(result.failures), 0)
424 self.assertEqual(result.testsRun, 2)
425 self.assertEqual(suite.countTestCases(), 2)
426
427
428 def test_overriding_call(self):
429 class ESC[4;38;5;81mMySuite(ESC[4;38;5;149munittestESC[4;38;5;149m.ESC[4;38;5;149mTestSuite):
430 called = False
431 def __call__(self, *args, **kw):
432 self.called = True
433 unittest.TestSuite.__call__(self, *args, **kw)
434
435 suite = MySuite()
436 result = unittest.TestResult()
437 wrapper = unittest.TestSuite()
438 wrapper.addTest(suite)
439 wrapper(result)
440 self.assertTrue(suite.called)
441
442 # reusing results should be permitted even if abominable
443 self.assertFalse(result._testRunEntered)
444
445
446 if __name__ == '__main__':
447 unittest.main()