At 03:05 PM 3/24/2006 -0800, Guido van Rossum wrote:
Oops, that's definitely a bug. Please go ahead and fix in both places.
(I'm still trying to fathom the other PEP 343 issue you brought up.)
Here's the paragraph I'm proposing to add to the PEP to explain that issue:
NOTE: to facilitate chaining of contexts, __exit__() methods should *not* reraise the error that is passed in, because it is always the responsibility of the *caller* to reraise. If an __exit__() method exits with *any* exception, the caller of __exit__() should interpret this as meaning that the __exit__() method itself failed to perform the desired cleanup or other operations.
Currently, the PEP is ambiguous on this point. When "with" calls __exit__() this point is irrelevant because either way, the same exception will be raised/propagated.
But if you are writing Python code that explicitly uses the context protocol (e.g. the 'nested' context manager), it should be clear as to whether a given __exit__() invocation failed or succeeded. Thus, __exit__() should only raise an exception if it *failed*.
(This then implies that the @contextmanager decorator must catch any re-raising done by the wrapped generator.)