B \]` @s^dZddlZddlZddlZddlmZddlmZddddd d d d d dddg ZGdd d ej Z Gdd d ej Z Gdd d e Z GdddZGdddee e ZGdddee ZddZddZGddde ZGddde ZGdddeZGd ddeZGd!dde ZGd"d#d#ZGd$d d ee ZGd%d d ee ZGd&dde ZdS)'z4Utilities for with-statement contexts. See PEP 343.N)deque)wrapsasynccontextmanagercontextmanagerclosing nullcontextAbstractContextManagerAbstractAsyncContextManagerAsyncExitStackContextDecorator ExitStackredirect_stdoutredirect_stderrsuppressc@s2eZdZdZddZejddZeddZ dS) rz,An abstract base class for context managers.cCs|S)z0Return `self` upon entering the runtime context.)selfrr&/usr/local/lib/python3.7/contextlib.py __enter__sz AbstractContextManager.__enter__cCsdS)z9Raise any exception triggered within the runtime context.Nr)rexc_type exc_value tracebackrrr__exit__szAbstractContextManager.__exit__cCs|tkrt|ddStS)Nrr)r_collections_abc_check_methodsNotImplemented)clsCrrr__subclasshook__sz'AbstractContextManager.__subclasshook__N) __name__ __module__ __qualname____doc__rabcabstractmethodr classmethodrrrrrrsc@s2eZdZdZddZejddZeddZ dS) r z9An abstract base class for asynchronous context managers.cs|S)z0Return `self` upon entering the runtime context.r)rrrr __aenter__&sz&AbstractAsyncContextManager.__aenter__csdS)z9Raise any exception triggered within the runtime context.Nr)rrrrrrr __aexit__*sz%AbstractAsyncContextManager.__aexit__cCs|tkrt|ddStS)Nr%r&)r rrr)rrrrrr/sz,AbstractAsyncContextManager.__subclasshook__N) rrr r!r%r"r#r&r$rrrrrr "sc@s eZdZdZddZddZdS)r zJA base class or mixin that enables context managers to work as decorators.cCs|S)a6Return a recreated instance of self. Allows an otherwise one-shot context manager like _GeneratorContextManager to support use as a decorator via implicit recreation. This is a private interface just for _GeneratorContextManager. See issue #11647 for details. r)rrrr _recreate_cm:s zContextDecorator._recreate_cmcstfdd}|S)Nc s ||SQRXdS)N)r')argskwds)funcrrrinnerGs z(ContextDecorator.__call__..inner)r)rr*r+r)r*rr__call__FszContextDecorator.__call__N)rrr r!r'r,rrrrr 7s c@seZdZdZddZdS)_GeneratorContextManagerBasezBShared functionality for @contextmanager and @asynccontextmanager.cCsJ||||_||||_|_|_t|dd}|dkr@t|j}||_dS)Nr!)genr*r(r)getattrtyper!)rr*r(r)docrrr__init__Qs    z%_GeneratorContextManagerBase.__init__N)rrr r!r2rrrrr-Nsr-c@s(eZdZdZddZddZddZdS) _GeneratorContextManagerz%Helper for @contextmanager decorator.cCs||j|j|jS)N) __class__r*r(r))rrrrr'esz%_GeneratorContextManager._recreate_cmcCs:|`|`|`y t|jStk r4tddYnXdS)Nzgenerator didn't yield)r(r)r*nextr. StopIteration RuntimeError)rrrrrks   z"_GeneratorContextManager.__enter__c Cs|dkr6yt|jWntk r*dSXtdn|dkrD|}y|j|||Wntk r~}z||k Sd}~XYnftk r}z(||krdS|tkr|j|krdSWdd}~XYn"td|krdSYnXtddS)NFzgenerator didn't stopz#generator didn't stop after throw())r5r.r6r7throw __cause__sysexc_info)rr0valuerexcrrrrts.  z!_GeneratorContextManager.__exit__N)rrr r!r'rrrrrrr3`s r3c@s eZdZdZddZddZdS)_AsyncGeneratorContextManagerz Helper for @asynccontextmanager.cs4y|jIdHStk r.tddYnXdS)Nzgenerator didn't yield)r. __anext__StopAsyncIterationr7)rrrrr%sz(_AsyncGeneratorContextManager.__aenter__c s|dkrrrrr&s.    z'_AsyncGeneratorContextManager.__aexit__N)rrr r!r%r&rrrrr?sr?cstfdd}|S)a@contextmanager decorator. Typical usage: @contextmanager def some_generator(): try: yield finally: This makes this: with some_generator() as : equivalent to this: try: = finally: cs t||S)N)r3)r(r))r*rrhelperszcontextmanager..helper)r)r*rFr)r*rrscstfdd}|S)a@asynccontextmanager decorator. Typical usage: @asynccontextmanager async def some_async_generator(): try: yield finally: This makes this: async with some_async_generator() as : equivalent to this: try: = finally: cs t||S)N)r?)r(r))r*rrrFsz#asynccontextmanager..helper)r)r*rFr)r*rrsc@s(eZdZdZddZddZddZdS) ra2Context to automatically close something at the end of a block. Code like this: with closing(.open()) as f: is equivalent to this: f = .open() try: finally: f.close() cCs ||_dS)N)thing)rrGrrrr2%szclosing.__init__cCs|jS)N)rG)rrrrr'szclosing.__enter__cGs|jdS)N)rGclose)rr<rrrr)szclosing.__exit__N)rrr r!r2rrrrrrrsc@s(eZdZdZddZddZddZdS)_RedirectStreamNcCs||_g|_dS)N) _new_target _old_targets)rZ new_targetrrrr21sz_RedirectStream.__init__cCs*|jtt|jtt|j|j|jS)N)rKappendr/r;_streamsetattrrJ)rrrrr6sz_RedirectStream.__enter__cCstt|j|jdS)N)rNr;rMrKpop)rexctypeexcinstexctbrrrr;sz_RedirectStream.__exit__)rrr rMr2rrrrrrrI-srIc@seZdZdZdZdS)r aAContext manager for temporarily redirecting stdout to another file. # How to send help() to stderr with redirect_stdout(sys.stderr): help(dir) # How to write help() to a file with open('help.txt', 'w') as f: with redirect_stdout(f): help(pow) stdoutN)rrr r!rMrrrrr ?s c@seZdZdZdZdS)rzCContext manager for temporarily redirecting stderr to another file.stderrN)rrr r!rMrrrrrOsc@s(eZdZdZddZddZddZdS) ra?Context manager to suppress specified exceptions After the exception is suppressed, execution proceeds with the next statement following the with statement. with suppress(FileNotFoundError): os.remove(somefile) # Execution still resumes here if the file was already removed cGs ||_dS)N) _exceptions)r exceptionsrrrr2`szsuppress.__init__cCsdS)Nr)rrrrrcszsuppress.__enter__cCs|dk ot||jS)N) issubclassrU)rrPrQrRrrrrfs zsuppress.__exit__N)rrr r!r2rrrrrrrUs c@sbeZdZdZeddZeddZddZdd Zd d Z d d Z ddZ ddZ dddZ dS)_BaseExitStackz.A base class for ExitStack and AsyncExitStack.csfdd}|S)Ncs|||S)Nr)rr>tb)cmcm_exitrr _exit_wrapperxsz:_BaseExitStack._create_exit_wrapper.._exit_wrapperr)rZr[r\r)rZr[r_create_exit_wrappervsz#_BaseExitStack._create_exit_wrappercs^fdd}|S)NcsdS)Nr)rr>rY)r(callbackr)rrr\sz8_BaseExitStack._create_cb_wrapper.._exit_wrapperr)r(r)r\r)r(r^r)r_create_cb_wrapper|sz!_BaseExitStack._create_cb_wrappercCs t|_dS)N)r_exit_callbacks)rrrrr2sz_BaseExitStack.__init__cCst|}|j|_t|_|S)z@Preserve the context stack by transferring it to a new instance.)r0r`r)rZ new_stackrrrpop_alls z_BaseExitStack.pop_allcCsBt|}y |j}Wntk r0||YnX||||S)aRegisters a callback with the standard __exit__ method signature. Can suppress exceptions the same way __exit__ method can. Also accepts any object with an __exit__ method (registering a call to the method instead of the object itself). )r0rAttributeError_push_exit_callback _push_cm_exit)rexit_cb_type exit_methodrrrpushs   z_BaseExitStack.pushcCs(t|}|j}||}||||S)zEnters the supplied context manager. If successful, also pushes its __exit__ method as a callback and returns the result of the __enter__ method. )r0rrrd)rrZ_cm_type_exitresultrrr enter_contexts   z_BaseExitStack.enter_contextcOs|t|dkr|^}}}n>|s&tdn0d|krB|d}|^}}ntdt|d|j|f||}||_|||S)z\Registers an arbitrary callback and arguments. Cannot suppress exceptions. zBdescriptor 'callback' of '_BaseExitStack' object needs an argumentr^z8callback expected at least 1 positional argument, got %dr8)len TypeErrorrOr_ __wrapped__rc)r(r)rr^r\rrrr^s      z_BaseExitStack.callbackcCs"|||}||_||ddS)z;Helper to correctly register callbacks to __exit__ methods.TN)r]__self__rc)rrZr[r\rrrrds z_BaseExitStack._push_cm_exitTcCs|j||fdS)N)r`rL)rr^is_syncrrrrcsz"_BaseExitStack._push_exit_callbackN)T)rrr r! staticmethodr]r_r2rarhrlr^rdrcrrrrrXss  rXc@s(eZdZdZddZddZddZdS) r aContext manager for dynamic management of a stack of exit callbacks. For example: with ExitStack() as stack: files = [stack.enter_context(open(fname)) for fname in filenames] # All opened files will automatically be closed at the end of # the with statement, even if attempts to open files later # in the list raise an exception. cCs|S)Nr)rrrrrszExitStack.__enter__c s|ddk }tdfdd}d}d}xh|jr|j\}}|sJty||r`d}d}d}Wq.t}||d|dd}|}Yq.Xq.W|ry|dj} |dWn tk r| |d_YnX|o|S)Nrr8cs8x,|j}||krdS|dks$|kr&P|}qW||_dS)N) __context__)new_excold_exc exc_context) frame_excrr_fix_exception_contextsz2ExitStack.__exit__.._fix_exception_contextFT)NNN)r;r<r`rOAssertionErrorrtrD) r exc_details received_excrysuppressed_exc pending_raiserrcbnew_exc_details fixed_ctxr)rxrrs4      zExitStack.__exit__cCs|ddddS)z%Immediately unwind the context stack.N)r)rrrrrHszExitStack.closeN)rrr r!rrrHrrrrr s 1c@s`eZdZdZeddZeddZddZdd Zd d Z d d Z ddZ ddZ ddZ dS)r aAsync context manager for dynamic management of a stack of exit callbacks. For example: async with AsyncExitStack() as stack: connections = [await stack.enter_async_context(get_connection()) for i in range(5)] # All opened connections will automatically be released at the # end of the async with statement, even if attempts to open a # connection later in the list raise an exception. csfdd}|S)Ncs|||IdHS)Nr)rr>rY)rZr[rrr\'sz@AsyncExitStack._create_async_exit_wrapper.._exit_wrapperr)rZr[r\r)rZr[r_create_async_exit_wrapper%sz)AsyncExitStack._create_async_exit_wrappercs^fdd}|S)NcsIdHdS)Nr)rr>rY)r(r^r)rrr\.sz>AsyncExitStack._create_async_cb_wrapper.._exit_wrapperr)r(r)r\r)r(r^r)r_create_async_cb_wrapper+sz'AsyncExitStack._create_async_cb_wrappercs.t|}|j}||IdH}||||S)zEnters the supplied async context manager. If successful, also pushes its __aexit__ method as a callback and returns the result of the __aenter__ method. N)r0r&r%_push_async_cm_exit)rrZrirjrkrrrenter_async_context2s  z"AsyncExitStack.enter_async_contextcCsDt|}y |j}Wn tk r2||dYnX||||S)a#Registers a coroutine function with the standard __aexit__ method signature. Can suppress exceptions the same way __aexit__ method can. Also accepts any object with an __aexit__ method (registering a call to the method instead of the object itself). F)r0r&rbrcr)rrerfrgrrrpush_async_exit>s  zAsyncExitStack.push_async_exitcOs~t|dkr|^}}}n>|s&tdn0d|krB|d}|^}}ntdt|d|j|f||}||_||d|S)zfRegisters an arbitrary coroutine function and arguments. Cannot suppress exceptions. rmzMdescriptor 'push_async_callback' of 'AsyncExitStack' object needs an argumentr^zCpush_async_callback expected at least 1 positional argument, got %dr8F)rnrorOrrprc)r(r)rr^r\rrrpush_async_callbackPs      z"AsyncExitStack.push_async_callbackcs|dddIdHdS)z%Immediately unwind the context stack.N)r&)rrrracloseiszAsyncExitStack.aclosecCs"|||}||_||ddS)zLHelper to correctly register coroutine function to __aexit__ method.FN)rrqrc)rrZr[r\rrrrms z"AsyncExitStack._push_async_cm_exitcs|S)Nr)rrrrr%tszAsyncExitStack.__aenter__c s|ddk }tdfdd}d}d}xx|jr|j\}}y0|rR||}n||IdH}|rpd}d}d}Wq.t} || d|dd}| }Yq.Xq.W|ry|dj} |dWn tk r| |d_YnX|o|S)Nrr8cs8x,|j}||krdS|dks$|kr&P|}qW||_dS)N)rt)rurvrw)rxrrry}sz8AsyncExitStack.__aexit__.._fix_exception_contextFT)NNN)r;r<r`rOrtrD) rr{r|ryr}r~rrrZ cb_suppressrrr)rxrr&ws8       zAsyncExitStack.__aexit__N)rrr r!rsrrrrrrrr%r&rrrrr s    c@s*eZdZdZd ddZddZddZdS) raOContext manager that does no additional processing. Used as a stand-in for a normal context manager, when a particular block of code is only sometimes used with a normal context manager: cm = optional_cm if condition else nullcontext() with cm: # Perform operation, using optional_cm if condition is True NcCs ||_dS)N) enter_result)rrrrrr2sznullcontext.__init__cCs|jS)N)r)rrrrrsznullcontext.__enter__cGsdS)Nr)rZexcinforrrrsznullcontext.__exit__)N)rrr r!r2rrrrrrrs  )r!r"r;r collectionsr functoolsr__all__ABCrr objectr r-r3r?rrrrIr rrrXr r rrrrrs<    B -!!`E