@@ -3620,9 +3620,9 @@ cdef class Resource(Provider):
36203620 self ._provides = None
36213621 self .set_provides(provides)
36223622
3623- self ._initialized = False
3624- self ._resource = None
3625- self ._shutdowner = None
3623+ self .__initialized = False
3624+ self .__resource = None
3625+ self .__shutdowner = None
36263626
36273627 self ._args = tuple ()
36283628 self ._args_len = 0
@@ -3760,6 +3760,36 @@ cdef class Resource(Provider):
37603760 self ._kwargs_len = len (self ._kwargs)
37613761 return self
37623762
3763+ @property
3764+ def _initialized (self ):
3765+ """ Get initialized state."""
3766+ return self .__initialized
3767+
3768+ @_initialized.setter
3769+ def _initialized (self , value ):
3770+ """ Set initialized state."""
3771+ self .__initialized = value
3772+
3773+ @property
3774+ def _resource (self ):
3775+ """ Get resource."""
3776+ return self .__resource
3777+
3778+ @_resource.setter
3779+ def _resource (self , value ):
3780+ """ Set resource."""
3781+ self .__resource = value
3782+
3783+ @property
3784+ def _shutdowner (self ):
3785+ """ Get shutdowner."""
3786+ return self .__shutdowner
3787+
3788+ @_shutdowner.setter
3789+ def _shutdowner (self , value ):
3790+ """ Set shutdowner."""
3791+ self .__shutdowner = value
3792+
37633793 @property
37643794 def initialized (self ):
37653795 """ Check if resource is initialized."""
@@ -3871,85 +3901,89 @@ cdef class ContextLocalResource(Resource):
38713901 _none = object ()
38723902
38733903 def __init__ (self , provides = None , *args , **kwargs ):
3904+ self ._initialized_context_var = ContextVar(" _initialized_context_var" , default = False )
38743905 self ._resource_context_var = ContextVar(" _resource_context_var" , default = self ._none)
38753906 self ._shutdowner_context_var = ContextVar(" _shutdowner_context_var" , default = self ._none)
38763907 super ().__init__(provides, * args, ** kwargs)
38773908
3878- def __deepcopy__ (self , memo ):
3879- """ Create and return full copy of provider."""
3880- copied = memo.get(id (self ))
3881- if copied is not None :
3882- return copied
3909+ @property
3910+ def _initialized (self ):
3911+ """ Get initialized state."""
3912+ return self ._initialized_context_var.get()
38833913
3884- if self ._resource_context_var.get() != self ._none:
3885- raise Error(" Can not copy initialized resource" )
3886- copied = _memorized_duplicate(self , memo)
3887- copied.set_provides(_copy_if_provider(self .provides, memo))
3888- copied.set_args(* deepcopy_args(self , self .args, memo))
3889- copied.set_kwargs(** deepcopy_kwargs(self , self .kwargs, memo))
3914+ @_initialized.setter
3915+ def _initialized (self , value ):
3916+ """ Set initialized state."""
3917+ self ._initialized_context_var.set(value)
38903918
3891- self ._copy_overridings(copied, memo)
3919+ @property
3920+ def _resource (self ):
3921+ """ Get resource."""
3922+ return self ._resource_context_var.get()
38923923
3893- return copied
3924+ @_resource.setter
3925+ def _resource (self , value ):
3926+ """ Set resource."""
3927+ self ._resource_context_var.set(value)
38943928
38953929 @property
3896- def initialized (self ):
3897- """ Check if resource is initialized."""
3898- return self ._resource_context_var.get() != self ._none
3930+ def _shutdowner (self ):
3931+ """ Get shutdowner."""
3932+ return self ._shutdowner_context_var.get()
3933+
3934+ @_shutdowner.setter
3935+ def _shutdowner (self , value ):
3936+ """ Set shutdowner."""
3937+ self ._shutdowner_context_var.set(value)
38993938
39003939
39013940 def shutdown (self ):
39023941 """ Shutdown resource."""
3903- if self ._resource_context_var.get() == self ._none :
3942+ if not self ._initialized :
39043943 self ._reset_all_contex_vars()
39053944 if self ._async_mode == ASYNC_MODE_ENABLED:
39063945 return NULL_AWAITABLE
39073946 return
3908- if self ._shutdowner_context_var.get() != self ._none:
3909- future = self ._shutdowner_context_var.get()(None , None , None )
3947+
3948+ if self ._shutdowner != self ._none:
3949+ future = self ._shutdowner(None , None , None )
39103950 if __is_future_or_coroutine(future):
39113951 self ._reset_all_contex_vars()
3912- return ensure_future(self ._shutdown_async( future) )
3952+ return ensure_future(future)
39133953
39143954
39153955 self ._reset_all_contex_vars()
39163956 if self ._async_mode == ASYNC_MODE_ENABLED:
39173957 return NULL_AWAITABLE
39183958
39193959 def _reset_all_contex_vars (self ):
3920- self ._resource_context_var.set(self ._none)
3921- self ._shutdowner_context_var.set(self ._none)
3922-
3923-
3924- async def _shutdown_async(self , future) - > None :
3925- await future
3926-
3960+ self ._initialized= False
3961+ self ._resource = self ._none
3962+ self ._shutdowner = self ._none
39273963
39283964 async def _handle_async_cm(self , obj) - > None :
39293965 resource = await obj.__aenter__()
39303966 return resource
39313967
39323968 async def _provide_async(self , future):
3933- try :
3934- obj = await future
3969+ obj = await future
39353970
3936- if hasattr (obj, ' __aenter__' ) and hasattr (obj, ' __aexit__' ):
3937- resource = await obj.__aenter__()
3938- shutdowner = obj.__aexit__
3939- elif hasattr (obj, ' __enter__' ) and hasattr (obj, ' __exit__' ):
3940- resource = obj.__enter__ ()
3941- shutdowner = obj.__exit__
3942- else :
3943- resource = obj
3944- shutdowner = None
3971+ if hasattr (obj, ' __aenter__' ) and hasattr (obj, ' __aexit__' ):
3972+ resource = await obj.__aenter__()
3973+ shutdowner = obj.__aexit__
3974+ elif hasattr (obj, ' __enter__' ) and hasattr (obj, ' __exit__' ):
3975+ resource = obj.__enter__ ()
3976+ shutdowner = obj.__exit__
3977+ else :
3978+ resource = obj
3979+ shutdowner = self ._none
39453980
3946- return resource, shutdowner
3947- except :
3948- raise
3981+ return resource, shutdowner
39493982
3983+
39503984 cpdef object _provide(self , tuple args, dict kwargs):
3951- if self ._resource_context_var.get() ! = self ._none :
3952- return self ._resource_context_var.get()
3985+ if self ._initialized :
3986+ return self ._resource
39533987 obj = __call(
39543988 self ._provides,
39553989 args,
@@ -3968,29 +4002,34 @@ cdef class ContextLocalResource(Resource):
39684002 return future_result
39694003 elif hasattr (obj, ' __enter__' ) and hasattr (obj, ' __exit__' ):
39704004 resource = obj.__enter__ ()
3971- self ._resource_context_var.set(resource)
3972- self ._shutdowner_context_var.set(obj.__exit__ )
4005+ self ._resource = resource
4006+ self ._initialized = True
4007+ self ._shutdowner = obj.__exit__
39734008 elif hasattr (obj, ' __aenter__' ) and hasattr (obj, ' __aexit__' ):
39744009 resource = ensure_future(self ._handle_async_cm(obj))
3975- self ._resource_context_var.set(resource)
3976- self ._shutdowner_context_var.set(obj.__aexit__)
4010+ self ._resource = resource
4011+ self ._initialized = True
4012+ self ._shutdowner = obj.__aexit__
39774013 return resource
39784014 else :
3979- self ._resource_context_var.set(obj)
3980- self ._shutdowner_context_var.set(self ._none)
4015+ self ._resource = obj
4016+ self ._initialized = True
4017+ self ._shutdowner = self ._none
39814018
3982- return self ._resource_context_var.get()
4019+ return self ._resource
39834020
39844021 def _async_init_instance (self , future_result , result ):
39854022 try :
39864023 resource, shutdowner = result.result()
39874024 except Exception as exception:
3988- self ._resource_context_var.set(self ._none)
3989- self ._shutdowner_context_var.set(self ._none)
4025+ self ._resource = self ._none
4026+ self ._shutdowner = self ._none
4027+ self ._initialized = False
39904028 future_result.set_exception(exception)
39914029 else :
3992- self ._resource_context_var.set(resource)
3993- self ._shutdowner_context_var.set(shutdowner)
4030+ self ._resource = resource
4031+ self ._initialized = True
4032+ self ._shutdowner = shutdowner
39944033 future_result.set_result(resource)
39954034
39964035
0 commit comments