[New-bugs-announce] [issue18677] Enhanced context managers with ContextManagerExit and None

Kristján Valur Jónsson report at bugs.python.org
Wed Aug 7 16:22:07 CEST 2013


New submission from Kristján Valur Jónsson:

A proposed patch adds two features to context managers:

1)It has always irked me that it was impossible to assemble nested context managers in the python language. See issue #5251.
The main problem, that exceptions in __enter__ cannot be properly handled, is fixed by introducing a new core exception, ContextManagerExit.  When raised by __enter__(), the body that the context manager protects is skipped.  This exception is in the spirit of other semi-internal exceptions such as GeneratorExit and StopIteration.  Using this exception, contextlib.nested can properly handle the case where the body isn't run because of an internal __enter__ exception which is handled by an outer __exit__.

2) The mechanism used in implementing ContextManagerExit above is easily extended to allowing a special context manager: None.  This is useful for having _optional_ context managers.  E.g. code like this:
    with performance_timer():
        do_work()

    def performance_timer():
        if profiling:
            return accumulator
        return None

None becomes the trivial context manager and its __enter__ and __exit__ calls are skipped, along with their overhead.

This patch implements both features.
In addition, it:
1) reintroduces contextlib.nested, which is based on nested_delayed
2) introduces contextlib.nested_delayed, which solves the other problem with previous versions of nested, that an inner context manager expression shouldn't be evaluated early.  contextlib.nested evaluates callables returning context managers, rather than managers directly.
3) Allows contextlib.contextmanager decorated functions to not yield, which amounts to skipping the protected body (implicitly raising ContextManagerExit)
4) unittests for the whole thing.

I'll introduce this stuff on python-ideas as well.

----------
components: Interpreter Core
files: contextmanagerexit.patch
keywords: patch
messages: 194615
nosy: kristjan.jonsson
priority: normal
severity: normal
status: open
title: Enhanced context managers with ContextManagerExit and None
type: enhancement
versions: Python 3.4
Added file: http://bugs.python.org/file31182/contextmanagerexit.patch

_______________________________________
Python tracker <report at bugs.python.org>
<http://bugs.python.org/issue18677>
_______________________________________


More information about the New-bugs-announce mailing list