Handling instances of a context manager inside another context manager
contextmanager, python
Solution
If you can use the `@contextlib.contextmanager` decorator your life gets a lot easier:
import contextlib
@contextlib.contextmanager
def internal_cm():
try:
print "Entering internal_cm"
yield None
print "Exiting cleanly from internal_cm"
finally:
print "Finally internal_cm"
@contextlib.contextmanager
def external_cm():
with internal_cm() as c:
try:
print "In external_cm_f", c
yield [c]
print "Exiting cleanly from external_cm_f", c
finally:
print "Finally external_cm_f", c
if "__main__" == __name__:
with external_cm():
print "Location A"
print
with external_cm():
print "Location B"
raise Exception("Some exception occurs!!")
Problem
How should a context manager created inside another context manager be handled in Python? Example: suppose you have class `A` that acts as a context manager, and class `B` that also acts as a context manager. But class `B` instances will have to instantiate and use an instance of class `A`. I've gone through PEP 343 and this is the solution I thought of: ``` class A(object): def __enter__(self): # Acquire some resources here return self def __exit__(seplf, exception_type, exception, traceback): # Release the resources and clean up pass class B(object): def __init__(self): self.a = A() def __enter__(self): # Acquire some resources, but also need to "start" our instance of A self.a.__enter__() return self def __exit__(self, exception_type, exception, traceback): # Release the resources, and make our instance of A clean up as well self.a.__exit__(exception_type, exception, traceback) ``` Is this the correct approach? Or am I missing some gotchas?