Index: Doc/library/contextlib.rst =================================================================== --- Doc/library/contextlib.rst (revision 82350) +++ Doc/library/contextlib.rst (working copy) @@ -51,7 +51,11 @@ the exception has been handled, and execution will resume with the statement immediately following the :keyword:`with` statement. + .. versionchanged:: 3.2 + contextmanager uses :class:`ContextDecorator` so the context managers it + creates can be used as decorators as well as in :keyword:`with` statements. + .. function:: closing(thing) Return a context manager that closes *thing* upon completion of the block. This @@ -79,6 +83,49 @@ ``page.close()`` will be called when the :keyword:`with` block is exited. +.. class:: ContextDecorator() + + A base class that enables a context manager to also be used as a decorator. + + Context managers inheriting from ``ContextDecorator`` have to implement + ``__enter__`` and ``__exit__`` as normal. ``__exit__`` retains its optional + exception handling even when used as a decorator. + + Example:: + + from contextlib import ContextDecorator + + class mycontext(ContextDecorator): + def __enter__(self): + print('Starting') + return self + + def __exit__(self, *exc): + print('Finishing') + return False + + @mycontext() + def function(): + print('The bit in the middle') + + with mycontext(): + print('The bit in the middle') + + Existing context managers that already have a base class can be extended by + using ``ContextDecorator`` as a mixin class:: + + from contextlib import ContextDecorator + + class mycontext(ContextBaseClass, ContextDecorator): + def __enter__(self): + return self + + def __exit__(self, *exc): + return False + + .. versionadded:: 3.2 + + .. seealso:: :pep:`0343` - The "with" statement