[Python-checkins] r75231 - in python/branches/py3k: Doc/c-api/init.rst Doc/c-api/unicode.rst Doc/documenting/markup.rst Doc/library/codecs.rst Doc/library/datetime.rst Doc/library/functions.rst Doc/library/hashlib.rst Doc/library/inspect.rst Doc/library/logging.rst Doc/library/shelve.rst Doc/library/stdtypes.rst Doc/library/sys.rst Doc/library/termios.rst Doc/library/threading.rst Doc/library/unittest.rst Doc/tutorial/interpreter.rst Doc/tutorial/modules.rst Doc/whatsnew/2.7.rst Lib/csv.py Lib/getpass.py Lib/inspect.py Lib/logging/__init__.py Lib/multiprocessing/managers.py Lib/platform.py Lib/test/test___all__.py Lib/test/test_csv.py Lib/test/test_socket.py Lib/test/test_unittest.py Lib/textwrap.py Lib/unittest/case.py Lib/unittest/loader.py Lib/unittest/main.py Lib/unittest/suite.py Misc/developers.txt Modules/socketmodule.c

benjamin.peterson python-checkins at python.org
Sun Oct 4 16:49:42 CEST 2009


Author: benjamin.peterson
Date: Sun Oct  4 16:49:41 2009
New Revision: 75231

Log:
Merged revisions 74779-74786,74793,74795,74811,74860-74861,74863,74876,74886,74896,74901,74903,74908,74912,74930,74933,74943,74946,74952-74955,75015,75019,75032,75068,75076,75095,75098,75102,75129,75139,75230 via svnmerge from 
svn+ssh://pythondev@svn.python.org/python/trunk

........
  r74779 | michael.foord | 2009-09-13 11:13:36 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Change to tutorial wording for reading text / binary files on Windows. Issue #6301.
........
  r74780 | michael.foord | 2009-09-13 11:40:02 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Objects that compare equal automatically pass or fail assertAlmostEqual and assertNotAlmostEqual tests on unittest.TestCase. Issue 6567.
........
  r74781 | michael.foord | 2009-09-13 11:46:19 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Note that sys._getframe is not guaranteed to exist in all implementations of Python, and a corresponding note in inspect.currentframe. Issue 6712.
........
  r74782 | michael.foord | 2009-09-13 12:07:46 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Tutorial tweaks. Issue 6849.
........
  r74783 | michael.foord | 2009-09-13 12:28:35 -0500 (Sun, 13 Sep 2009) | 1 line
  
  unittest.TestLoader.loadTestsFromName honors the loader suiteClass attribute. Issue 6866.
........
  r74784 | georg.brandl | 2009-09-13 13:15:07 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Typo fix.
........
  r74785 | michael.foord | 2009-09-13 14:07:03 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Test discovery in unittest will only attempt to import modules that are importable; i.e. their names are valid Python identifiers. If an import fails during discovery this will be recorded as an error and test discovery will continue. Issue 6568.
........
  r74786 | michael.foord | 2009-09-13 14:08:18 -0500 (Sun, 13 Sep 2009) | 1 line
  
  Remove an extraneous space in unittest documentation.
........
  r74793 | georg.brandl | 2009-09-14 09:50:47 -0500 (Mon, 14 Sep 2009) | 1 line
  
  #6908: fix association of hashlib hash attributes.
........
  r74795 | benjamin.peterson | 2009-09-14 22:36:26 -0500 (Mon, 14 Sep 2009) | 1 line
  
  Py_SetPythonHome uses static storage #6913
........
  r74811 | georg.brandl | 2009-09-15 15:26:59 -0500 (Tue, 15 Sep 2009) | 1 line
  
  Add Armin Ronacher.
........
  r74860 | benjamin.peterson | 2009-09-16 21:46:54 -0500 (Wed, 16 Sep 2009) | 1 line
  
  kill bare except
........
  r74861 | benjamin.peterson | 2009-09-16 22:18:28 -0500 (Wed, 16 Sep 2009) | 1 line
  
  pep 8 defaults
........
  r74863 | benjamin.peterson | 2009-09-16 22:27:33 -0500 (Wed, 16 Sep 2009) | 1 line
  
  rationalize a bit
........
  r74876 | georg.brandl | 2009-09-17 11:15:53 -0500 (Thu, 17 Sep 2009) | 1 line
  
  #6932: remove paragraph that advises relying on __del__ being called.
........
  r74886 | benjamin.peterson | 2009-09-17 16:33:46 -0500 (Thu, 17 Sep 2009) | 1 line
  
  use macros
........
  r74896 | georg.brandl | 2009-09-18 02:22:41 -0500 (Fri, 18 Sep 2009) | 1 line
  
  #6936: for interactive use, quit() is just fine.
........
  r74901 | georg.brandl | 2009-09-18 04:14:52 -0500 (Fri, 18 Sep 2009) | 1 line
  
  #6905: use better exception messages in inspect when the argument is of the wrong type.
........
  r74903 | georg.brandl | 2009-09-18 04:18:27 -0500 (Fri, 18 Sep 2009) | 1 line
  
  #6938: "ident" is always a string, so use a format code which works.
........
  r74908 | georg.brandl | 2009-09-18 08:57:11 -0500 (Fri, 18 Sep 2009) | 1 line
  
  Use str.format() to fix beginner's mistake with %-style string formatting.
........
  r74912 | georg.brandl | 2009-09-18 11:19:56 -0500 (Fri, 18 Sep 2009) | 1 line
  
  Optimize optimization and fix method name in docstring.
........
  r74930 | georg.brandl | 2009-09-18 16:21:41 -0500 (Fri, 18 Sep 2009) | 1 line
  
  #6925: rewrite docs for locals() and vars() a bit.
........
  r74933 | georg.brandl | 2009-09-18 16:35:59 -0500 (Fri, 18 Sep 2009) | 1 line
  
  #6930: clarify description about byteorder handling in UTF decoder routines.
........
  r74943 | georg.brandl | 2009-09-19 02:35:07 -0500 (Sat, 19 Sep 2009) | 1 line
  
  #6944: the argument to PyArg_ParseTuple should be a tuple, otherwise a SystemError is set.  Also clean up another usage of PyArg_ParseTuple.
........
  r74946 | georg.brandl | 2009-09-19 03:43:16 -0500 (Sat, 19 Sep 2009) | 1 line
  
  Update bug tracker reference.
........
  r74952 | georg.brandl | 2009-09-19 05:42:34 -0500 (Sat, 19 Sep 2009) | 1 line
  
  #6946: fix duplicate index entries for datetime classes.
........
  r74953 | georg.brandl | 2009-09-19 07:04:16 -0500 (Sat, 19 Sep 2009) | 1 line
  
  Fix references to threading.enumerate().
........
  r74954 | georg.brandl | 2009-09-19 08:13:56 -0500 (Sat, 19 Sep 2009) | 1 line
  
  Add Doug.
........
  r74955 | georg.brandl | 2009-09-19 08:20:49 -0500 (Sat, 19 Sep 2009) | 1 line
  
  Add Mark Summerfield.
........
  r75015 | georg.brandl | 2009-09-22 05:55:08 -0500 (Tue, 22 Sep 2009) | 1 line
  
  Fix encoding name.
........
  r75019 | vinay.sajip | 2009-09-22 12:23:41 -0500 (Tue, 22 Sep 2009) | 1 line
  
  Fixed a typo, and added sections on optimization and using arbitrary objects as messages.
........
  r75032 | benjamin.peterson | 2009-09-22 17:15:28 -0500 (Tue, 22 Sep 2009) | 1 line
  
  fix typos/rephrase
........
  r75068 | benjamin.peterson | 2009-09-25 21:57:59 -0500 (Fri, 25 Sep 2009) | 1 line
  
  comment out ugly xxx
........
  r75076 | vinay.sajip | 2009-09-26 09:53:32 -0500 (Sat, 26 Sep 2009) | 1 line
  
  Tidied up name of parameter in StreamHandler
........
  r75095 | michael.foord | 2009-09-27 14:15:41 -0500 (Sun, 27 Sep 2009) | 1 line
  
  Test creation moved from TestProgram.parseArgs to TestProgram.createTests exclusively. Issue 6956.
