@@ -91,19 +91,19 @@ def parse_executed_tests(self, output):
91
91
return list (match .group (1 ) for match in parser )
92
92
93
93
def check_executed_tests (self , output , tests , skipped = (), failed = (),
94
- omitted = (), randomize = False , interrupted = False ):
94
+ env_changed = (), omitted = (),
95
+ randomize = False , interrupted = False ,
96
+ fail_env_changed = False ):
95
97
if isinstance (tests , str ):
96
98
tests = [tests ]
97
99
if isinstance (skipped , str ):
98
100
skipped = [skipped ]
99
101
if isinstance (failed , str ):
100
102
failed = [failed ]
103
+ if isinstance (env_changed , str ):
104
+ env_changed = [env_changed ]
101
105
if isinstance (omitted , str ):
102
106
omitted = [omitted ]
103
- ntest = len (tests )
104
- nskipped = len (skipped )
105
- nfailed = len (failed )
106
- nomitted = len (omitted )
107
107
108
108
executed = self .parse_executed_tests (output )
109
109
if randomize :
@@ -129,11 +129,17 @@ def list_regex(line_format, tests):
129
129
regex = list_regex ('%s test%s failed' , failed )
130
130
self .check_line (output , regex )
131
131
132
+ if env_changed :
133
+ regex = list_regex ('%s test%s altered the execution environment' ,
134
+ env_changed )
135
+ self .check_line (output , regex )
136
+
132
137
if omitted :
133
138
regex = list_regex ('%s test%s omitted' , omitted )
134
139
self .check_line (output , regex )
135
140
136
- good = ntest - nskipped - nfailed - nomitted
141
+ good = (len (tests ) - len (skipped ) - len (failed )
142
+ - len (omitted ) - len (env_changed ))
137
143
if good :
138
144
regex = r'%s test%s OK\.$' % (good , plural (good ))
139
145
if not skipped and not failed and good > 1 :
@@ -143,10 +149,12 @@ def list_regex(line_format, tests):
143
149
if interrupted :
144
150
self .check_line (output , 'Test suite interrupted by signal SIGINT.' )
145
151
146
- if nfailed :
152
+ if failed :
147
153
result = 'FAILURE'
148
154
elif interrupted :
149
155
result = 'INTERRUPTED'
156
+ elif fail_env_changed and env_changed :
157
+ result = 'ENV CHANGED'
150
158
else :
151
159
result = 'SUCCESS'
152
160
self .check_line (output , 'Tests result: %s' % result )
@@ -325,7 +333,7 @@ def test_main():
325
333
test_failing = self .create_test ('failing' , code = code )
326
334
tests = [test_ok , test_failing ]
327
335
328
- output = self .run_tests (* tests , exitcode = 1 )
336
+ output = self .run_tests (* tests , exitcode = 2 )
329
337
self .check_executed_tests (output , tests , failed = test_failing )
330
338
331
339
def test_resources (self ):
@@ -394,7 +402,7 @@ def test_fromfile(self):
394
402
def test_interrupted (self ):
395
403
code = TEST_INTERRUPTED
396
404
test = self .create_test ('sigint' , code = code )
397
- output = self .run_tests (test , exitcode = 1 )
405
+ output = self .run_tests (test , exitcode = 130 )
398
406
self .check_executed_tests (output , test , omitted = test ,
399
407
interrupted = True )
400
408
@@ -423,7 +431,7 @@ def test_slow_interrupted(self):
423
431
args = ("--slowest" , "-j2" , test )
424
432
else :
425
433
args = ("--slowest" , test )
426
- output = self .run_tests (* args , exitcode = 1 )
434
+ output = self .run_tests (* args , exitcode = 130 )
427
435
self .check_executed_tests (output , test ,
428
436
omitted = test , interrupted = True )
429
437
@@ -461,24 +469,88 @@ def test_main():
461
469
support.run_unittest(ForeverTester)
462
470
""" )
463
471
test = self .create_test ('forever' , code = code )
464
- output = self .run_tests ('--forever' , test , exitcode = 1 )
472
+ output = self .run_tests ('--forever' , test , exitcode = 2 )
465
473
self .check_executed_tests (output , [test ]* 3 , failed = test )
466
474
475
+ def check_leak (self , code , what ):
476
+ test = self .create_test ('huntrleaks' , code = code )
477
+
478
+ filename = 'reflog.txt'
479
+ self .addCleanup (support .unlink , filename )
480
+ output = self .run_tests ('--huntrleaks' , '3:3:' , test ,
481
+ exitcode = 2 ,
482
+ stderr = subprocess .STDOUT )
483
+ self .check_executed_tests (output , [test ], failed = test )
484
+
485
+ line = 'beginning 6 repetitions\n 123456\n ......\n '
486
+ self .check_line (output , re .escape (line ))
487
+
488
+ line2 = '%s leaked [1, 1, 1] %s, sum=3\n ' % (test , what )
489
+ self .assertIn (line2 , output )
490
+
491
+ with open (filename ) as fp :
492
+ reflog = fp .read ()
493
+ self .assertIn (line2 , reflog )
494
+
495
+ @unittest .skipUnless (Py_DEBUG , 'need a debug build' )
496
+ def test_huntrleaks (self ):
497
+ # test --huntrleaks
498
+ code = textwrap .dedent ("""
499
+ import unittest
500
+ from test import support
501
+
502
+ GLOBAL_LIST = []
503
+
504
+ class RefLeakTest(unittest.TestCase):
505
+ def test_leak(self):
506
+ GLOBAL_LIST.append(object())
507
+
508
+ def test_main():
509
+ support.run_unittest(RefLeakTest)
510
+ """ )
511
+ self .check_leak (code , 'references' )
512
+
467
513
def test_list_tests (self ):
468
514
# test --list-tests
469
515
tests = [self .create_test () for i in range (5 )]
470
516
output = self .run_tests ('--list-tests' , * tests )
471
517
self .assertEqual (output .rstrip ().splitlines (),
472
518
tests )
473
519
520
+ def test_list_cases (self ):
521
+ # test --list-cases
522
+ code = textwrap .dedent ("""
523
+ import unittest
524
+
525
+ class Tests(unittest.TestCase):
526
+ def test_method1(self):
527
+ pass
528
+ def test_method2(self):
529
+ pass
530
+ """ )
531
+ testname = self .create_test (code = code )
532
+
533
+ # Test --list-cases
534
+ all_methods = ['%s.Tests.test_method1' % testname ,
535
+ '%s.Tests.test_method2' % testname ]
536
+ output = self .run_tests ('--list-cases' , testname )
537
+ self .assertEqual (output .splitlines (), all_methods )
538
+
539
+ # Test --list-cases with --match
540
+ all_methods = ['%s.Tests.test_method1' % testname ]
541
+ output = self .run_tests ('--list-cases' ,
542
+ '-m' , 'test_method1' ,
543
+ testname )
544
+ self .assertEqual (output .splitlines (), all_methods )
545
+
474
546
def test_crashed (self ):
475
547
# Any code which causes a crash
476
548
code = 'import test.support; test.support._crash_python()'
477
549
crash_test = self .create_test (name = "crash" , code = code )
478
550
ok_test = self .create_test (name = "ok" )
479
551
480
552
tests = [crash_test , ok_test ]
481
- output = self .run_tests ("-j2" , * tests , exitcode = 1 )
553
+ output = self .run_tests ("-j2" , * tests , exitcode = 2 )
482
554
self .check_executed_tests (output , tests , failed = crash_test ,
483
555
randomize = True )
484
556
@@ -532,26 +604,28 @@ def test_main():
532
604
subset = ['test_method1' , 'test_method3' ]
533
605
self .assertEqual (methods , subset )
534
606
535
- def test_list_cases (self ):
536
- # test --list-cases
607
+ def test_env_changed (self ):
537
608
code = textwrap .dedent ("""
538
609
import unittest
539
610
from test import support
540
611
541
612
class Tests(unittest.TestCase):
542
- def test_method1(self):
543
- pass
544
- def test_method2(self):
545
- pass
613
+ def test_env_changed(self):
614
+ open("env_changed", "w").close()
546
615
547
616
def test_main():
548
617
support.run_unittest(Tests)
549
618
""" )
550
619
testname = self .create_test (code = code )
551
- all_methods = ['%s.Tests.test_method1' % testname ,
552
- '%s.Tests.test_method2' % testname ]
553
- output = self .run_tests ('--list-cases' , testname )
554
- self .assertEqual (output .splitlines (), all_methods )
620
+
621
+ # don't fail by default
622
+ output = self .run_tests (testname )
623
+ self .check_executed_tests (output , [testname ], env_changed = testname )
624
+
625
+ # fail with --fail-env-changed
626
+ output = self .run_tests ("--fail-env-changed" , testname , exitcode = 3 )
627
+ self .check_executed_tests (output , [testname ], env_changed = testname ,
628
+ fail_env_changed = True )
555
629
556
630
557
631
def test_main ():
0 commit comments