[Python-checkins] r79049 - in python/trunk: Doc/library/test.rst Lib/test/test_support.py Lib/test/test_warnings.py

florent.xicluna python-checkins at python.org
Thu Mar 18 20:51:47 CET 2010


Author: florent.xicluna
Date: Thu Mar 18 20:51:47 2010
New Revision: 79049

Log:
#8155: Preserve backward compatibility for test_support.check_warnings().  Add regression tests.


Modified:
   python/trunk/Doc/library/test.rst
   python/trunk/Lib/test/test_support.py
   python/trunk/Lib/test/test_warnings.py

Modified: python/trunk/Doc/library/test.rst
==============================================================================
--- python/trunk/Doc/library/test.rst	(original)
+++ python/trunk/Doc/library/test.rst	Thu Mar 18 20:51:47 2010
@@ -90,17 +90,17 @@
 guidelines to be followed:
 
 * The testing suite should exercise all classes, functions, and constants. This
-  includes not just the external API that is to be presented to the outside world
-  but also "private" code.
+  includes not just the external API that is to be presented to the outside
+  world but also "private" code.
 
 * Whitebox testing (examining the code being tested when the tests are being
   written) is preferred. Blackbox testing (testing only the published user
-  interface) is not complete enough to make sure all boundary and edge cases are
-  tested.
+  interface) is not complete enough to make sure all boundary and edge cases
+  are tested.
 
 * Make sure all possible values are tested including invalid ones. This makes
-  sure that not only all valid values are acceptable but also that improper values
-  are handled correctly.
+  sure that not only all valid values are acceptable but also that improper
+  values are handled correctly.
 
 * Exhaust as many code paths as possible. Test where branching occurs and thus
   tailor input to make sure as many different paths through the code are taken.
@@ -120,8 +120,8 @@
   behavior from side-effects of importing a module.
 
 * Try to maximize code reuse. On occasion, tests will vary by something as small
-  as what type of input is used. Minimize code duplication by subclassing a basic
-  test class with a class that specifies the input::
+  as what type of input is used. Minimize code duplication by subclassing a
+  basic test class with a class that specifies the input::
 
      class TestFuncAcceptsSequences(unittest.TestCase):
 
@@ -155,10 +155,10 @@
 suite. Running the script by itself automatically starts running all regression
 tests in the :mod:`test` package. It does this by finding all modules in the
 package whose name starts with ``test_``, importing them, and executing the
-function :func:`test_main` if present. The names of tests to execute may also be
-passed to the script. Specifying a single regression test (:program:`python
-regrtest.py` :option:`test_spam.py`) will minimize output and only print whether
-the test passed or failed and thus minimize output.
+function :func:`test_main` if present. The names of tests to execute may also
+be passed to the script. Specifying a single regression test (:program:`python
+regrtest.py` :option:`test_spam.py`) will minimize output and only print
+whether the test passed or failed and thus minimize output.
 
 Running :mod:`test.regrtest` directly allows what resources are available for
 tests to use to be set. You do this by using the :option:`-u` command-line