........
  r75098 | michael.foord | 2009-09-27 15:08:23 -0500 (Sun, 27 Sep 2009) | 1 line
  
  Documentation improvement for load_tests protocol in unittest. Issue 6515.
........
  r75102 | skip.montanaro | 2009-09-27 21:12:27 -0500 (Sun, 27 Sep 2009) | 3 lines
  
  Patch from Thomas Barr so that csv.Sniffer will set doublequote property.
  Closes issue 6606.
........
  r75129 | vinay.sajip | 2009-09-29 02:08:54 -0500 (Tue, 29 Sep 2009) | 1 line
  
  Issue #7014: logging: Improved IronPython 2.6 compatibility.
........
  r75139 | raymond.hettinger | 2009-09-29 13:53:24 -0500 (Tue, 29 Sep 2009) | 3 lines
  
  Issue 7008: Better document str.title and show how to work around the apostrophe problem.
........
  r75230 | benjamin.peterson | 2009-10-04 08:38:38 -0500 (Sun, 04 Oct 2009) | 1 line
  
  test logging
........


Modified:
   python/branches/py3k/   (props changed)
   python/branches/py3k/Doc/c-api/init.rst
   python/branches/py3k/Doc/c-api/unicode.rst
   python/branches/py3k/Doc/documenting/markup.rst
   python/branches/py3k/Doc/library/codecs.rst
   python/branches/py3k/Doc/library/datetime.rst
   python/branches/py3k/Doc/library/functions.rst
   python/branches/py3k/Doc/library/hashlib.rst
   python/branches/py3k/Doc/library/inspect.rst
   python/branches/py3k/Doc/library/logging.rst
   python/branches/py3k/Doc/library/shelve.rst
   python/branches/py3k/Doc/library/stdtypes.rst
   python/branches/py3k/Doc/library/sys.rst
   python/branches/py3k/Doc/library/termios.rst
   python/branches/py3k/Doc/library/threading.rst
   python/branches/py3k/Doc/library/unittest.rst
   python/branches/py3k/Doc/tutorial/interpreter.rst
   python/branches/py3k/Doc/tutorial/modules.rst
   python/branches/py3k/Doc/whatsnew/2.7.rst
   python/branches/py3k/Lib/csv.py
   python/branches/py3k/Lib/getpass.py
   python/branches/py3k/Lib/inspect.py
   python/branches/py3k/Lib/logging/__init__.py
   python/branches/py3k/Lib/multiprocessing/managers.py
   python/branches/py3k/Lib/platform.py
   python/branches/py3k/Lib/test/test___all__.py
   python/branches/py3k/Lib/test/test_csv.py
   python/branches/py3k/Lib/test/test_socket.py
   python/branches/py3k/Lib/test/test_unittest.py
   python/branches/py3k/Lib/textwrap.py
   python/branches/py3k/Lib/unittest/case.py
   python/branches/py3k/Lib/unittest/loader.py
   python/branches/py3k/Lib/unittest/main.py
   python/branches/py3k/Lib/unittest/suite.py
   python/branches/py3k/Misc/developers.txt
   python/branches/py3k/Modules/socketmodule.c

Modified: python/branches/py3k/Doc/c-api/init.rst
==============================================================================
--- python/branches/py3k/Doc/c-api/init.rst	(original)
+++ python/branches/py3k/Doc/c-api/init.rst	Sun Oct  4 16:49:41 2009
@@ -371,6 +371,10 @@
    Set the default "home" directory, that is, the location of the standard
    Python libraries.  The libraries are searched in
    :file:`{home}/lib/python{version}` and :file:`{home}/lib/python{version}`.
+   The argument should point to a zero-terminated character string in static
+   storage whose contents will not change for the duration of the program's
+   execution.  No code in the Python interpreter will change the contents of
+   this storage.
 
 
 .. cfunction:: w_char* Py_GetPythonHome()

Modified: python/branches/py3k/Doc/c-api/unicode.rst
==============================================================================
--- python/branches/py3k/Doc/c-api/unicode.rst	(original)
+++ python/branches/py3k/Doc/c-api/unicode.rst	Sun Oct  4 16:49:41 2009
@@ -476,10 +476,13 @@
       *byteorder == 0:  native order
       *byteorder == 1:  big endian
 
-   and then switches if the first four bytes of the input data are a byte order mark
-   (BOM) and the specified byte order is native order.  This BOM is not copied into
-   the resulting Unicode string.  After completion, *\*byteorder* is set to the
-   current byte order at the end of input data.
+   If ``*byteorder`` is zero, and the first four bytes of the input data are a
+   byte order mark (BOM), the decoder switches to this byte order and the BOM is
+   not copied into the resulting Unicode string.  If ``*byteorder`` is ``-1`` or
+   ``1``, any byte order mark is copied to the output.
+
+   After completion, *\*byteorder* is set to the current byte order at the end
+   of input data.
 
    In a narrow build codepoints outside the BMP will be decoded as surrogate pairs.
 
@@ -500,8 +503,7 @@
 .. cfunction:: PyObject* PyUnicode_EncodeUTF32(const Py_UNICODE *s, Py_ssize_t size, const char *errors, int byteorder)
 
    Return a Python bytes object holding the UTF-32 encoded value of the Unicode
-   data in *s*.  If *byteorder* is not ``0``, output is written according to the
-   following byte order::
+   data in *s*.  Output is written according to the following byte order::
 
       byteorder == -1: little endian
       byteorder == 0:  native byte order (writes a BOM mark)
@@ -541,10 +543,14 @@
       *byteorder == 0:  native order
       *byteorder == 1:  big endian
 
-   and then switches if the first two bytes of the input data are a byte order mark
-   (BOM) and the specified byte order is native order.  This BOM is not copied into
-   the resulting Unicode string.  After completion, *\*byteorder* is set to the
-   current byte order at the end of input data.
+   If ``*byteorder`` is zero, and the first two bytes of the input data are a
+   byte order mark (BOM), the decoder switches to this byte order and the BOM is
+   not copied into the resulting Unicode string.  If ``*byteorder`` is ``-1`` or
+   ``1``, any byte order mark is copied to the output (where it will result in
+   either a ``\ufeff`` or a ``\ufffe`` character).
+
+   After completion, *\*byteorder* is set to the current byte order at the end
+   of input data.
 
    If *byteorder* is *NULL*, the codec starts in native order mode.
 
@@ -563,8 +569,7 @@
 .. cfunction:: PyObject* PyUnicode_EncodeUTF16(const Py_UNICODE *s, Py_ssize_t size, const char *errors, int byteorder)
 
    Return a Python bytes object holding the UTF-16 encoded value of the Unicode
-   data in *s*.  If *byteorder* is not ``0``, output is written according to the
-   following byte order::
+   data in *s*.  Output is written according to the following byte order::
 
       byteorder == -1: little endian
       byteorder == 0:  native byte order (writes a BOM mark)

Modified: python/branches/py3k/Doc/documenting/markup.rst
==============================================================================
--- python/branches/py3k/Doc/documenting/markup.rst	(original)
+++ python/branches/py3k/Doc/documenting/markup.rst	Sun Oct  4 16:49:41 2009
@@ -597,8 +597,10 @@
    An important bit of information about an API that a user should be aware of
    when using whatever bit of API the warning pertains to.  The content of the
    directive should be written in complete sentences and include all appropriate
-   punctuation.  This should only be chosen over ``note`` for information
-   regarding the possibility of crashes, data loss, or security implications.
+   punctuation.  In the interest of not scaring users away from pages filled
+   with warnings, this directive should only be chosen over ``note`` for
+   information regarding the possibility of crashes, data loss, or security
+   implications.
 
 .. describe:: versionadded
 

Modified: python/branches/py3k/Doc/library/codecs.rst
==============================================================================
--- python/branches/py3k/Doc/library/codecs.rst	(original)
+++ python/branches/py3k/Doc/library/codecs.rst	Sun Oct  4 16:49:41 2009
@@ -988,7 +988,7 @@
 +-----------------+--------------------------------+--------------------------------+
 | cp1255          | windows-1255                   | Hebrew                         |
 +-----------------+--------------------------------+--------------------------------+
-| cp1256          | windows1256                    | Arabic                         |
+| cp1256          | windows-1256                   | Arabic                         |
 +-----------------+--------------------------------+--------------------------------+
 | cp1257          | windows-1257                   | Baltic languages               |
 +-----------------+--------------------------------+--------------------------------+

