1from contextlib import contextmanager 2import linecache 3import os 4from io import StringIO 5import re 6import sys 7import textwrap 8import unittest 9from test import support 10from test.support.script_helper import assert_python_ok, assert_python_failure 11 12from test.test_warnings.data import stacklevel as warning_tests 13 14import warnings as original_warnings 15 16py_warnings = support.import_fresh_module('warnings', blocked=['_warnings']) 17c_warnings = support.import_fresh_module('warnings', fresh=['_warnings']) 18 19Py_DEBUG = hasattr(sys, 'gettotalrefcount') 20 21@contextmanager 22def warnings_state(module): 23 """Use a specific warnings implementation in warning_tests.""" 24 global __warningregistry__ 25 for to_clear in (sys, warning_tests): 26 try: 27 to_clear.__warningregistry__.clear() 28 except AttributeError: 29 pass 30 try: 31 __warningregistry__.clear() 32 except NameError: 33 pass 34 original_warnings = warning_tests.warnings 35 original_filters = module.filters 36 try: 37 module.filters = original_filters[:] 38 module.simplefilter("once") 39 warning_tests.warnings = module 40 yield 41 finally: 42 warning_tests.warnings = original_warnings 43 module.filters = original_filters 44 45 46class BaseTest: 47 48 """Basic bookkeeping required for testing.""" 49 50 def setUp(self): 51 self.old_unittest_module = unittest.case.warnings 52 # The __warningregistry__ needs to be in a pristine state for tests 53 # to work properly. 54 if '__warningregistry__' in globals(): 55 del globals()['__warningregistry__'] 56 if hasattr(warning_tests, '__warningregistry__'): 57 del warning_tests.__warningregistry__ 58 if hasattr(sys, '__warningregistry__'): 59 del sys.__warningregistry__ 60 # The 'warnings' module must be explicitly set so that the proper 61 # interaction between _warnings and 'warnings' can be controlled. 62 sys.modules['warnings'] = self.module 63 # Ensure that unittest.TestCase.assertWarns() uses the same warnings 64 # module than warnings.catch_warnings(). Otherwise, 65 # warnings.catch_warnings() will be unable to remove the added filter. 66 unittest.case.warnings = self.module 67 super(BaseTest, self).setUp() 68 69 def tearDown(self): 70 sys.modules['warnings'] = original_warnings 71 unittest.case.warnings = self.old_unittest_module 72 super(BaseTest, self).tearDown() 73 74class PublicAPITests(BaseTest): 75 76 """Ensures that the correct values are exposed in the 77 public API. 78 """ 79 80 def test_module_all_attribute(self): 81 self.assertTrue(hasattr(self.module, '__all__')) 82 target_api = ["warn", "warn_explicit", "showwarning", 83 "formatwarning", "filterwarnings", "simplefilter", 84 "resetwarnings", "catch_warnings"] 85 self.assertSetEqual(set(self.module.__all__), 86 set(target_api)) 87 88class CPublicAPITests(PublicAPITests, unittest.TestCase): 89 module = c_warnings 90 91class PyPublicAPITests(PublicAPITests, unittest.TestCase): 92 module = py_warnings 93 94class FilterTests(BaseTest): 95 96 """Testing the filtering functionality.""" 97 98 def test_error(self): 99 with original_warnings.catch_warnings(module=self.module) as w: 100 self.module.resetwarnings() 101 self.module.filterwarnings("error", category=UserWarning) 102 self.assertRaises(UserWarning, self.module.warn, 103 "FilterTests.test_error") 104 105 def test_error_after_default(self): 106 with original_warnings.catch_warnings(module=self.module) as w: 107 self.module.resetwarnings() 108 message = "FilterTests.test_ignore_after_default" 109 def f(): 110 self.module.warn(message, UserWarning) 111 112 with support.captured_stderr() as stderr: 113 f() 114 stderr = stderr.getvalue() 115 self.assertIn("UserWarning: FilterTests.test_ignore_after_default", 116 stderr) 117 self.assertIn("self.module.warn(message, UserWarning)", 118 stderr) 119 120 self.module.filterwarnings("error", category=UserWarning) 121 self.assertRaises(UserWarning, f) 122 123 def test_ignore(self): 124 with original_warnings.catch_warnings(record=True, 125 module=self.module) as w: 126 self.module.resetwarnings() 127 self.module.filterwarnings("ignore", category=UserWarning) 128 self.module.warn("FilterTests.test_ignore", UserWarning) 129 self.assertEqual(len(w), 0) 130 self.assertEqual(list(__warningregistry__), ['version']) 131 132 def test_ignore_after_default(self): 133 with original_warnings.catch_warnings(record=True, 134 module=self.module) as w: 135 self.module.resetwarnings() 136 message = "FilterTests.test_ignore_after_default" 137 def f(): 138 self.module.warn(message, UserWarning) 139 f() 140 self.module.filterwarnings("ignore", category=UserWarning) 141 f() 142 f() 143 self.assertEqual(len(w), 1) 144 145 def test_always(self): 146 with original_warnings.catch_warnings(record=True, 147 module=self.module) as w: 148 self.module.resetwarnings() 149 self.module.filterwarnings("always", category=UserWarning) 150 message = "FilterTests.test_always" 151 def f(): 152 self.module.warn(message, UserWarning) 153 f() 154 self.assertEqual(len(w), 1) 155 self.assertEqual(w[-1].message.args[0], message) 156 f() 157 self.assertEqual(len(w), 2) 158 self.assertEqual(w[-1].message.args[0], message) 159 160 def test_always_after_default(self): 161 with original_warnings.catch_warnings(record=True, 162 module=self.module) as w: 163 self.module.resetwarnings() 164 message = "FilterTests.test_always_after_ignore" 165 def f(): 166 self.module.warn(message, UserWarning) 167 f() 168 self.assertEqual(len(w), 1) 169 self.assertEqual(w[-1].message.args[0], message) 170 f() 171 self.assertEqual(len(w), 1) 172 self.module.filterwarnings("always", category=UserWarning) 173 f() 174 self.assertEqual(len(w), 2) 175 self.assertEqual(w[-1].message.args[0], message) 176 f() 177 self.assertEqual(len(w), 3) 178 self.assertEqual(w[-1].message.args[0], message) 179 180 def test_default(self): 181 with original_warnings.catch_warnings(record=True, 182 module=self.module) as w: 183 self.module.resetwarnings() 184 self.module.filterwarnings("default", category=UserWarning) 185 message = UserWarning("FilterTests.test_default") 186 for x in range(2): 187 self.module.warn(message, UserWarning) 188 if x == 0: 189 self.assertEqual(w[-1].message, message) 190 del w[:] 191 elif x == 1: 192 self.assertEqual(len(w), 0) 193 else: 194 raise ValueError("loop variant unhandled") 195 196 def test_module(self): 197 with original_warnings.catch_warnings(record=True, 198 module=self.module) as w: 199 self.module.resetwarnings() 200 self.module.filterwarnings("module", category=UserWarning) 201 message = UserWarning("FilterTests.test_module") 202 self.module.warn(message, UserWarning) 203 self.assertEqual(w[-1].message, message) 204 del w[:] 205 self.module.warn(message, UserWarning) 206 self.assertEqual(len(w), 0) 207 208 def test_once(self): 209 with original_warnings.catch_warnings(record=True, 210 module=self.module) as w: 211 self.module.resetwarnings() 212 self.module.filterwarnings("once", category=UserWarning) 213 message = UserWarning("FilterTests.test_once") 214 self.module.warn_explicit(message, UserWarning, "__init__.py", 215 42) 216 self.assertEqual(w[-1].message, message) 217 del w[:] 218 self.module.warn_explicit(message, UserWarning, "__init__.py", 219 13) 220 self.assertEqual(len(w), 0) 221 self.module.warn_explicit(message, UserWarning, "test_warnings2.py", 222 42) 223 self.assertEqual(len(w), 0) 224 225 def test_module_globals(self): 226 with original_warnings.catch_warnings(record=True, 227 module=self.module) as w: 228 self.module.simplefilter("always", UserWarning) 229 230 # bpo-33509: module_globals=None must not crash 231 self.module.warn_explicit('msg', UserWarning, "filename", 42, 232 module_globals=None) 233 self.assertEqual(len(w), 1) 234 235 # Invalid module_globals type 236 with self.assertRaises(TypeError): 237 self.module.warn_explicit('msg', UserWarning, "filename", 42, 238 module_globals=True) 239 self.assertEqual(len(w), 1) 240 241 # Empty module_globals 242 self.module.warn_explicit('msg', UserWarning, "filename", 42, 243 module_globals={}) 244 self.assertEqual(len(w), 2) 245 246 def test_inheritance(self): 247 with original_warnings.catch_warnings(module=self.module) as w: 248 self.module.resetwarnings() 249 self.module.filterwarnings("error", category=Warning) 250 self.assertRaises(UserWarning, self.module.warn, 251 "FilterTests.test_inheritance", UserWarning) 252 253 def test_ordering(self): 254 with original_warnings.catch_warnings(record=True, 255 module=self.module) as w: 256 self.module.resetwarnings() 257 self.module.filterwarnings("ignore", category=UserWarning) 258 self.module.filterwarnings("error", category=UserWarning, 259 append=True) 260 del w[:] 261 try: 262 self.module.warn("FilterTests.test_ordering", UserWarning) 263 except UserWarning: 264 self.fail("order handling for actions failed") 265 self.assertEqual(len(w), 0) 266 267 def test_filterwarnings(self): 268 # Test filterwarnings(). 269 # Implicitly also tests resetwarnings(). 270 with original_warnings.catch_warnings(record=True, 271 module=self.module) as w: 272 self.module.filterwarnings("error", "", Warning, "", 0) 273 self.assertRaises(UserWarning, self.module.warn, 'convert to error') 274 275 self.module.resetwarnings() 276 text = 'handle normally' 277 self.module.warn(text) 278 self.assertEqual(str(w[-1].message), text) 279 self.assertIs(w[-1].category, UserWarning) 280 281 self.module.filterwarnings("ignore", "", Warning, "", 0) 282 text = 'filtered out' 283 self.module.warn(text) 284 self.assertNotEqual(str(w[-1].message), text) 285 286 self.module.resetwarnings() 287 self.module.filterwarnings("error", "hex*", Warning, "", 0) 288 self.assertRaises(UserWarning, self.module.warn, 'hex/oct') 289 text = 'nonmatching text' 290 self.module.warn(text) 291 self.assertEqual(str(w[-1].message), text) 292 self.assertIs(w[-1].category, UserWarning) 293 294 def test_message_matching(self): 295 with original_warnings.catch_warnings(record=True, 296 module=self.module) as w: 297 self.module.simplefilter("ignore", UserWarning) 298 self.module.filterwarnings("error", "match", UserWarning) 299 self.assertRaises(UserWarning, self.module.warn, "match") 300 self.assertRaises(UserWarning, self.module.warn, "match prefix") 301 self.module.warn("suffix match") 302 self.assertEqual(w, []) 303 self.module.warn("something completely different") 304 self.assertEqual(w, []) 305 306 def test_mutate_filter_list(self): 307 class X: 308 def match(self, a): 309 L[:] = [] 310 311 L = [("default",X(),UserWarning,X(),0) for i in range(2)] 312 with original_warnings.catch_warnings(record=True, 313 module=self.module) as w: 314 self.module.filters = L 315 self.module.warn_explicit(UserWarning("b"), None, "f.py", 42) 316 self.assertEqual(str(w[-1].message), "b") 317 318 def test_filterwarnings_duplicate_filters(self): 319 with original_warnings.catch_warnings(module=self.module): 320 self.module.resetwarnings() 321 self.module.filterwarnings("error", category=UserWarning) 322 self.assertEqual(len(self.module.filters), 1) 323 self.module.filterwarnings("ignore", category=UserWarning) 324 self.module.filterwarnings("error", category=UserWarning) 325 self.assertEqual( 326 len(self.module.filters), 2, 327 "filterwarnings inserted duplicate filter" 328 ) 329 self.assertEqual( 330 self.module.filters[0][0], "error", 331 "filterwarnings did not promote filter to " 332 "the beginning of list" 333 ) 334 335 def test_simplefilter_duplicate_filters(self): 336 with original_warnings.catch_warnings(module=self.module): 337 self.module.resetwarnings() 338 self.module.simplefilter("error", category=UserWarning) 339 self.assertEqual(len(self.module.filters), 1) 340 self.module.simplefilter("ignore", category=UserWarning) 341 self.module.simplefilter("error", category=UserWarning) 342 self.assertEqual( 343 len(self.module.filters), 2, 344 "simplefilter inserted duplicate filter" 345 ) 346 self.assertEqual( 347 self.module.filters[0][0], "error", 348 "simplefilter did not promote filter to the beginning of list" 349 ) 350 351 def test_append_duplicate(self): 352 with original_warnings.catch_warnings(module=self.module, 353 record=True) as w: 354 self.module.resetwarnings() 355 self.module.simplefilter("ignore") 356 self.module.simplefilter("error", append=True) 357 self.module.simplefilter("ignore", append=True) 358 self.module.warn("test_append_duplicate", category=UserWarning) 359 self.assertEqual(len(self.module.filters), 2, 360 "simplefilter inserted duplicate filter" 361 ) 362 self.assertEqual(len(w), 0, 363 "appended duplicate changed order of filters" 364 ) 365 366class CFilterTests(FilterTests, unittest.TestCase): 367 module = c_warnings 368 369class PyFilterTests(FilterTests, unittest.TestCase): 370 module = py_warnings 371 372 373class WarnTests(BaseTest): 374 375 """Test warnings.warn() and warnings.warn_explicit().""" 376 377 def test_message(self): 378 with original_warnings.catch_warnings(record=True, 379 module=self.module) as w: 380 self.module.simplefilter("once") 381 for i in range(4): 382 text = 'multi %d' %i # Different text on each call. 383 self.module.warn(text) 384 self.assertEqual(str(w[-1].message), text) 385 self.assertIs(w[-1].category, UserWarning) 386 387 # Issue 3639 388 def test_warn_nonstandard_types(self): 389 # warn() should handle non-standard types without issue. 390 for ob in (Warning, None, 42): 391 with original_warnings.catch_warnings(record=True, 392 module=self.module) as w: 393 self.module.simplefilter("once") 394 self.module.warn(ob) 395 # Don't directly compare objects since 396 # ``Warning() != Warning()``. 397 self.assertEqual(str(w[-1].message), str(UserWarning(ob))) 398 399 def test_filename(self): 400 with warnings_state(self.module): 401 with original_warnings.catch_warnings(record=True, 402 module=self.module) as w: 403 warning_tests.inner("spam1") 404 self.assertEqual(os.path.basename(w[-1].filename), 405 "stacklevel.py") 406 warning_tests.outer("spam2") 407 self.assertEqual(os.path.basename(w[-1].filename), 408 "stacklevel.py") 409 410 def test_stacklevel(self): 411 # Test stacklevel argument 412 # make sure all messages are different, so the warning won't be skipped 413 with warnings_state(self.module): 414 with original_warnings.catch_warnings(record=True, 415 module=self.module) as w: 416 warning_tests.inner("spam3", stacklevel=1) 417 self.assertEqual(os.path.basename(w[-1].filename), 418 "stacklevel.py") 419 warning_tests.outer("spam4", stacklevel=1) 420 self.assertEqual(os.path.basename(w[-1].filename), 421 "stacklevel.py") 422 423 warning_tests.inner("spam5", stacklevel=2) 424 self.assertEqual(os.path.basename(w[-1].filename), 425 "__init__.py") 426 warning_tests.outer("spam6", stacklevel=2) 427 self.assertEqual(os.path.basename(w[-1].filename), 428 "stacklevel.py") 429 warning_tests.outer("spam6.5", stacklevel=3) 430 self.assertEqual(os.path.basename(w[-1].filename), 431 "__init__.py") 432 433 warning_tests.inner("spam7", stacklevel=9999) 434 self.assertEqual(os.path.basename(w[-1].filename), 435 "sys") 436 437 def test_stacklevel_import(self): 438 # Issue #24305: With stacklevel=2, module-level warnings should work. 439 support.unload('test.test_warnings.data.import_warning') 440 with warnings_state(self.module): 441 with original_warnings.catch_warnings(record=True, 442 module=self.module) as w: 443 self.module.simplefilter('always') 444 import test.test_warnings.data.import_warning 445 self.assertEqual(len(w), 1) 446 self.assertEqual(w[0].filename, __file__) 447 448 def test_missing_filename_not_main(self): 449 # If __file__ is not specified and __main__ is not the module name, 450 # then __file__ should be set to the module name. 451 filename = warning_tests.__file__ 452 try: 453 del warning_tests.__file__ 454 with warnings_state(self.module): 455 with original_warnings.catch_warnings(record=True, 456 module=self.module) as w: 457 warning_tests.inner("spam8", stacklevel=1) 458 self.assertEqual(w[-1].filename, warning_tests.__name__) 459 finally: 460 warning_tests.__file__ = filename 461 462 @unittest.skipUnless(hasattr(sys, 'argv'), 'test needs sys.argv') 463 def test_missing_filename_main_with_argv(self): 464 # If __file__ is not specified and the caller is __main__ and sys.argv 465 # exists, then use sys.argv[0] as the file. 466 filename = warning_tests.__file__ 467 module_name = warning_tests.__name__ 468 try: 469 del warning_tests.__file__ 470 warning_tests.__name__ = '__main__' 471 with warnings_state(self.module): 472 with original_warnings.catch_warnings(record=True, 473 module=self.module) as w: 474 warning_tests.inner('spam9', stacklevel=1) 475 self.assertEqual(w[-1].filename, sys.argv[0]) 476 finally: 477 warning_tests.__file__ = filename 478 warning_tests.__name__ = module_name 479 480 def test_missing_filename_main_without_argv(self): 481 # If __file__ is not specified, the caller is __main__, and sys.argv 482 # is not set, then '__main__' is the file name. 483 filename = warning_tests.__file__ 484 module_name = warning_tests.__name__ 485 argv = sys.argv 486 try: 487 del warning_tests.__file__ 488 warning_tests.__name__ = '__main__' 489 del sys.argv 490 with warnings_state(self.module): 491 with original_warnings.catch_warnings(record=True, 492 module=self.module) as w: 493 warning_tests.inner('spam10', stacklevel=1) 494 self.assertEqual(w[-1].filename, '__main__') 495 finally: 496 warning_tests.__file__ = filename 497 warning_tests.__name__ = module_name 498 sys.argv = argv 499 500 def test_missing_filename_main_with_argv_empty_string(self): 501 # If __file__ is not specified, the caller is __main__, and sys.argv[0] 502 # is the empty string, then '__main__ is the file name. 503 # Tests issue 2743. 504 file_name = warning_tests.__file__ 505 module_name = warning_tests.__name__ 506 argv = sys.argv 507 try: 508 del warning_tests.__file__ 509 warning_tests.__name__ = '__main__' 510 sys.argv = [''] 511 with warnings_state(self.module): 512 with original_warnings.catch_warnings(record=True, 513 module=self.module) as w: 514 warning_tests.inner('spam11', stacklevel=1) 515 self.assertEqual(w[-1].filename, '__main__') 516 finally: 517 warning_tests.__file__ = file_name 518 warning_tests.__name__ = module_name 519 sys.argv = argv 520 521 def test_warn_explicit_non_ascii_filename(self): 522 with original_warnings.catch_warnings(record=True, 523 module=self.module) as w: 524 self.module.resetwarnings() 525 self.module.filterwarnings("always", category=UserWarning) 526 for filename in ("nonascii\xe9\u20ac", "surrogate\udc80"): 527 try: 528 os.fsencode(filename) 529 except UnicodeEncodeError: 530 continue 531 self.module.warn_explicit("text", UserWarning, filename, 1) 532 self.assertEqual(w[-1].filename, filename) 533 534 def test_warn_explicit_type_errors(self): 535 # warn_explicit() should error out gracefully if it is given objects 536 # of the wrong types. 537 # lineno is expected to be an integer. 538 self.assertRaises(TypeError, self.module.warn_explicit, 539 None, UserWarning, None, None) 540 # Either 'message' needs to be an instance of Warning or 'category' 541 # needs to be a subclass. 542 self.assertRaises(TypeError, self.module.warn_explicit, 543 None, None, None, 1) 544 # 'registry' must be a dict or None. 545 self.assertRaises((TypeError, AttributeError), 546 self.module.warn_explicit, 547 None, Warning, None, 1, registry=42) 548 549 def test_bad_str(self): 550 # issue 6415 551 # Warnings instance with a bad format string for __str__ should not 552 # trigger a bus error. 553 class BadStrWarning(Warning): 554 """Warning with a bad format string for __str__.""" 555 def __str__(self): 556 return ("A bad formatted string %(err)" % 557 {"err" : "there is no %(err)s"}) 558 559 with self.assertRaises(ValueError): 560 self.module.warn(BadStrWarning()) 561 562 def test_warning_classes(self): 563 class MyWarningClass(Warning): 564 pass 565 566 class NonWarningSubclass: 567 pass 568 569 # passing a non-subclass of Warning should raise a TypeError 570 with self.assertRaises(TypeError) as cm: 571 self.module.warn('bad warning category', '') 572 self.assertIn('category must be a Warning subclass, not ', 573 str(cm.exception)) 574 575 with self.assertRaises(TypeError) as cm: 576 self.module.warn('bad warning category', NonWarningSubclass) 577 self.assertIn('category must be a Warning subclass, not ', 578 str(cm.exception)) 579 580 # check that warning instances also raise a TypeError 581 with self.assertRaises(TypeError) as cm: 582 self.module.warn('bad warning category', MyWarningClass()) 583 self.assertIn('category must be a Warning subclass, not ', 584 str(cm.exception)) 585 586 with original_warnings.catch_warnings(module=self.module): 587 self.module.resetwarnings() 588 self.module.filterwarnings('default') 589 with self.assertWarns(MyWarningClass) as cm: 590 self.module.warn('good warning category', MyWarningClass) 591 self.assertEqual('good warning category', str(cm.warning)) 592 593 with self.assertWarns(UserWarning) as cm: 594 self.module.warn('good warning category', None) 595 self.assertEqual('good warning category', str(cm.warning)) 596 597 with self.assertWarns(MyWarningClass) as cm: 598 self.module.warn('good warning category', MyWarningClass) 599 self.assertIsInstance(cm.warning, Warning) 600 601class CWarnTests(WarnTests, unittest.TestCase): 602 module = c_warnings 603 604 # As an early adopter, we sanity check the 605 # test.support.import_fresh_module utility function 606 def test_accelerated(self): 607 self.assertIsNot(original_warnings, self.module) 608 self.assertFalse(hasattr(self.module.warn, '__code__')) 609 610class PyWarnTests(WarnTests, unittest.TestCase): 611 module = py_warnings 612 613 # As an early adopter, we sanity check the 614 # test.support.import_fresh_module utility function 615 def test_pure_python(self): 616 self.assertIsNot(original_warnings, self.module) 617 self.assertTrue(hasattr(self.module.warn, '__code__')) 618 619 620class WCmdLineTests(BaseTest): 621 622 def test_improper_input(self): 623 # Uses the private _setoption() function to test the parsing 624 # of command-line warning arguments 625 with original_warnings.catch_warnings(module=self.module): 626 self.assertRaises(self.module._OptionError, 627 self.module._setoption, '1:2:3:4:5:6') 628 self.assertRaises(self.module._OptionError, 629 self.module._setoption, 'bogus::Warning') 630 self.assertRaises(self.module._OptionError, 631 self.module._setoption, 'ignore:2::4:-5') 632 self.module._setoption('error::Warning::0') 633 self.assertRaises(UserWarning, self.module.warn, 'convert to error') 634 635 636class CWCmdLineTests(WCmdLineTests, unittest.TestCase): 637 module = c_warnings 638 639 640class PyWCmdLineTests(WCmdLineTests, unittest.TestCase): 641 module = py_warnings 642 643 def test_improper_option(self): 644 # Same as above, but check that the message is printed out when 645 # the interpreter is executed. This also checks that options are 646 # actually parsed at all. 647 rc, out, err = assert_python_ok("-Wxxx", "-c", "pass") 648 self.assertIn(b"Invalid -W option ignored: invalid action: 'xxx'", err) 649 650 def test_warnings_bootstrap(self): 651 # Check that the warnings module does get loaded when -W<some option> 652 # is used (see issue #10372 for an example of silent bootstrap failure). 653 rc, out, err = assert_python_ok("-Wi", "-c", 654 "import sys; sys.modules['warnings'].warn('foo', RuntimeWarning)") 655 # '-Wi' was observed 656 self.assertFalse(out.strip()) 657 self.assertNotIn(b'RuntimeWarning', err) 658 659 660class _WarningsTests(BaseTest, unittest.TestCase): 661 662 """Tests specific to the _warnings module.""" 663 664 module = c_warnings 665 666 def test_filter(self): 667 # Everything should function even if 'filters' is not in warnings. 668 with original_warnings.catch_warnings(module=self.module) as w: 669 self.module.filterwarnings("error", "", Warning, "", 0) 670 self.assertRaises(UserWarning, self.module.warn, 671 'convert to error') 672 del self.module.filters 673 self.assertRaises(UserWarning, self.module.warn, 674 'convert to error') 675 676 def test_onceregistry(self): 677 # Replacing or removing the onceregistry should be okay. 678 global __warningregistry__ 679 message = UserWarning('onceregistry test') 680 try: 681 original_registry = self.module.onceregistry 682 __warningregistry__ = {} 683 with original_warnings.catch_warnings(record=True, 684 module=self.module) as w: 685 self.module.resetwarnings() 686 self.module.filterwarnings("once", category=UserWarning) 687 self.module.warn_explicit(message, UserWarning, "file", 42) 688 self.assertEqual(w[-1].message, message) 689 del w[:] 690 self.module.warn_explicit(message, UserWarning, "file", 42) 691 self.assertEqual(len(w), 0) 692 # Test the resetting of onceregistry. 693 self.module.onceregistry = {} 694 __warningregistry__ = {} 695 self.module.warn('onceregistry test') 696 self.assertEqual(w[-1].message.args, message.args) 697 # Removal of onceregistry is okay. 698 del w[:] 699 del self.module.onceregistry 700 __warningregistry__ = {} 701 self.module.warn_explicit(message, UserWarning, "file", 42) 702 self.assertEqual(len(w), 0) 703 finally: 704 self.module.onceregistry = original_registry 705 706 def test_default_action(self): 707 # Replacing or removing defaultaction should be okay. 708 message = UserWarning("defaultaction test") 709 original = self.module.defaultaction 710 try: 711 with original_warnings.catch_warnings(record=True, 712 module=self.module) as w: 713 self.module.resetwarnings() 714 registry = {} 715 self.module.warn_explicit(message, UserWarning, "<test>", 42, 716 registry=registry) 717 self.assertEqual(w[-1].message, message) 718 self.assertEqual(len(w), 1) 719 # One actual registry key plus the "version" key 720 self.assertEqual(len(registry), 2) 721 self.assertIn("version", registry) 722 del w[:] 723 # Test removal. 724 del self.module.defaultaction 725 __warningregistry__ = {} 726 registry = {} 727 self.module.warn_explicit(message, UserWarning, "<test>", 43, 728 registry=registry) 729 self.assertEqual(w[-1].message, message) 730 self.assertEqual(len(w), 1) 731 self.assertEqual(len(registry), 2) 732 del w[:] 733 # Test setting. 734 self.module.defaultaction = "ignore" 735 __warningregistry__ = {} 736 registry = {} 737 self.module.warn_explicit(message, UserWarning, "<test>", 44, 738 registry=registry) 739 self.assertEqual(len(w), 0) 740 finally: 741 self.module.defaultaction = original 742 743 def test_showwarning_missing(self): 744 # Test that showwarning() missing is okay. 745 text = 'del showwarning test' 746 with original_warnings.catch_warnings(module=self.module): 747 self.module.filterwarnings("always", category=UserWarning) 748 del self.module.showwarning 749 with support.captured_output('stderr') as stream: 750 self.module.warn(text) 751 result = stream.getvalue() 752 self.assertIn(text, result) 753 754 def test_showwarnmsg_missing(self): 755 # Test that _showwarnmsg() missing is okay. 756 text = 'del _showwarnmsg test' 757 with original_warnings.catch_warnings(module=self.module): 758 self.module.filterwarnings("always", category=UserWarning) 759 760 show = self.module._showwarnmsg 761 try: 762 del self.module._showwarnmsg 763 with support.captured_output('stderr') as stream: 764 self.module.warn(text) 765 result = stream.getvalue() 766 finally: 767 self.module._showwarnmsg = show 768 self.assertIn(text, result) 769 770 def test_showwarning_not_callable(self): 771 with original_warnings.catch_warnings(module=self.module): 772 self.module.filterwarnings("always", category=UserWarning) 773 self.module.showwarning = print 774 with support.captured_output('stdout'): 775 self.module.warn('Warning!') 776 self.module.showwarning = 23 777 self.assertRaises(TypeError, self.module.warn, "Warning!") 778 779 def test_show_warning_output(self): 780 # With showarning() missing, make sure that output is okay. 781 text = 'test show_warning' 782 with original_warnings.catch_warnings(module=self.module): 783 self.module.filterwarnings("always", category=UserWarning) 784 del self.module.showwarning 785 with support.captured_output('stderr') as stream: 786 warning_tests.inner(text) 787 result = stream.getvalue() 788 self.assertEqual(result.count('\n'), 2, 789 "Too many newlines in %r" % result) 790 first_line, second_line = result.split('\n', 1) 791 expected_file = os.path.splitext(warning_tests.__file__)[0] + '.py' 792 first_line_parts = first_line.rsplit(':', 3) 793 path, line, warning_class, message = first_line_parts 794 line = int(line) 795 self.assertEqual(expected_file, path) 796 self.assertEqual(warning_class, ' ' + UserWarning.__name__) 797 self.assertEqual(message, ' ' + text) 798 expected_line = ' ' + linecache.getline(path, line).strip() + '\n' 799 assert expected_line 800 self.assertEqual(second_line, expected_line) 801 802 def test_filename_none(self): 803 # issue #12467: race condition if a warning is emitted at shutdown 804 globals_dict = globals() 805 oldfile = globals_dict['__file__'] 806 try: 807 catch = original_warnings.catch_warnings(record=True, 808 module=self.module) 809 with catch as w: 810 self.module.filterwarnings("always", category=UserWarning) 811 globals_dict['__file__'] = None 812 original_warnings.warn('test', UserWarning) 813 self.assertTrue(len(w)) 814 finally: 815 globals_dict['__file__'] = oldfile 816 817 def test_stderr_none(self): 818 rc, stdout, stderr = assert_python_ok("-c", 819 "import sys; sys.stderr = None; " 820 "import warnings; warnings.simplefilter('always'); " 821 "warnings.warn('Warning!')") 822 self.assertEqual(stdout, b'') 823 self.assertNotIn(b'Warning!', stderr) 824 self.assertNotIn(b'Error', stderr) 825 826 def test_issue31285(self): 827 # warn_explicit() should neither raise a SystemError nor cause an 828 # assertion failure, in case the return value of get_source() has a 829 # bad splitlines() method. 830 def get_bad_loader(splitlines_ret_val): 831 class BadLoader: 832 def get_source(self, fullname): 833 class BadSource(str): 834 def splitlines(self): 835 return splitlines_ret_val 836 return BadSource('spam') 837 return BadLoader() 838 839 wmod = self.module 840 with original_warnings.catch_warnings(module=wmod): 841 wmod.filterwarnings('default', category=UserWarning) 842 843 with support.captured_stderr() as stderr: 844 wmod.warn_explicit( 845 'foo', UserWarning, 'bar', 1, 846 module_globals={'__loader__': get_bad_loader(42), 847 '__name__': 'foobar'}) 848 self.assertIn('UserWarning: foo', stderr.getvalue()) 849 850 show = wmod._showwarnmsg 851 try: 852 del wmod._showwarnmsg 853 with support.captured_stderr() as stderr: 854 wmod.warn_explicit( 855 'eggs', UserWarning, 'bar', 1, 856 module_globals={'__loader__': get_bad_loader([42]), 857 '__name__': 'foobar'}) 858 self.assertIn('UserWarning: eggs', stderr.getvalue()) 859 finally: 860 wmod._showwarnmsg = show 861 862 @support.cpython_only 863 def test_issue31411(self): 864 # warn_explicit() shouldn't raise a SystemError in case 865 # warnings.onceregistry isn't a dictionary. 866 wmod = self.module 867 with original_warnings.catch_warnings(module=wmod): 868 wmod.filterwarnings('once') 869 with support.swap_attr(wmod, 'onceregistry', None): 870 with self.assertRaises(TypeError): 871 wmod.warn_explicit('foo', Warning, 'bar', 1, registry=None) 872 873 @support.cpython_only 874 def test_issue31416(self): 875 # warn_explicit() shouldn't cause an assertion failure in case of a 876 # bad warnings.filters or warnings.defaultaction. 877 wmod = self.module 878 with original_warnings.catch_warnings(module=wmod): 879 wmod.filters = [(None, None, Warning, None, 0)] 880 with self.assertRaises(TypeError): 881 wmod.warn_explicit('foo', Warning, 'bar', 1) 882 883 wmod.filters = [] 884 with support.swap_attr(wmod, 'defaultaction', None), \ 885 self.assertRaises(TypeError): 886 wmod.warn_explicit('foo', Warning, 'bar', 1) 887 888 @support.cpython_only 889 def test_issue31566(self): 890 # warn() shouldn't cause an assertion failure in case of a bad 891 # __name__ global. 892 with original_warnings.catch_warnings(module=self.module): 893 self.module.filterwarnings('error', category=UserWarning) 894 with support.swap_item(globals(), '__name__', b'foo'), \ 895 support.swap_item(globals(), '__file__', None): 896 self.assertRaises(UserWarning, self.module.warn, 'bar') 897 898 899class WarningsDisplayTests(BaseTest): 900 901 """Test the displaying of warnings and the ability to overload functions 902 related to displaying warnings.""" 903 904 def test_formatwarning(self): 905 message = "msg" 906 category = Warning 907 file_name = os.path.splitext(warning_tests.__file__)[0] + '.py' 908 line_num = 3 909 file_line = linecache.getline(file_name, line_num).strip() 910 format = "%s:%s: %s: %s\n %s\n" 911 expect = format % (file_name, line_num, category.__name__, message, 912 file_line) 913 self.assertEqual(expect, self.module.formatwarning(message, 914 category, file_name, line_num)) 915 # Test the 'line' argument. 916 file_line += " for the win!" 917 expect = format % (file_name, line_num, category.__name__, message, 918 file_line) 919 self.assertEqual(expect, self.module.formatwarning(message, 920 category, file_name, line_num, file_line)) 921 922 def test_showwarning(self): 923 file_name = os.path.splitext(warning_tests.__file__)[0] + '.py' 924 line_num = 3 925 expected_file_line = linecache.getline(file_name, line_num).strip() 926 message = 'msg' 927 category = Warning 928 file_object = StringIO() 929 expect = self.module.formatwarning(message, category, file_name, 930 line_num) 931 self.module.showwarning(message, category, file_name, line_num, 932 file_object) 933 self.assertEqual(file_object.getvalue(), expect) 934 # Test 'line' argument. 935 expected_file_line += "for the win!" 936 expect = self.module.formatwarning(message, category, file_name, 937 line_num, expected_file_line) 938 file_object = StringIO() 939 self.module.showwarning(message, category, file_name, line_num, 940 file_object, expected_file_line) 941 self.assertEqual(expect, file_object.getvalue()) 942 943 def test_formatwarning_override(self): 944 # bpo-35178: Test that a custom formatwarning function gets the 'line' 945 # argument as a positional argument, and not only as a keyword argument 946 def myformatwarning(message, category, filename, lineno, text): 947 return f'm={message}:c={category}:f={filename}:l={lineno}:t={text}' 948 949 file_name = os.path.splitext(warning_tests.__file__)[0] + '.py' 950 line_num = 3 951 file_line = linecache.getline(file_name, line_num).strip() 952 message = 'msg' 953 category = Warning 954 file_object = StringIO() 955 expected = f'm={message}:c={category}:f={file_name}:l={line_num}' + \ 956 f':t={file_line}' 957 with support.swap_attr(self.module, 'formatwarning', myformatwarning): 958 self.module.showwarning(message, category, file_name, line_num, 959 file_object, file_line) 960 self.assertEqual(file_object.getvalue(), expected) 961 962 963class CWarningsDisplayTests(WarningsDisplayTests, unittest.TestCase): 964 module = c_warnings 965 966class PyWarningsDisplayTests(WarningsDisplayTests, unittest.TestCase): 967 module = py_warnings 968 969 def test_tracemalloc(self): 970 self.addCleanup(support.unlink, support.TESTFN) 971 972 with open(support.TESTFN, 'w') as fp: 973 fp.write(textwrap.dedent(""" 974 def func(): 975 f = open(__file__) 976 # Emit ResourceWarning 977 f = None 978 979 func() 980 """)) 981 982 def run(*args): 983 res = assert_python_ok(*args) 984 stderr = res.err.decode('ascii', 'replace') 985 stderr = '\n'.join(stderr.splitlines()) 986 987 # normalize newlines 988 stderr = re.sub('<.*>', '<...>', stderr) 989 return stderr 990 991 # tracemalloc disabled 992 stderr = run('-Wd', support.TESTFN) 993 expected = textwrap.dedent(''' 994 {fname}:5: ResourceWarning: unclosed file <...> 995 f = None 996 ResourceWarning: Enable tracemalloc to get the object allocation traceback 997 ''') 998 expected = expected.format(fname=support.TESTFN).strip() 999 self.assertEqual(stderr, expected) 1000 1001 # tracemalloc enabled 1002 stderr = run('-Wd', '-X', 'tracemalloc=2', support.TESTFN) 1003 expected = textwrap.dedent(''' 1004 {fname}:5: ResourceWarning: unclosed file <...> 1005 f = None 1006 Object allocated at (most recent call last): 1007 File "{fname}", lineno 7 1008 func() 1009 File "{fname}", lineno 3 1010 f = open(__file__) 1011 ''') 1012 expected = expected.format(fname=support.TESTFN).strip() 1013 self.assertEqual(stderr, expected) 1014 1015 1016class CatchWarningTests(BaseTest): 1017 1018 """Test catch_warnings().""" 1019 1020 def test_catch_warnings_restore(self): 1021 wmod = self.module 1022 orig_filters = wmod.filters 1023 orig_showwarning = wmod.showwarning 1024 # Ensure both showwarning and filters are restored when recording 1025 with wmod.catch_warnings(module=wmod, record=True): 1026 wmod.filters = wmod.showwarning = object() 1027 self.assertIs(wmod.filters, orig_filters) 1028 self.assertIs(wmod.showwarning, orig_showwarning) 1029 # Same test, but with recording disabled 1030 with wmod.catch_warnings(module=wmod, record=False): 1031 wmod.filters = wmod.showwarning = object() 1032 self.assertIs(wmod.filters, orig_filters) 1033 self.assertIs(wmod.showwarning, orig_showwarning) 1034 1035 def test_catch_warnings_recording(self): 1036 wmod = self.module 1037 # Ensure warnings are recorded when requested 1038 with wmod.catch_warnings(module=wmod, record=True) as w: 1039 self.assertEqual(w, []) 1040 self.assertIs(type(w), list) 1041 wmod.simplefilter("always") 1042 wmod.warn("foo") 1043 self.assertEqual(str(w[-1].message), "foo") 1044 wmod.warn("bar") 1045 self.assertEqual(str(w[-1].message), "bar") 1046 self.assertEqual(str(w[0].message), "foo") 1047 self.assertEqual(str(w[1].message), "bar") 1048 del w[:] 1049 self.assertEqual(w, []) 1050 # Ensure warnings are not recorded when not requested 1051 orig_showwarning = wmod.showwarning 1052 with wmod.catch_warnings(module=wmod, record=False) as w: 1053 self.assertIsNone(w) 1054 self.assertIs(wmod.showwarning, orig_showwarning) 1055 1056 def test_catch_warnings_reentry_guard(self): 1057 wmod = self.module 1058 # Ensure catch_warnings is protected against incorrect usage 1059 x = wmod.catch_warnings(module=wmod, record=True) 1060 self.assertRaises(RuntimeError, x.__exit__) 1061 with x: 1062 self.assertRaises(RuntimeError, x.__enter__) 1063 # Same test, but with recording disabled 1064 x = wmod.catch_warnings(module=wmod, record=False) 1065 self.assertRaises(RuntimeError, x.__exit__) 1066 with x: 1067 self.assertRaises(RuntimeError, x.__enter__) 1068 1069 def test_catch_warnings_defaults(self): 1070 wmod = self.module 1071 orig_filters = wmod.filters 1072 orig_showwarning = wmod.showwarning 1073 # Ensure default behaviour is not to record warnings 1074 with wmod.catch_warnings(module=wmod) as w: 1075 self.assertIsNone(w) 1076 self.assertIs(wmod.showwarning, orig_showwarning) 1077 self.assertIsNot(wmod.filters, orig_filters) 1078 self.assertIs(wmod.filters, orig_filters) 1079 if wmod is sys.modules['warnings']: 1080 # Ensure the default module is this one 1081 with wmod.catch_warnings() as w: 1082 self.assertIsNone(w) 1083 self.assertIs(wmod.showwarning, orig_showwarning) 1084 self.assertIsNot(wmod.filters, orig_filters) 1085 self.assertIs(wmod.filters, orig_filters) 1086 1087 def test_record_override_showwarning_before(self): 1088 # Issue #28835: If warnings.showwarning() was overridden, make sure 1089 # that catch_warnings(record=True) overrides it again. 1090 text = "This is a warning" 1091 wmod = self.module 1092 my_log = [] 1093 1094 def my_logger(message, category, filename, lineno, file=None, line=None): 1095 nonlocal my_log 1096 my_log.append(message) 1097 1098 # Override warnings.showwarning() before calling catch_warnings() 1099 with support.swap_attr(wmod, 'showwarning', my_logger): 1100 with wmod.catch_warnings(module=wmod, record=True) as log: 1101 self.assertIsNot(wmod.showwarning, my_logger) 1102 1103 wmod.simplefilter("always") 1104 wmod.warn(text) 1105 1106 self.assertIs(wmod.showwarning, my_logger) 1107 1108 self.assertEqual(len(log), 1, log) 1109 self.assertEqual(log[0].message.args[0], text) 1110 self.assertEqual(my_log, []) 1111 1112 def test_record_override_showwarning_inside(self): 1113 # Issue #28835: It is possible to override warnings.showwarning() 1114 # in the catch_warnings(record=True) context manager. 1115 text = "This is a warning" 1116 wmod = self.module 1117 my_log = [] 1118 1119 def my_logger(message, category, filename, lineno, file=None, line=None): 1120 nonlocal my_log 1121 my_log.append(message) 1122 1123 with wmod.catch_warnings(module=wmod, record=True) as log: 1124 wmod.simplefilter("always") 1125 wmod.showwarning = my_logger 1126 wmod.warn(text) 1127 1128 self.assertEqual(len(my_log), 1, my_log) 1129 self.assertEqual(my_log[0].args[0], text) 1130 self.assertEqual(log, []) 1131 1132 def test_check_warnings(self): 1133 # Explicit tests for the test.support convenience wrapper 1134 wmod = self.module 1135 if wmod is not sys.modules['warnings']: 1136 self.skipTest('module to test is not loaded warnings module') 1137 with support.check_warnings(quiet=False) as w: 1138 self.assertEqual(w.warnings, []) 1139 wmod.simplefilter("always") 1140 wmod.warn("foo") 1141 self.assertEqual(str(w.message), "foo") 1142 wmod.warn("bar") 1143 self.assertEqual(str(w.message), "bar") 1144 self.assertEqual(str(w.warnings[0].message), "foo") 1145 self.assertEqual(str(w.warnings[1].message), "bar") 1146 w.reset() 1147 self.assertEqual(w.warnings, []) 1148 1149 with support.check_warnings(): 1150 # defaults to quiet=True without argument 1151 pass 1152 with support.check_warnings(('foo', UserWarning)): 1153 wmod.warn("foo") 1154 1155 with self.assertRaises(AssertionError): 1156 with support.check_warnings(('', RuntimeWarning)): 1157 # defaults to quiet=False with argument 1158 pass 1159 with self.assertRaises(AssertionError): 1160 with support.check_warnings(('foo', RuntimeWarning)): 1161 wmod.warn("foo") 1162 1163class CCatchWarningTests(CatchWarningTests, unittest.TestCase): 1164 module = c_warnings 1165 1166class PyCatchWarningTests(CatchWarningTests, unittest.TestCase): 1167 module = py_warnings 1168 1169 1170class EnvironmentVariableTests(BaseTest): 1171 1172 def test_single_warning(self): 1173 rc, stdout, stderr = assert_python_ok("-c", 1174 "import sys; sys.stdout.write(str(sys.warnoptions))", 1175 PYTHONWARNINGS="ignore::DeprecationWarning", 1176 PYTHONDEVMODE="") 1177 self.assertEqual(stdout, b"['ignore::DeprecationWarning']") 1178 1179 def test_comma_separated_warnings(self): 1180 rc, stdout, stderr = assert_python_ok("-c", 1181 "import sys; sys.stdout.write(str(sys.warnoptions))", 1182 PYTHONWARNINGS="ignore::DeprecationWarning,ignore::UnicodeWarning", 1183 PYTHONDEVMODE="") 1184 self.assertEqual(stdout, 1185 b"['ignore::DeprecationWarning', 'ignore::UnicodeWarning']") 1186 1187 def test_envvar_and_command_line(self): 1188 rc, stdout, stderr = assert_python_ok("-Wignore::UnicodeWarning", "-c", 1189 "import sys; sys.stdout.write(str(sys.warnoptions))", 1190 PYTHONWARNINGS="ignore::DeprecationWarning", 1191 PYTHONDEVMODE="") 1192 self.assertEqual(stdout, 1193 b"['ignore::DeprecationWarning', 'ignore::UnicodeWarning']") 1194 1195 def test_conflicting_envvar_and_command_line(self): 1196 rc, stdout, stderr = assert_python_failure("-Werror::DeprecationWarning", "-c", 1197 "import sys, warnings; sys.stdout.write(str(sys.warnoptions)); " 1198 "warnings.warn('Message', DeprecationWarning)", 1199 PYTHONWARNINGS="default::DeprecationWarning", 1200 PYTHONDEVMODE="") 1201 self.assertEqual(stdout, 1202 b"['default::DeprecationWarning', 'error::DeprecationWarning']") 1203 self.assertEqual(stderr.splitlines(), 1204 [b"Traceback (most recent call last):", 1205 b" File \"<string>\", line 1, in <module>", 1206 b"DeprecationWarning: Message"]) 1207 1208 def test_default_filter_configuration(self): 1209 pure_python_api = self.module is py_warnings 1210 if Py_DEBUG: 1211 expected_default_filters = [] 1212 else: 1213 if pure_python_api: 1214 main_module_filter = re.compile("__main__") 1215 else: 1216 main_module_filter = "__main__" 1217 expected_default_filters = [ 1218 ('default', None, DeprecationWarning, main_module_filter, 0), 1219 ('ignore', None, DeprecationWarning, None, 0), 1220 ('ignore', None, PendingDeprecationWarning, None, 0), 1221 ('ignore', None, ImportWarning, None, 0), 1222 ('ignore', None, ResourceWarning, None, 0), 1223 ] 1224 expected_output = [str(f).encode() for f in expected_default_filters] 1225 1226 if pure_python_api: 1227 # Disable the warnings acceleration module in the subprocess 1228 code = "import sys; sys.modules.pop('warnings', None); sys.modules['_warnings'] = None; " 1229 else: 1230 code = "" 1231 code += "import warnings; [print(f) for f in warnings.filters]" 1232 1233 rc, stdout, stderr = assert_python_ok("-c", code, __isolated=True) 1234 stdout_lines = [line.strip() for line in stdout.splitlines()] 1235 self.maxDiff = None 1236 self.assertEqual(stdout_lines, expected_output) 1237 1238 1239 @unittest.skipUnless(sys.getfilesystemencoding() != 'ascii', 1240 'requires non-ascii filesystemencoding') 1241 def test_nonascii(self): 1242 rc, stdout, stderr = assert_python_ok("-c", 1243 "import sys; sys.stdout.write(str(sys.warnoptions))", 1244 PYTHONIOENCODING="utf-8", 1245 PYTHONWARNINGS="ignore:DeprecaciónWarning", 1246 PYTHONDEVMODE="") 1247 self.assertEqual(stdout, 1248 "['ignore:DeprecaciónWarning']".encode('utf-8')) 1249 1250class CEnvironmentVariableTests(EnvironmentVariableTests, unittest.TestCase): 1251 module = c_warnings 1252 1253class PyEnvironmentVariableTests(EnvironmentVariableTests, unittest.TestCase): 1254 module = py_warnings 1255 1256 1257class BootstrapTest(unittest.TestCase): 1258 def test_issue_8766(self): 1259 # "import encodings" emits a warning whereas the warnings is not loaded 1260 # or not completely loaded (warnings imports indirectly encodings by 1261 # importing linecache) yet 1262 with support.temp_cwd() as cwd, support.temp_cwd('encodings'): 1263 # encodings loaded by initfsencoding() 1264 assert_python_ok('-c', 'pass', PYTHONPATH=cwd) 1265 1266 # Use -W to load warnings module at startup 1267 assert_python_ok('-c', 'pass', '-W', 'always', PYTHONPATH=cwd) 1268 1269 1270class FinalizationTest(unittest.TestCase): 1271 @support.requires_type_collecting 1272 def test_finalization(self): 1273 # Issue #19421: warnings.warn() should not crash 1274 # during Python finalization 1275 code = """ 1276import warnings 1277warn = warnings.warn 1278 1279class A: 1280 def __del__(self): 1281 warn("test") 1282 1283a=A() 1284 """ 1285 rc, out, err = assert_python_ok("-c", code) 1286 # note: "__main__" filename is not correct, it should be the name 1287 # of the script 1288 self.assertEqual(err.decode(), '__main__:7: UserWarning: test') 1289 1290 def test_late_resource_warning(self): 1291 # Issue #21925: Emitting a ResourceWarning late during the Python 1292 # shutdown must be logged. 1293 1294 expected = b"sys:1: ResourceWarning: unclosed file " 1295 1296 # don't import the warnings module 1297 # (_warnings will try to import it) 1298 code = "f = open(%a)" % __file__ 1299 rc, out, err = assert_python_ok("-Wd", "-c", code) 1300 self.assertTrue(err.startswith(expected), ascii(err)) 1301 1302 # import the warnings module 1303 code = "import warnings; f = open(%a)" % __file__ 1304 rc, out, err = assert_python_ok("-Wd", "-c", code) 1305 self.assertTrue(err.startswith(expected), ascii(err)) 1306 1307 1308def setUpModule(): 1309 py_warnings.onceregistry.clear() 1310 c_warnings.onceregistry.clear() 1311 1312tearDownModule = setUpModule 1313 1314if __name__ == "__main__": 1315 unittest.main() 1316