@@ -173,10 +173,10 @@
 regrtest.py` :option:`-h`.
 
 Some other ways to execute the regression tests depend on what platform the
-tests are being executed on. On Unix, you can run :program:`make` :option:`test`
-at the top-level directory where Python was built. On Windows, executing
-:program:`rt.bat` from your :file:`PCBuild` directory will run all regression
-tests.
+tests are being executed on. On Unix, you can run :program:`make`
+:option:`test` at the top-level directory where Python was built. On Windows,
+executing :program:`rt.bat` from your :file:`PCBuild` directory will run all
+regression tests.
 
 
 :mod:`test.test_support` --- Utility functions for tests
@@ -209,8 +209,9 @@
 
 .. exception:: ResourceDenied
 
-   Subclass of :exc:`unittest.SkipTest`. Raised when a resource (such as a network
-   connection) is not available. Raised by the :func:`requires` function.
+   Subclass of :exc:`unittest.SkipTest`. Raised when a resource (such as a
+   network connection) is not available. Raised by the :func:`requires`
+   function.
 
 The :mod:`test.test_support` module defines the following constants:
 
@@ -256,22 +257,23 @@
 .. function:: requires(resource[, msg])
 
    Raise :exc:`ResourceDenied` if *resource* is not available. *msg* is the
-   argument to :exc:`ResourceDenied` if it is raised. Always returns True if called
-   by a function whose ``__name__`` is ``'__main__'``. Used when tests are executed
-   by :mod:`test.regrtest`.
+   argument to :exc:`ResourceDenied` if it is raised. Always returns
+   :const:`True` if called by a function whose ``__name__`` is ``'__main__'``.
+   Used when tests are executed by :mod:`test.regrtest`.
 
 
 .. function:: findfile(filename)
 
-   Return the path to the file named *filename*. If no match is found *filename* is
-   returned. This does not equal a failure since it could be the path to the file.
+   Return the path to the file named *filename*. If no match is found
+   *filename* is returned. This does not equal a failure since it could be the
+   path to the file.
 
 
 .. function:: run_unittest(*classes)
 
    Execute :class:`unittest.TestCase` subclasses passed to the function. The
-   function scans the classes for methods starting with the prefix ``test_`` and
-   executes the tests individually.
+   function scans the classes for methods starting with the prefix ``test_``
+   and executes the tests individually.
 
    It is also legal to pass strings as parameters; these should be keys in
    ``sys.modules``. Each associated module will be scanned by
@@ -284,7 +286,7 @@
    This will run all tests defined in the named module.
 
 
-.. function:: check_warnings(*filters, quiet=False)
+.. function:: check_warnings(*filters, quiet=None)
 
    A convenience wrapper for ``warnings.catch_warnings()`` that makes
    it easier to test that a warning was correctly raised with a single
@@ -292,30 +294,31 @@
    ``warnings.catch_warnings(record=True)``.
 
    It accepts 2-tuples ``("message regexp", WarningCategory)`` as positional
-   arguments. When the optional keyword argument ``quiet`` is True, it does
-   not fail if a filter catches nothing. Without argument, it defaults to::
-
-      check_warnings(("", Warning), quiet=False)
-
-   The main difference is that it verifies the warnings raised. If some filter
-   did not catch any warning, the test fails. If some warnings are not caught,
-   the test fails, too. To disable these checks, use argument ``quiet=True``.
-
-   Another significant difference is that on entry to the context manager, a
-   :class:`WarningRecorder` instance is returned instead of a simple list.
-   The underlying warnings list is available via the recorder object's
-   :attr:`warnings` attribute, while the attributes of the last raised
-   warning are also accessible directly on the object. If no warning has
-   been raised, then the latter attributes will all be :const:`None`.
+   arguments. If there's some ``*filters`` defined, or if the optional keyword
+   argument ``quiet`` is :const:`False`, it checks if the warnings are
+   effective. If some filter did not catch any warning, the test fails. If some
+   warnings are not caught, the test fails, too. To disable these checks, set
+   argument ``quiet`` to :const:`True`.
+
+   Without argument, it defaults to::
+
+      check_warnings(("", Warning), quiet=True)
+
+   Additionally, on entry to the context manager, a :class:`WarningRecorder`
+   instance is returned. The underlying warnings list is available via the
+   recorder object's :attr:`warnings` attribute, while the attributes of the
+   last raised warning are also accessible directly on the object. If no
+   warning has been raised, then the latter attributes will all be
+   :const:`None`.
 
    A :meth:`reset` method is also provided on the recorder object. This
-   method simply clears the warning list.
+   method simply clears the warnings list.
 
    The context manager may be used like this::
 
       import warnings
 
-      with check_warnings():
+      with check_warnings(quiet=False):
           exec('assert(False, "Hey!")')
           warnings.warn(UserWarning("Hide me!"))
 
@@ -337,7 +340,6 @@
 
    .. versionadded:: 2.6
    .. versionchanged:: 2.7
-      The test fails when the context manager do not catch any warning.
       New optional attributes ``*filters`` and ``quiet``.
 
 
@@ -348,8 +350,9 @@
    If ``sys.py3kwarning == 0``, it checks that no warning is raised.
 
    It accepts 2-tuples ``("message regexp", WarningCategory)`` as positional
-   arguments. When the optional keyword argument ``quiet`` is True, it does
-   not fail if a filter catches nothing. Without argument, it defaults to::
+   arguments. When the optional keyword argument ``quiet`` is :const:`True`, it
+   does not fail if a filter catches nothing. Without argument, it defaults
+   to::
 
       check_py3k_warnings(("", DeprecationWarning), quiet=False)
 
@@ -432,11 +435,11 @@
    .. versionadded:: 2.6
 .. class:: EnvironmentVarGuard()
 
-   Class used to temporarily set or unset environment variables.  Instances can be
-   used as a context manager and have a complete dictionary interface for
-   querying/modifying the underlying ``os.environ``. After exit from the context
-   manager all changes to environment variables done through this instance will
-   be rolled back.
+   Class used to temporarily set or unset environment variables.  Instances can
+   be used as a context manager and have a complete dictionary interface for
+   querying/modifying the underlying ``os.environ``. After exit from the
+   context manager all changes to environment variables done through this
+   instance will be rolled back.
 
    .. versionadded:: 2.6
    .. versionchanged:: 2.7
@@ -445,7 +448,8 @@
 
 .. method:: EnvironmentVarGuard.set(envvar, value)
 
-   Temporarily set the environment variable ``envvar`` to the value of ``value``.
+   Temporarily set the environment variable ``envvar`` to the value of
+   ``value``.
 
 
 .. method:: EnvironmentVarGuard.unset(envvar)
@@ -459,4 +463,3 @@
    :func:`check_warnings` above for more details.
 
    .. versionadded:: 2.6
-

Modified: python/trunk/Lib/test/test_support.py
==============================================================================
--- python/trunk/Lib/test/test_support.py	(original)
+++ python/trunk/Lib/test/test_support.py	Thu Mar 18 20:51:47 2010
@@ -577,14 +577,19 @@
 
     Optional argument:
      - if 'quiet' is True, it does not fail if a filter catches nothing
-        (default False)
+        (default True without argument,
+         default False if some filters are defined)
 
     Without argument, it defaults to:
-        check_warnings(("", Warning), quiet=False)
+        check_warnings(("", Warning), quiet=True)
     """
+    quiet = kwargs.get('quiet')
     if not filters:
         filters = (("", Warning),)
-    return _filterwarnings(filters, kwargs.get('quiet'))
+        # Preserve backward compatibility
+        if quiet is None:
+            quiet = True
+    return _filterwarnings(filters, quiet)
 
 
 @contextlib.contextmanager

Modified: python/trunk/Lib/test/test_warnings.py
==============================================================================
--- python/trunk/Lib/test/test_warnings.py	(original)
+++ python/trunk/Lib/test/test_warnings.py	Thu Mar 18 20:51:47 2010
@@ -633,19 +633,33 @@
     def test_check_warnings(self):
         # Explicit tests for the test_support convenience wrapper
         wmod = self.module
-        if wmod is sys.modules['warnings']:
-            with test_support.check_warnings() as w:
-                self.assertEqual(w.warnings, [])
-                wmod.simplefilter("always")
+        if wmod is not sys.modules['warnings']:
+            return
+        with test_support.check_warnings(quiet=False) as w:
+            self.assertEqual(w.warnings, [])
+            wmod.simplefilter("always")
+            wmod.warn("foo")
+            self.assertEqual(str(w.message), "foo")
+            wmod.warn("bar")
+            self.assertEqual(str(w.message), "bar")
+            self.assertEqual(str(w.warnings[0].message), "foo")
+            self.assertEqual(str(w.warnings[1].message), "bar")
+            w.reset()
+            self.assertEqual(w.warnings, [])
+
+        with test_support.check_warnings():
+            # defaults to quiet=True without argument
+            pass
+        with test_support.check_warnings(('foo', UserWarning)):
+            wmod.warn("foo")
+
+        with self.assertRaises(AssertionError):
+            with test_support.check_warnings(('', RuntimeWarning)):
+                # defaults to quiet=False with argument
+                pass
+        with self.assertRaises(AssertionError):
+            with test_support.check_warnings(('foo', RuntimeWarning)):
                 wmod.warn("foo")
-                self.assertEqual(str(w.message), "foo")
-                wmod.warn("bar")
-                self.assertEqual(str(w.message), "bar")
-                self.assertEqual(str(w.warnings[0].message), "foo")
-                self.assertEqual(str(w.warnings[1].message), "bar")
-                w.reset()
-                self.assertEqual(w.warnings, [])
-
 
 
 class CCatchWarningTests(CatchWarningTests):


More information about the Python-checkins mailing list