Modified: python/branches/py3k/Doc/library/datetime.rst
==============================================================================
--- python/branches/py3k/Doc/library/datetime.rst	(original)
+++ python/branches/py3k/Doc/library/datetime.rst	Sun Oct  4 16:49:41 2009
@@ -63,6 +63,7 @@
 
 
 .. class:: date
+   :noindex:
 
    An idealized naive date, assuming the current Gregorian calendar always was, and
    always will be, in effect. Attributes: :attr:`year`, :attr:`month`, and
@@ -70,6 +71,7 @@
 
 
 .. class:: time
+   :noindex:
 
    An idealized time, independent of any particular day, assuming that every day
    has exactly 24\*60\*60 seconds (there is no notion of "leap seconds" here).
@@ -78,6 +80,7 @@
 
 
 .. class:: datetime
+   :noindex:
 
    A combination of a date and a time. Attributes: :attr:`year`, :attr:`month`,
    :attr:`day`, :attr:`hour`, :attr:`minute`, :attr:`second`, :attr:`microsecond`,
@@ -85,6 +88,7 @@
 
 
 .. class:: timedelta
+   :noindex:
 
    A duration expressing the difference between two :class:`date`, :class:`time`,
    or :class:`datetime` instances to microsecond resolution.

Modified: python/branches/py3k/Doc/library/functions.rst
==============================================================================
--- python/branches/py3k/Doc/library/functions.rst	(original)
+++ python/branches/py3k/Doc/library/functions.rst	Sun Oct  4 16:49:41 2009
@@ -600,16 +600,12 @@
 .. function:: locals()
 
    Update and return a dictionary representing the current local symbol table.
+   Free variables are returned by :func:`locals` when it is called in function
+   blocks, but not in class blocks.
 
    .. note::
-
       The contents of this dictionary should not be modified; changes may not
-      affect the values of local variables used by the interpreter.
-
-   Free variables are returned by :func:`locals` when it is called in a function
-   block.  Modifications of free variables may not affect the values used by the
-   interpreter.  Free variables are not returned in class blocks.
-
+      affect the values of local and free variables used by the interpreter.
 
 .. function:: map(function, iterable, ...)
 
@@ -1176,10 +1172,10 @@
 
 .. function:: vars([object])
 
-   Without arguments, return a dictionary corresponding to the current local symbol
-   table.  With a module, class or class instance object as argument (or anything
-   else that has a :attr:`__dict__` attribute), returns a dictionary corresponding
-   to the object's symbol table.
+   Without an argument, act like :func:`locals`.
+
+   With a module, class or class instance object as argument (or anything else that
+   has a :attr:`__dict__` attribute), return that attribute.
 
    .. note::
       The returned dictionary should not be modified:

Modified: python/branches/py3k/Doc/library/hashlib.rst
==============================================================================
--- python/branches/py3k/Doc/library/hashlib.rst	(original)
+++ python/branches/py3k/Doc/library/hashlib.rst	Sun Oct  4 16:49:41 2009
@@ -86,11 +86,11 @@
 returned by the constructors:
 
 
-.. data:: digest_size
+.. data:: hash.digest_size
 
    The size of the resulting hash in bytes.
 
-.. data:: block_size
+.. data:: hash.block_size
 
    The internal block size of the hash algorithm in bytes.
 

Modified: python/branches/py3k/Doc/library/inspect.rst
==============================================================================
--- python/branches/py3k/Doc/library/inspect.rst	(original)
+++ python/branches/py3k/Doc/library/inspect.rst	Sun Oct  4 16:49:41 2009
@@ -508,6 +508,11 @@
 
    Return the frame object for the caller's stack frame.
 
+   This function relies on Python stack frame support in the interpreter, which
+   isn't guaranteed to exist in all implementations of Python. If running in
+   an implementation without Python stack frame support this function returns
+   ``None``.
+
 
 .. function:: stack(context=1)
 

Modified: python/branches/py3k/Doc/library/logging.rst
==============================================================================
--- python/branches/py3k/Doc/library/logging.rst	(original)
+++ python/branches/py3k/Doc/library/logging.rst	Sun Oct  4 16:49:41 2009
@@ -57,7 +57,7 @@
 
    import logging
    LOG_FILENAME = '/tmp/logging_example.out'
-   logging.basicConfig(filename=LOG_FILENAME,level=logging.DEBUG,)
+   logging.basicConfig(filename=LOG_FILENAME,level=logging.DEBUG)
 
    logging.debug('This message should go to the log file')
 
@@ -1493,6 +1493,55 @@
       69 myapp.area2     WARNING  Jail zesty vixen who grabbed pay from quack.
       69 myapp.area2     ERROR    The five boxing wizards jump quickly.
 
+Using arbitrary objects as messages
+-----------------------------------
+
+In the preceding sections and examples, it has been assumed that the message
+passed when logging the event is a string. However, this is not the only
+possibility. You can pass an arbitrary object as a message, and its
+:meth:`__str__` method will be called when the logging system needs to convert
+it to a string representation. In fact, if you want to, you can avoid
+computing a string representation altogether - for example, the
+:class:`SocketHandler` emits an event by pickling it and sending it over the
+wire.
+
+Optimization
+------------
+
+Formatting of message arguments is deferred until it cannot be avoided.
+However, computing the arguments passed to the logging method can also be
+expensive, and you may want to avoid doing it if the logger will just throw
+away your event. To decide what to do, you can call the :meth:`isEnabledFor`
+method which takes a level argument and returns true if the event would be
+created by the Logger for that level of call. You can write code like this::
+
+    if logger.isEnabledFor(logging.DEBUG):
+        logger.debug("Message with %s, %s", expensive_func1(),
+                                            expensive_func2())
+
+so that if the logger's threshold is set above ``DEBUG``, the calls to
+:func:`expensive_func1` and :func:`expensive_func2` are never made.
+
+There are other optimizations which can be made for specific applications which
+need more precise control over what logging information is collected. Here's a
+list of things you can do to avoid processing during logging which you don't
+need:
+
++-----------------------------------------------+----------------------------------------+
+| What you don't want to collect                | How to avoid collecting it             |
++===============================================+========================================+
+| Information about where calls were made from. | Set ``logging._srcfile`` to ``None``.  |
++-----------------------------------------------+----------------------------------------+
+| Threading information.                        | Set ``logging.logThreads`` to ``0``.   |
++-----------------------------------------------+----------------------------------------+
+| Process information.                          | Set ``logging.logProcesses`` to ``0``. |
++-----------------------------------------------+----------------------------------------+
+
+Also note that the core logging module only includes the basic handlers. If
+you don't import :mod:`logging.handlers` and :mod:`logging.config`, they won't
+take up any memory.
+
+.. _handler:
 
 Handler Objects
 ---------------
@@ -1608,9 +1657,9 @@
 and :meth:`flush` methods).
 
 
-.. class:: StreamHandler(strm=None)
+.. class:: StreamHandler(stream=None)
 
-   Returns a new instance of the :class:`StreamHandler` class. If *strm* is
+   Returns a new instance of the :class:`StreamHandler` class. If *stream* is
    specified, the instance will use it for logging output; otherwise, *sys.stderr*
    will be used.
 

Modified: python/branches/py3k/Doc/library/shelve.rst
==============================================================================
--- python/branches/py3k/Doc/library/shelve.rst	(original)
+++ python/branches/py3k/Doc/library/shelve.rst	Sun Oct  4 16:49:41 2009
@@ -27,27 +27,39 @@
 
    Because of Python semantics, a shelf cannot know when a mutable
    persistent-dictionary entry is modified.  By default modified objects are
-   written only when assigned to the shelf (see :ref:`shelve-example`).  If
-   the optional *writeback* parameter is set to *True*, all entries accessed
-   are cached in memory, and written back at close time; this can make it
-   handier to mutate mutable entries in the persistent dictionary, but, if
-   many entries are accessed, it can consume vast amounts of memory for the
-   cache, and it can make the close operation very slow since all accessed
-   entries are written back (there is no way to determine which accessed
-   entries are mutable, nor which ones were actually mutated).
+   written only when assigned to the shelf (see :ref:`shelve-example`).  If the
+   optional *writeback* parameter is set to *True*, all entries accessed are
+   cached in memory, and written back on :meth:`sync` and :meth:`close`; this
+   can make it handier to mutate mutable entries in the persistent dictionary,
+   but, if many entries are accessed, it can consume vast amounts of memory for
+   the cache, and it can make the close operation very slow since all accessed
+   entries are written back (there is no way to determine which accessed entries
+   are mutable, nor which ones were actually mutated).
+
+   .. note::
+
+      Do not rely on the shelf being closed automatically; always call
+      :meth:`close` explicitly when you don't need it any more, or use a
+      :keyword:`with` statement with :func:`contextlib.closing`.
+
 
 Shelf objects support all methods supported by dictionaries.  This eases the
 transition from dictionary based scripts to those requiring persistent storage.
 
-One additional method is supported:
-
+Two additional methods are supported:
 
 .. method:: Shelf.sync()
 
-   Write back all entries in the cache if the shelf was opened with *writeback* set
-   to *True*. Also empty the cache and synchronize the persistent dictionary on
-   disk, if feasible.  This is called automatically when the shelf is closed with
-   :meth:`close`.
+   Write back all entries in the cache if the shelf was opened with *writeback*
+   set to :const:`True`.  Also empty the cache and synchronize the persistent
+   dictionary on disk, if feasible.  This is called automatically when the shelf
+   is closed with :meth:`close`.
+
+.. method:: Shelf.close()
+
+   Synchronize and close the persistent *dict* object.  Operations on a closed
+   shelf will fail with a :exc:`ValueError`.
+
 
 .. seealso::
 
@@ -71,11 +83,6 @@
   database should be fairly small, and in rare cases key collisions may cause
   the database to refuse updates.
 
-* Depending on the implementation, closing a persistent dictionary may or may
-  not be necessary to flush changes to disk.  The :meth:`__del__` method of the
-  :class:`Shelf` class calls the :meth:`close` method, so the programmer generally
-  need not do this explicitly.
-
 * The :mod:`shelve` module does not support *concurrent* read/write access to
   shelved objects.  (Multiple simultaneous read accesses are safe.)  When a
   program has a shelf open for writing, no other program should have it open for

Modified: python/branches/py3k/Doc/library/stdtypes.rst
==============================================================================
--- python/branches/py3k/Doc/library/stdtypes.rst	(original)
+++ python/branches/py3k/Doc/library/stdtypes.rst	Sun Oct  4 16:49:41 2009
@@ -1149,6 +1149,8 @@
         >>> titlecase("they're bill's friends.")
         "They're Bill's Friends."
 
+   For 8-bit strings, this method is locale-dependent.
+
 
 .. method:: str.translate(map)
 

Modified: python/branches/py3k/Doc/library/sys.rst
==============================================================================
--- python/branches/py3k/Doc/library/sys.rst	(original)
+++ python/branches/py3k/Doc/library/sys.rst	Sun Oct  4 16:49:41 2009
@@ -337,12 +337,12 @@
    does not have to hold true for third-party extensions as it is implementation
    specific.
 
-   The *default* argument allows to define a value which will be returned
-   if the object type does not provide means to retrieve the size and would
-   cause a `TypeError`.
+   If given, *default* will be returned if the object does not provide means to
+   retrieve the size.  Otherwise a `TypeError` will be raised.
 
-   :func:`getsizeof` calls the object's __sizeof__ method and adds an additional
-   garbage collector overhead if the object is managed by the garbage collector.
+   :func:`getsizeof` calls the object's ``__sizeof__`` method and adds an
+   additional garbage collector overhead if the object is managed by the garbage
+   collector.
 
 
 .. function:: _getframe([depth])
@@ -352,7 +352,8 @@
    that is deeper than the call stack, :exc:`ValueError` is raised.  The default
    for *depth* is zero, returning the frame at the top of the call stack.
 
-   This function should be used for internal and specialized purposes only.
+   This function should be used for internal and specialized purposes only. It
+   is not guaranteed to exist in all implementations of Python.
 
 
 .. function:: getprofile()

Modified: python/branches/py3k/Doc/library/termios.rst
==============================================================================
--- python/branches/py3k/Doc/library/termios.rst	(original)
+++ python/branches/py3k/Doc/library/termios.rst	Sun Oct  4 16:49:41 2009
@@ -89,7 +89,7 @@
 :keyword:`finally` statement to ensure that the old tty attributes are restored
 exactly no matter what happens::
 
-   def getpass(prompt = "Password: "):
+   def getpass(prompt="Password: "):
        import termios, sys
        fd = sys.stdin.fileno()
        old = termios.tcgetattr(fd)

Modified: python/branches/py3k/Doc/library/threading.rst
==============================================================================
--- python/branches/py3k/Doc/library/threading.rst	(original)
+++ python/branches/py3k/Doc/library/threading.rst	Sun Oct  4 16:49:41 2009
@@ -23,7 +23,7 @@
 .. function:: active_count()
 
    Return the number of :class:`Thread` objects currently alive.  The returned
-   count is equal to the length of the list returned by :func:`enumerate`.
+   count is equal to the length of the list returned by :func:`.enumerate`.
 
 
 .. function:: Condition()
@@ -301,7 +301,7 @@
 
       Roughly, a thread is alive from the moment the :meth:`start` method
       returns until its :meth:`run` method terminates. The module function
-      :func:`enumerate` returns a list of all alive threads.
+      :func:`.enumerate` returns a list of all alive threads.
 
    .. attribute:: daemon
 

Modified: python/branches/py3k/Doc/library/unittest.rst
==============================================================================
--- python/branches/py3k/Doc/library/unittest.rst	(original)
+++ python/branches/py3k/Doc/library/unittest.rst	Sun Oct  4 16:49:41 2009
@@ -728,6 +728,9 @@
       compare equal, the test will fail with the explanation given by *msg*, or
       :const:`None`.
 
+      .. versionchanged:: 3.2
+         Objects that compare equal are automatically almost equal.
+
       .. deprecated:: 3.1
          :meth:`failUnlessAlmostEqual`.
 
@@ -744,6 +747,9 @@
       compare equal, the test will fail with the explanation given by *msg*, or
       :const:`None`.
 
+      .. versionchanged:: 3.2
+         Objects that compare equal automatically fail.
+
       .. deprecated:: 3.1
          :meth:`failIfAlmostEqual`.
 
@@ -1244,18 +1250,23 @@
 
       Find and return all test modules from the specified start directory,
       recursing into subdirectories to find them. Only test files that match
-      *pattern* will be loaded. (Using shell style pattern matching.)
+      *pattern* will be loaded. (Using shell style pattern matching.) Only
+      module names that are importable (i.e. are valid Python identifiers) will
+      be loaded.
 
       All test modules must be importable from the top level of the project. If
       the start directory is not the top level directory then the top level
       directory must be specified separately.
 
+      If importing a module fails, for example due to a syntax error, then this
+      will be recorded as a single error and discovery will continue.
+
       If a test package name (directory with :file:`__init__.py`) matches the
       pattern then the package will be checked for a ``load_tests``
       function. If this exists then it will be called with *loader*, *tests*,
       *pattern*.
 
-      If load_tests exists then discovery does  *not* recurse into the package,
+      If load_tests exists then discovery does *not* recurse into the package,
       ``load_tests`` is responsible for loading all tests in the package.
 
       The pattern is deliberately not stored as a loader attribute so that
@@ -1263,6 +1274,7 @@
       ``load_tests`` does not need to pass this argument in to
       ``loader.discover()``.
 
+      .. versionadded:: 2.7
 
    The following attributes of a :class:`TestLoader` can be configured either by
    subclassing or assignment on an instance:
@@ -1518,6 +1530,10 @@
 load_tests Protocol
 ###################
 
+
+.. versionadded:: 2.7
+
+
 Modules or packages can customize how tests are loaded from them during normal
 test runs or test discovery by implementing a function called ``load_tests``.
 

Modified: python/branches/py3k/Doc/tutorial/interpreter.rst
==============================================================================
--- python/branches/py3k/Doc/tutorial/interpreter.rst	(original)
+++ python/branches/py3k/Doc/tutorial/interpreter.rst	Sun Oct  4 16:49:41 2009
@@ -31,7 +31,7 @@
 Typing an end-of-file character (:kbd:`Control-D` on Unix, :kbd:`Control-Z` on
 Windows) at the primary prompt causes the interpreter to exit with a zero exit
 status.  If that doesn't work, you can exit the interpreter by typing the
-following commands: ``import sys; sys.exit()``.
+following command: ``quit()``.
 
 The interpreter's line-editing features usually aren't very sophisticated.  On
 Unix, whoever installed the interpreter may have enabled support for the GNU

Modified: python/branches/py3k/Doc/tutorial/modules.rst
==============================================================================
--- python/branches/py3k/Doc/tutorial/modules.rst	(original)
+++ python/branches/py3k/Doc/tutorial/modules.rst	Sun Oct  4 16:49:41 2009
@@ -107,6 +107,10 @@
 an unknown set of names into the interpreter, possibly hiding some things
 you have already defined.
 
+Note that in general the practice of importing ``*`` from a module or package is
+frowned upon, since it often causes poorly readable code. However, it is okay to
+use it to save typing in interactive sessions.
+
 .. note::
 
    For efficiency reasons, each module is only imported once per interpreter
@@ -445,14 +449,9 @@
 
 Now what happens when the user writes ``from sound.effects import *``?  Ideally,
 one would hope that this somehow goes out to the filesystem, finds which
-submodules are present in the package, and imports them all.  Unfortunately,
-this operation does not work very well on Windows platforms, where the
-filesystem does not always have accurate information about the case of a
-filename.  On these platforms, there is no guaranteed way to know whether a file
-:file:`ECHO.PY` should be imported as a module :mod:`echo`, :mod:`Echo` or
-:mod:`ECHO`.  (For example, Windows 95 has the annoying practice of showing all
-file names with a capitalized first letter.)  The DOS 8+3 filename restriction
-adds another interesting problem for long module names.
+submodules are present in the package, and imports them all.  This could take a
+long time and importing sub-modules might have unwanted side-effects that should
+only happen when the sub-module is explicitly imported.
 
 The only solution is for the package author to provide an explicit index of the
 package.  The :keyword:`import` statement uses the following convention: if a package's
@@ -487,10 +486,9 @@
 when the ``from...import`` statement is executed.  (This also works when
 ``__all__`` is defined.)
 
-Note that in general the practice of importing ``*`` from a module or package is
-frowned upon, since it often causes poorly readable code. However, it is okay to
-use it to save typing in interactive sessions, and certain modules are designed
-to export only names that follow certain patterns.
+Although certain modules are designed to export only names that follow certain
+patterns when you use ``import *``, it is still considered bad practise in
+production code.
 
 Remember, there is nothing wrong with using ``from Package import
 specific_submodule``!  In fact, this is the recommended notation unless the

Modified: python/branches/py3k/Doc/whatsnew/2.7.rst
==============================================================================
--- python/branches/py3k/Doc/whatsnew/2.7.rst	(original)
+++ python/branches/py3k/Doc/whatsnew/2.7.rst	Sun Oct  4 16:49:41 2009
@@ -505,6 +505,13 @@
     differences.  :meth:`assertDictContainsSubset` checks whether
     all of the key/value pairs in *first* are found in *second*.
 
+  * :meth:`assertAlmostEqual` and :meth:`assertNotAlmostEqual` short-circuit
+    (automatically pass or fail without checking decimal places) if the objects
+    are equal.
+
+  * :meth:`loadTestsFromName` properly honors the ``suiteClass`` attribute of
+    the :class:`TestLoader`. (Fixed by Mark Roddy; :issue:`6866`.)
+
   * A new hook, :meth:`addTypeEqualityFunc` takes a type object and a
     function.  The :meth:`assertEqual` method will use the function
     when both of the objects being compared are of the specified type.

Modified: python/branches/py3k/Lib/csv.py
==============================================================================
--- python/branches/py3k/Lib/csv.py	(original)
+++ python/branches/py3k/Lib/csv.py	Sun Oct  4 16:49:41 2009
@@ -165,7 +165,7 @@
         Returns a dialect (or None) corresponding to the sample
         """
 
-        quotechar, delimiter, skipinitialspace = \
+        quotechar, doublequote, delimiter, skipinitialspace = \
                    self._guess_quote_and_delimiter(sample, delimiters)
         if not delimiter:
             delimiter, skipinitialspace = self._guess_delimiter(sample,
@@ -179,8 +179,8 @@
             lineterminator = '\r\n'
             quoting = QUOTE_MINIMAL
             # escapechar = ''
-            doublequote = False
 
+        dialect.doublequote = doublequote
         dialect.delimiter = delimiter
         # _csv.reader won't accept a quotechar of ''
         dialect.quotechar = quotechar or '"'
@@ -212,8 +212,8 @@
                 break
 
         if not matches:
-            return ('', None, 0) # (quotechar, delimiter, skipinitialspace)
-
+            # (quotechar, doublequote, delimiter, skipinitialspace)
+            return ('', False, None, 0)
         quotes = {}
         delims = {}
         spaces = 0
@@ -248,7 +248,19 @@
             delim = ''
             skipinitialspace = 0
 
-        return (quotechar, delim, skipinitialspace)
+        # if we see an extra quote between delimiters, we've got a
+        # double quoted format
+        dq_regexp = re.compile(r"((%(delim)s)|^)\W*%(quote)s[^%(delim)s\n]*%(quote)s[^%(delim)s\n]*%(quote)s\W*((%(delim)s)|$)" % \
+                               {'delim':delim, 'quote':quotechar}, re.MULTILINE)
+
+
+
+        if dq_regexp.search(data):
+            doublequote = True
+        else:
+            doublequote = False
+
+        return (quotechar, doublequote, delim, skipinitialspace)
 
 
     def _guess_delimiter(self, data, delimiters):

Modified: python/branches/py3k/Lib/getpass.py
==============================================================================
--- python/branches/py3k/Lib/getpass.py	(original)
+++ python/branches/py3k/Lib/getpass.py	Sun Oct  4 16:49:41 2009
@@ -51,7 +51,7 @@
         # If that fails, see if stdin can be controlled.
         try:
             fd = sys.stdin.fileno()
-        except:
+        except (AttributeError, ValueError):
             passwd = fallback_getpass(prompt, stream)
         input = sys.stdin
         if not stream:

Modified: python/branches/py3k/Lib/inspect.py
==============================================================================
--- python/branches/py3k/Lib/inspect.py	(original)
+++ python/branches/py3k/Lib/inspect.py	Sun Oct  4 16:49:41 2009
@@ -398,12 +398,12 @@
     if ismodule(object):
         if hasattr(object, '__file__'):
             return object.__file__
-        raise TypeError('arg is a built-in module')
+        raise TypeError('{!r} is a built-in module'.format(object))
     if isclass(object):
         object = sys.modules.get(object.__module__)
         if hasattr(object, '__file__'):
             return object.__file__
-        raise TypeError('arg is a built-in class')
+        raise TypeError('{!r} is a built-in class'.format(object))
     if ismethod(object):
         object = object.__func__
     if isfunction(object):
@@ -414,8 +414,8 @@
         object = object.f_code
     if iscode(object):
         return object.co_filename
-    raise TypeError('arg is not a module, class, method, '
-                    'function, traceback, frame, or code object')
+    raise TypeError('{!r} is not a module, class, method, '
+                    'function, traceback, frame, or code object'.format(object))
 
 ModuleInfo = namedtuple('ModuleInfo', 'name suffix mode module_type')
 
@@ -747,7 +747,7 @@
     names of the * and ** arguments or None."""
 
     if not iscode(co):
-        raise TypeError('arg is not a code object')
+        raise TypeError('{!r} is not a code object'.format(co))
 
     nargs = co.co_argcount
     names = co.co_varnames
@@ -811,7 +811,7 @@
     if ismethod(func):
         func = func.__func__
     if not isfunction(func):
-        raise TypeError('arg is not a Python function')
+        raise TypeError('{!r} is not a Python function'.format(func))
     args, varargs, kwonlyargs, varkw = _getfullargs(func.__code__)
     return FullArgSpec(args, varargs, varkw, func.__defaults__,
             kwonlyargs, func.__kwdefaults__, func.__annotations__)
@@ -944,7 +944,7 @@
     else:
         lineno = frame.f_lineno
     if not isframe(frame):
-        raise TypeError('arg is not a frame or traceback object')
+        raise TypeError('{!r} is not a frame or traceback object'.format(frame))
 
     filename = getsourcefile(frame) or getfile(frame)
     if context > 0:

Modified: python/branches/py3k/Lib/logging/__init__.py
==============================================================================
--- python/branches/py3k/Lib/logging/__init__.py	(original)
+++ python/branches/py3k/Lib/logging/__init__.py	Sun Oct  4 16:49:41 2009
@@ -282,11 +282,14 @@
         else:
             self.thread = None
             self.threadName = None
-        if logMultiprocessing:
-            from multiprocessing import current_process
-            self.processName = current_process().name
-        else:
+        if not logMultiprocessing:
             self.processName = None
+        else:
+            try:
+                from multiprocessing import current_process
+                self.processName = current_process().name
+            except ImportError:
+                self.processName = None
         if logProcesses and hasattr(os, 'getpid'):
             self.process = os.getpid()
         else:
@@ -745,16 +748,16 @@
     sys.stdout or sys.stderr may be used.
     """
 
-    def __init__(self, strm=None):
+    def __init__(self, stream=None):
         """
         Initialize the handler.
 
-        If strm is not specified, sys.stderr is used.
+        If stream is not specified, sys.stderr is used.
         """
         Handler.__init__(self)
-        if strm is None:
-            strm = sys.stderr
-        self.stream = strm
+        if stream is None:
+            stream = sys.stderr
+        self.stream = stream
 
     def flush(self):
         """
@@ -1124,7 +1127,11 @@
         Find the stack frame of the caller so that we can note the source
         file name, line number and function name.
         """
-        f = currentframe().f_back
+        f = currentframe()
+        #On some versions of IronPython, currentframe() returns None if
+        #IronPython isn't run with -X:Frames.
+        if f is not None:
+            f = f.f_back
         rv = "(unknown file)", 0, "(unknown function)"
         while hasattr(f, "f_code"):
             co = f.f_code
@@ -1156,7 +1163,8 @@
         """
         if _srcfile:
             #IronPython doesn't track Python frames, so findCaller throws an
-            #exception. We trap it here so that IronPython can use logging.
+            #exception on some versions of IronPython. We trap it here so that
+            #IronPython can use logging.
             try:
                 fn, lno, func = self.findCaller()
             except ValueError:

Modified: python/branches/py3k/Lib/multiprocessing/managers.py
==============================================================================
--- python/branches/py3k/Lib/multiprocessing/managers.py	(original)
+++ python/branches/py3k/Lib/multiprocessing/managers.py	Sun Oct  4 16:49:41 2009
@@ -413,7 +413,7 @@
             self.id_to_refcount[ident] -= 1
             if self.id_to_refcount[ident] == 0:
                 del self.id_to_obj[ident], self.id_to_refcount[ident]
-                util.debug('disposing of obj with id %d', ident)
+                util.debug('disposing of obj with id %r', ident)
         finally:
             self.mutex.release()
 

Modified: python/branches/py3k/Lib/platform.py
==============================================================================
--- python/branches/py3k/Lib/platform.py	(original)
+++ python/branches/py3k/Lib/platform.py	Sun Oct  4 16:49:41 2009
@@ -10,7 +10,7 @@
 """
 #    This module is maintained by Marc-Andre Lemburg <mal at egenix.com>.
 #    If you find problems, please submit bug reports/patches via the
-#    Python SourceForge Project Page and assign them to "lemburg".
+#    Python bug tracker (http://bugs.python.org) and assign them to "lemburg".
 #
 #    Still needed:
 #    * more support for WinCE

Modified: python/branches/py3k/Lib/test/test___all__.py
==============================================================================
--- python/branches/py3k/Lib/test/test___all__.py	(original)
+++ python/branches/py3k/Lib/test/test___all__.py	Sun Oct  4 16:49:41 2009
@@ -82,6 +82,7 @@
         self.check_all("keyword")
         self.check_all("linecache")
         self.check_all("locale")
+        self.check_all("logging")
         self.check_all("macpath")
         self.check_all("macurl2path")
         self.check_all("mailbox")

Modified: python/branches/py3k/Lib/test/test_csv.py
==============================================================================
--- python/branches/py3k/Lib/test/test_csv.py	(original)
+++ python/branches/py3k/Lib/test/test_csv.py	Sun Oct  4 16:49:41 2009
@@ -767,7 +767,7 @@
 'Harry''s':'Arlington Heights':'IL':'2/1/03':'Kimi Hayes'
 'Shark City':'Glendale Heights':'IL':'12/28/02':'Prezence'
 'Tommy''s Place':'Blue Island':'IL':'12/28/02':'Blue Sunday/White Crow'
-'Stonecutters Seafood and Chop House':'Lemont':'IL':'12/19/02':'Week Back'
+'Stonecutters ''Seafood'' and Chop House':'Lemont':'IL':'12/19/02':'Week Back'
 """
     header = '''\
 "venue","city","state","date","performers"
@@ -826,6 +826,13 @@
         self.assertEqual(dialect.delimiter, "|")
         self.assertEqual(dialect.quotechar, "'")
 
+    def test_doublequote(self):
+        sniffer = csv.Sniffer()
+        dialect = sniffer.sniff(self.header)
+        self.assertFalse(dialect.doublequote)
+        dialect = sniffer.sniff(self.sample2)
+        self.assertTrue(dialect.doublequote)
+
 if not hasattr(sys, "gettotalrefcount"):
     if support.verbose: print("*** skipping leakage tests ***")
 else:

Modified: python/branches/py3k/Lib/test/test_socket.py
==============================================================================
--- python/branches/py3k/Lib/test/test_socket.py	(original)
+++ python/branches/py3k/Lib/test/test_socket.py	Sun Oct  4 16:49:41 2009
@@ -291,7 +291,7 @@
                 # On some versions, this loses a reference
                 orig = sys.getrefcount(__name__)
                 socket.getnameinfo(__name__,0)
-            except SystemError:
+            except TypeError:
                 if sys.getrefcount(__name__) != orig:
                     self.fail("socket.getnameinfo loses a reference")
 

Modified: python/branches/py3k/Lib/test/test_unittest.py
==============================================================================
--- python/branches/py3k/Lib/test/test_unittest.py	(original)
+++ python/branches/py3k/Lib/test/test_unittest.py	Sun Oct  4 16:49:41 2009
@@ -555,6 +555,47 @@
         self.assertEqual(list(suite), [testcase_1])
 
     # "The specifier name is a ``dotted name'' that may resolve ... to
+    # ... a callable object which returns a TestCase ... instance"
+    #*****************************************************************
+    #Override the suiteClass attribute to ensure that the suiteClass
+    #attribute is used
+    def test_loadTestsFromName__callable__TestCase_instance_ProperSuiteClass(self):
+        class SubTestSuite(unittest.TestSuite):
+            pass
+        m = types.ModuleType('m')
+        testcase_1 = unittest.FunctionTestCase(lambda: None)
+        def return_TestCase():
+            return testcase_1
+        m.return_TestCase = return_TestCase
+
+        loader = unittest.TestLoader()
+        loader.suiteClass = SubTestSuite
+        suite = loader.loadTestsFromName('return_TestCase', m)
+        self.assertTrue(isinstance(suite, loader.suiteClass))
+        self.assertEqual(list(suite), [testcase_1])
+
+    # "The specifier name is a ``dotted name'' that may resolve ... to
+    # ... a test method within a test case class"
+    #*****************************************************************
+    #Override the suiteClass attribute to ensure that the suiteClass
+    #attribute is used
+    def test_loadTestsFromName__relative_testmethod_ProperSuiteClass(self):
+        class SubTestSuite(unittest.TestSuite):
+            pass
+        m = types.ModuleType('m')
+        class MyTestCase(unittest.TestCase):
+            def test(self):
+                pass
+        m.testcase_1 = MyTestCase
+
+        loader = unittest.TestLoader()
+        loader.suiteClass=SubTestSuite
+        suite = loader.loadTestsFromName('testcase_1.test', m)
+        self.assertTrue(isinstance(suite, loader.suiteClass))
+
+        self.assertEqual(list(suite), [MyTestCase('test')])
+
+    # "The specifier name is a ``dotted name'' that may resolve ... to
     # ... a callable object which returns a TestCase or TestSuite instance"
     #
     # What happens if the callable returns something else?
@@ -2953,6 +2994,11 @@
         self.assertRaises(self.failureException,
                           self.assertNotAlmostEqual, 0, .1+.1j, places=0)
 
+        self.assertAlmostEqual(float('inf'), float('inf'))
+        self.assertRaises(self.failureException, self.assertNotAlmostEqual,
+                          float('inf'), float('inf'))
+
+
     def test_assertRaises(self):
         def _raise(e):
             raise e
@@ -3387,31 +3433,18 @@
 class TestDiscovery(TestCase):
 
     # Heavily mocked tests so I can avoid hitting the filesystem
-    def test_get_module_from_path(self):
+    def test_get_name_from_path(self):
         loader = unittest.TestLoader()
-
-        old_import = __import__
-        def restore_import():
-            builtins.__import__ = old_import
-        builtins.__import__ = lambda *_: None
-        self.addCleanup(restore_import)
-
-        expected_module = object()
-        def del_module():
-            del sys.modules['bar.baz']
-        sys.modules['bar.baz'] = expected_module
-        self.addCleanup(del_module)
-
         loader._top_level_dir = '/foo'
-        module = loader._get_module_from_path('/foo/bar/baz.py')
-        self.assertEqual(module, expected_module)
+        name = loader._get_name_from_path('/foo/bar/baz.py')
+        self.assertEqual(name, 'bar.baz')
 
         if not __debug__:
             # asserts are off
             return
 
         with self.assertRaises(AssertionError):
-            loader._get_module_from_path('/bar/baz.py')
+            loader._get_name_from_path('/bar/baz.py')
 
     def test_find_tests(self):
         loader = unittest.TestLoader()
@@ -3427,7 +3460,7 @@
             os.path.isdir = original_isdir
 
         path_lists = [['test1.py', 'test2.py', 'not_a_test.py', 'test_dir',
-                       'test.foo', 'another_dir'],
+                       'test.foo', 'test-not-a-module.py', 'another_dir'],
                       ['test3.py', 'test4.py', ]]
         os.listdir = lambda path: path_lists.pop(0)
         self.addCleanup(restore_listdir)
@@ -3443,16 +3476,16 @@
         os.path.isfile = isfile
         self.addCleanup(restore_isfile)
 
-        loader._get_module_from_path = lambda path: path + ' module'
+        loader._get_module_from_name = lambda path: path + ' module'
         loader.loadTestsFromModule = lambda module: module + ' tests'
 
         loader._top_level_dir = '/foo'
         suite = list(loader._find_tests('/foo', 'test*.py'))
 
-        expected = [os.path.join('/foo', name) + ' module tests' for name in
-                    ('test1.py', 'test2.py')]
-        expected.extend([os.path.join('/foo', 'test_dir', name) + ' module tests' for name in
-                    ('test3.py', 'test4.py')])
+        expected = [name + ' module tests' for name in
+                    ('test1', 'test2')]
+        expected.extend([('test_dir.%s' % name) + ' module tests' for name in
+                    ('test3', 'test4')])
         self.assertEqual(suite, expected)
 
     def test_find_tests_with_package(self):
@@ -3495,7 +3528,7 @@
             def __eq__(self, other):
                 return self.path == other.path
 
-        loader._get_module_from_path = lambda path: Module(path)
+        loader._get_module_from_name = lambda name: Module(name)
         def loadTestsFromModule(module, use_load_tests):
             if use_load_tests:
                 raise self.failureException('use_load_tests should be False for packages')
@@ -3510,15 +3543,12 @@
         # We should have loaded tests from the test_directory package by calling load_tests
         # and directly from the test_directory2 package
         self.assertEqual(suite,
-                         ['load_tests',
-                          os.path.join('/foo', 'test_directory2') + ' module tests'])
-        self.assertEqual(Module.paths, [os.path.join('/foo', 'test_directory'),
-                                        os.path.join('/foo', 'test_directory2')])
+                         ['load_tests', 'test_directory2' + ' module tests'])
+        self.assertEqual(Module.paths, ['test_directory', 'test_directory2'])
 
         # load_tests should have been called once with loader, tests and pattern
         self.assertEqual(Module.load_tests_args,
-                         [(loader, os.path.join('/foo', 'test_directory') + ' module tests',
-                           'test*')])
+                         [(loader, 'test_directory' + ' module tests', 'test*')])
 
     def test_discover(self):
         loader = unittest.TestLoader()
@@ -3558,6 +3588,25 @@
         self.assertEqual(loader._top_level_dir, top_level_dir)
         self.assertEqual(_find_tests_args, [(start_dir, 'pattern')])
 
+    def test_discover_with_modules_that_fail_to_import(self):
+        loader = unittest.TestLoader()
+
+        listdir = os.listdir
+        os.listdir = lambda _: ['test_this_does_not_exist.py']
+        isfile = os.path.isfile
+        os.path.isfile = lambda _: True
+        def restore():
+            os.path.isfile = isfile
+            os.listdir = listdir
+        self.addCleanup(restore)
+
+        suite = loader.discover('.')
+        self.assertEqual(suite.countTestCases(), 1)
+        test = list(list(suite)[0])[0] # extract test from suite
+
+        with self.assertRaises(ImportError):
+            test.test_this_does_not_exist()
+
     def test_command_line_handling_parseArgs(self):
         # Haha - take that uninstantiable class
         program = object.__new__(TestProgram)

Modified: python/branches/py3k/Lib/textwrap.py
==============================================================================
--- python/branches/py3k/Lib/textwrap.py	(original)
+++ python/branches/py3k/Lib/textwrap.py	Sun Oct  4 16:49:41 2009
@@ -135,7 +135,7 @@
         """_split(text : string) -> [string]
 
         Split the text to wrap into indivisible chunks.  Chunks are
-        not quite the same as words; see wrap_chunks() for full
+        not quite the same as words; see _wrap_chunks() for full
         details.  As an example, the text
           Look, goof-ball -- use the -b option!
         breaks into the following chunks:
@@ -163,9 +163,9 @@
         space to two.
         """
         i = 0
-        pat = self.sentence_end_re
+        patsearch = self.sentence_end_re.search
         while i < len(chunks)-1:
-            if chunks[i+1] == " " and pat.search(chunks[i]):
+            if chunks[i+1] == " " and patsearch(chunks[i]):
                 chunks[i+1] = "  "
                 i += 2
             else:

Modified: python/branches/py3k/Lib/unittest/case.py
==============================================================================
--- python/branches/py3k/Lib/unittest/case.py	(original)
+++ python/branches/py3k/Lib/unittest/case.py	Sun Oct  4 16:49:41 2009
@@ -468,7 +468,13 @@
 
            Note that decimal places (from zero) are usually not the same
            as significant digits (measured from the most signficant digit).
+
+           If the two objects compare equal then they will automatically
+           compare almost equal.
         """
+        if first == second:
+            # shortcut for ite
+            return
         if round(abs(second-first), places) != 0:
             standardMsg = '%r != %r within %r places' % (first, second, places)
             msg = self._formatMessage(msg, standardMsg)
@@ -481,8 +487,10 @@
 
            Note that decimal places (from zero) are usually not the same
            as significant digits (measured from the most signficant digit).
+
+           Objects that are equal automatically fail.
         """
-        if round(abs(second-first), places) == 0:
+        if (first == second) or round(abs(second-first), places) == 0:
             standardMsg = '%r == %r within %r places' % (first, second, places)
             msg = self._formatMessage(msg, standardMsg)
             raise self.failureException(msg)

Modified: python/branches/py3k/Lib/unittest/loader.py
==============================================================================
--- python/branches/py3k/Lib/unittest/loader.py	(original)
+++ python/branches/py3k/Lib/unittest/loader.py	Sun Oct  4 16:49:41 2009
@@ -1,7 +1,9 @@
 """Loading unittests."""
 
 import os
+import re
 import sys
+import traceback
 import types
 
 from fnmatch import fnmatch
@@ -9,6 +11,26 @@
 from . import case, suite, util
 
 
+# what about .pyc or .pyo (etc)
+# we would need to avoid loading the same tests multiple times
+# from '.py', '.pyc' *and* '.pyo'
+VALID_MODULE_NAME = re.compile(r'[_a-z]\w*\.py$', re.IGNORECASE)
+
+
+def _make_failed_import_test(name, suiteClass):
+    message = 'Failed to import test module: %s' % name
+    if hasattr(traceback, 'format_exc'):
+        # Python 2.3 compatibility
+        # format_exc returns two frames of discover.py as well
+        message += '\n%s' % traceback.format_exc()
+
+    def testImportFailure(self):
+        raise ImportError(message)
+    attrs = {name: testImportFailure}
+    ModuleImportFailure = type('ModuleImportFailure', (case.TestCase,), attrs)
+    return suiteClass((ModuleImportFailure(name),))
+
+
 class TestLoader(object):
     """
     This class is responsible for loading tests according to various criteria
@@ -79,7 +101,7 @@
             inst = parent(name)
             # static methods follow a different path
             if not isinstance(getattr(inst, name), types.FunctionType):
-                return suite.TestSuite([inst])
+                return self.suiteClass([inst])
         elif isinstance(obj, suite.TestSuite):
             return obj
         if hasattr(obj, '__call__'):
@@ -87,7 +109,7 @@
             if isinstance(test, suite.TestSuite):
                 return test
             elif isinstance(test, case.TestCase):
-                return suite.TestSuite([test])
+                return self.suiteClass([test])
             else:
                 raise TypeError("calling %s returned %s, not a test" %
                                 (obj, test))
@@ -156,17 +178,17 @@
         tests = list(self._find_tests(start_dir, pattern))
         return self.suiteClass(tests)
 
-
-    def _get_module_from_path(self, path):
-        """Load a module from a path relative to the top-level directory
-        of a project. Used by discovery."""
+    def _get_name_from_path(self, path):
         path = os.path.splitext(os.path.normpath(path))[0]
 
-        relpath = os.path.relpath(path, self._top_level_dir)
-        assert not os.path.isabs(relpath), "Path must be within the project"
-        assert not relpath.startswith('..'), "Path must be within the project"
+        _relpath = os.path.relpath(path, self._top_level_dir)
+        assert not os.path.isabs(_relpath), "Path must be within the project"
+        assert not _relpath.startswith('..'), "Path must be within the project"
+
+        name = _relpath.replace(os.path.sep, '.')
+        return name
 
-        name = relpath.replace(os.path.sep, '.')
+    def _get_module_from_name(self, name):
         __import__(name)
         return sys.modules[name]
 
@@ -176,14 +198,20 @@
 
         for path in paths:
             full_path = os.path.join(start_dir, path)
-            # what about __init__.pyc or pyo (etc)
-            # we would need to avoid loading the same tests multiple times
-            # from '.py', '.pyc' *and* '.pyo'
-            if os.path.isfile(full_path) and path.lower().endswith('.py'):
+            if os.path.isfile(full_path):
+                if not VALID_MODULE_NAME.match(path):
+                    # valid Python identifiers only
+                    continue
+
                 if fnmatch(path, pattern):
                     # if the test file matches, load it
-                    module = self._get_module_from_path(full_path)
-                    yield self.loadTestsFromModule(module)
+                    name = self._get_name_from_path(full_path)
+                    try:
+                        module = self._get_module_from_name(name)
+                    except:
+                        yield _make_failed_import_test(name, self.suiteClass)
+                    else:
+                        yield self.loadTestsFromModule(module)
             elif os.path.isdir(full_path):
                 if not os.path.isfile(os.path.join(full_path, '__init__.py')):
                     continue
@@ -192,7 +220,8 @@
                 tests = None
                 if fnmatch(path, pattern):
                     # only check load_tests if the package directory itself matches the filter
-                    package = self._get_module_from_path(full_path)
+                    name = self._get_name_from_path(full_path)
+                    package = self._get_module_from_name(name)
                     load_tests = getattr(package, 'load_tests', None)
                     tests = self.loadTestsFromModule(package, use_load_tests=False)
 

Modified: python/branches/py3k/Lib/unittest/main.py
==============================================================================
--- python/branches/py3k/Lib/unittest/main.py	(original)
+++ python/branches/py3k/Lib/unittest/main.py	Sun Oct  4 16:49:41 2009
@@ -109,9 +109,9 @@
                 if opt in ('-v','--verbose'):
                     self.verbosity = 2
             if len(args) == 0 and self.defaultTest is None:
-                self.test = self.testLoader.loadTestsFromModule(self.module)
-                return
-            if len(args) > 0:
+                # createTests will load tests from self.module
+                self.testNames = None
+            elif len(args) > 0:
                 self.testNames = args
                 if __name__ == '__main__':
                     # to support python -m unittest ...
@@ -123,8 +123,11 @@
             self.usageExit(msg)
 
     def createTests(self):
-        self.test = self.testLoader.loadTestsFromNames(self.testNames,
-                                                       self.module)
+        if self.testNames is None:
+            self.test = self.testLoader.loadTestsFromModule(self.module)
+        else:
+            self.test = self.testLoader.loadTestsFromNames(self.testNames,
+                                                           self.module)
 
     def _do_discovery(self, argv, Loader=loader.TestLoader):
         # handle command line args for test discovery

Modified: python/branches/py3k/Lib/unittest/suite.py
==============================================================================
--- python/branches/py3k/Lib/unittest/suite.py	(original)
+++ python/branches/py3k/Lib/unittest/suite.py	Sun Oct  4 16:49:41 2009
@@ -1,6 +1,7 @@
 """TestSuite"""
 
 from . import case
+from . import util
 
 
 class TestSuite(object):
@@ -17,7 +18,7 @@
         self.addTests(tests)
 
     def __repr__(self):
-        return "<%s tests=%s>" % (_strclass(self.__class__), list(self))
+        return "<%s tests=%s>" % (util.strclass(self.__class__), list(self))
 
     def __eq__(self, other):
         if not isinstance(other, self.__class__):

Modified: python/branches/py3k/Misc/developers.txt
==============================================================================
--- python/branches/py3k/Misc/developers.txt	(original)
+++ python/branches/py3k/Misc/developers.txt	Sun Oct  4 16:49:41 2009
@@ -20,6 +20,9 @@
 Permissions History
 -------------------
 
+- Doug Hellmann was given SVN access on September 19 2009 by GFB, at
+  suggestion of Jesse Noller, for documentation work.
+
 - Ezio Melotti was given SVN access on June 7 2009 by GFB, for work on and
   fixes to the documentation.
 
@@ -109,6 +112,13 @@
 - Jeffrey Yasskin was given SVN access on 9 August 2007 by NCN,
   for his work on PEPs and other general patches. 
 
+- Mark Summerfield was given SVN access on 1 August 2007 by GFB,
+  for work on documentation.
+
+- Armin Ronacher was given SVN access on 23 July 2007 by GFB,
+  for work on the documentation toolset.  He now maintains the
+  ast module.
+
 - Senthil Kumaran was given SVN access on 16 June 2007 by MvL,
   for his Summer-of-Code project, mentored by Skip Montanaro.
 

Modified: python/branches/py3k/Modules/socketmodule.c
==============================================================================
--- python/branches/py3k/Modules/socketmodule.c	(original)
+++ python/branches/py3k/Modules/socketmodule.c	Sun Oct  4 16:49:41 2009
@@ -3909,8 +3909,13 @@
 	flags = flowinfo = scope_id = 0;
 	if (!PyArg_ParseTuple(args, "Oi:getnameinfo", &sa, &flags))
 		return NULL;
-	if  (!PyArg_ParseTuple(sa, "si|ii",
-			       &hostp, &port, &flowinfo, &scope_id))
+	if (!PyTuple_Check(sa)) {
+		PyErr_SetString(PyExc_TypeError,
+				"getnameinfo() argument 1 must be a tuple");
+		return NULL;
+	}
+	if (!PyArg_ParseTuple(sa, "si|ii",
+			      &hostp, &port, &flowinfo, &scope_id))
 		return NULL;
 	PyOS_snprintf(pbuf, sizeof(pbuf), "%d", port);
 	memset(&hints, 0, sizeof(hints));
@@ -3933,9 +3938,7 @@
 	switch (res->ai_family) {
 	case AF_INET:
 	    {
-		char *t1;
-		int t2;
-		if (PyArg_ParseTuple(sa, "si", &t1, &t2) == 0) {
+		if (PyTuple_GET_SIZE(sa) != 2) {
 			PyErr_SetString(socket_error,
 				"IPv4 sockaddr must be 2 tuple");
 			goto fail;


More information about the Python-checkins mailing list