mirror of
https://github.com/ets-labs/python-dependency-injector.git
synced 2024-11-29 21:14:00 +03:00
Implement lazy initialization and improve copying for ItemGetter provider
This commit is contained in:
parent
b8078f904e
commit
773a7d86f7
|
@ -1416,13 +1416,13 @@ struct __pyx_obj_19dependency_injector_9providers_AttributeGetter {
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* cdef class ItemGetter(Provider): # <<<<<<<<<<<<<<
|
* cdef class ItemGetter(Provider): # <<<<<<<<<<<<<<
|
||||||
* cdef Provider __provider
|
* cdef object __provides
|
||||||
* cdef object __item
|
* cdef object __name
|
||||||
*/
|
*/
|
||||||
struct __pyx_obj_19dependency_injector_9providers_ItemGetter {
|
struct __pyx_obj_19dependency_injector_9providers_ItemGetter {
|
||||||
struct __pyx_obj_19dependency_injector_9providers_Provider __pyx_base;
|
struct __pyx_obj_19dependency_injector_9providers_Provider __pyx_base;
|
||||||
struct __pyx_obj_19dependency_injector_9providers_Provider *__pyx___provider;
|
PyObject *__pyx___provides;
|
||||||
PyObject *__pyx___item;
|
PyObject *__pyx___name;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
@ -2172,8 +2172,8 @@ static struct __pyx_vtabstruct_19dependency_injector_9providers_AttributeGetter
|
||||||
*
|
*
|
||||||
*
|
*
|
||||||
* cdef class ItemGetter(Provider): # <<<<<<<<<<<<<<
|
* cdef class ItemGetter(Provider): # <<<<<<<<<<<<<<
|
||||||
* cdef Provider __provider
|
* cdef object __provides
|
||||||
* cdef object __item
|
* cdef object __name
|
||||||
*/
|
*/
|
||||||
|
|
||||||
struct __pyx_vtabstruct_19dependency_injector_9providers_ItemGetter {
|
struct __pyx_vtabstruct_19dependency_injector_9providers_ItemGetter {
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -248,8 +248,8 @@ cdef class AttributeGetter(Provider):
|
||||||
|
|
||||||
|
|
||||||
cdef class ItemGetter(Provider):
|
cdef class ItemGetter(Provider):
|
||||||
cdef Provider __provider
|
cdef object __provides
|
||||||
cdef object __item
|
cdef object __name
|
||||||
|
|
||||||
cpdef object _provide(self, tuple args, dict kwargs)
|
cpdef object _provide(self, tuple args, dict kwargs)
|
||||||
|
|
||||||
|
|
|
@ -433,14 +433,17 @@ class ProvidedInstance(Provider, ProvidedInstanceFluentInterface):
|
||||||
|
|
||||||
|
|
||||||
class AttributeGetter(Provider, ProvidedInstanceFluentInterface):
|
class AttributeGetter(Provider, ProvidedInstanceFluentInterface):
|
||||||
def __init__(self, provides: Optional[Provider] = None, attribute: Optional[str] = None) -> None: ...
|
def __init__(self, provides: Optional[Provider] = None, name: Optional[str] = None) -> None: ...
|
||||||
@property
|
@property
|
||||||
def name(self) -> Optional[str]: ...
|
def name(self) -> Optional[str]: ...
|
||||||
def set_name(self, name: Optional[str]) -> ProvidedInstanceFluentInterface: ...
|
def set_name(self, name: Optional[str]) -> ProvidedInstanceFluentInterface: ...
|
||||||
|
|
||||||
|
|
||||||
class ItemGetter(Provider, ProvidedInstanceFluentInterface):
|
class ItemGetter(Provider, ProvidedInstanceFluentInterface):
|
||||||
def __init__(self, provider: Provider, item: str) -> None: ...
|
def __init__(self, provides: Optional[Provider] = None, name: Optional[str] = None) -> None: ...
|
||||||
|
@property
|
||||||
|
def name(self) -> Optional[str]: ...
|
||||||
|
def set_name(self, name: Optional[str]) -> ProvidedInstanceFluentInterface: ...
|
||||||
|
|
||||||
|
|
||||||
class MethodCaller(Provider, ProvidedInstanceFluentInterface):
|
class MethodCaller(Provider, ProvidedInstanceFluentInterface):
|
||||||
|
|
|
@ -4021,25 +4021,26 @@ cdef class ItemGetter(Provider):
|
||||||
You should not create this provider directly. See :py:class:`ProvidedInstance` instead.
|
You should not create this provider directly. See :py:class:`ProvidedInstance` instead.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
def __init__(self, Provider provider, object item):
|
def __init__(self, provides=None, name=None):
|
||||||
self.__provider = provider
|
self.__provides = None
|
||||||
self.__item = item
|
self.set_provides(provides)
|
||||||
|
|
||||||
|
self.__name = None
|
||||||
|
self.set_name(name)
|
||||||
super().__init__()
|
super().__init__()
|
||||||
|
|
||||||
def __repr__(self):
|
def __repr__(self):
|
||||||
return f'{self.__class__.__name__}(\'{self.__item}\')'
|
return f'{self.__class__.__name__}(\'{self.name}\')'
|
||||||
|
|
||||||
def __deepcopy__(self, memo=None):
|
|
||||||
cdef ItemGetter copied
|
|
||||||
|
|
||||||
|
def __deepcopy__(self, memo):
|
||||||
copied = memo.get(id(self))
|
copied = memo.get(id(self))
|
||||||
if copied is not None:
|
if copied is not None:
|
||||||
return copied
|
return copied
|
||||||
|
|
||||||
return self.__class__(
|
copied = _memorized_duplicate(self, memo)
|
||||||
deepcopy(self.__provider, memo),
|
copied.set_provides(_copy_if_provider(self.provides, memo))
|
||||||
self.__item,
|
copied.set_name(self.name)
|
||||||
)
|
return copied
|
||||||
|
|
||||||
def __getattr__(self, item):
|
def __getattr__(self, item):
|
||||||
return AttributeGetter(self, item)
|
return AttributeGetter(self, item)
|
||||||
|
@ -4049,13 +4050,23 @@ cdef class ItemGetter(Provider):
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def provides(self):
|
def provides(self):
|
||||||
"""Return provider."""
|
"""Return provider's provides."""
|
||||||
return self.__provider
|
return self.__provides
|
||||||
|
|
||||||
|
def set_provides(self, provides):
|
||||||
|
"""Set provider's provides."""
|
||||||
|
self.__provides = provides
|
||||||
|
return self
|
||||||
|
|
||||||
@property
|
@property
|
||||||
def name(self):
|
def name(self):
|
||||||
"""Return name of the item."""
|
"""Return name of the item."""
|
||||||
return self.__item
|
return self.__name
|
||||||
|
|
||||||
|
def set_name(self, name):
|
||||||
|
"""Set name of the item."""
|
||||||
|
self.__name = name
|
||||||
|
return self
|
||||||
|
|
||||||
def call(self, *args, **kwargs):
|
def call(self, *args, **kwargs):
|
||||||
return MethodCaller(self, *args, **kwargs)
|
return MethodCaller(self, *args, **kwargs)
|
||||||
|
@ -4063,21 +4074,22 @@ cdef class ItemGetter(Provider):
|
||||||
@property
|
@property
|
||||||
def related(self):
|
def related(self):
|
||||||
"""Return related providers generator."""
|
"""Return related providers generator."""
|
||||||
yield self.__provider
|
if is_provider(self.provides):
|
||||||
|
yield self.provides
|
||||||
yield from super().related
|
yield from super().related
|
||||||
|
|
||||||
cpdef object _provide(self, tuple args, dict kwargs):
|
cpdef object _provide(self, tuple args, dict kwargs):
|
||||||
provided = self.__provider(*args, **kwargs)
|
provided = self.provides(*args, **kwargs)
|
||||||
if __is_future_or_coroutine(provided):
|
if __is_future_or_coroutine(provided):
|
||||||
future_result = asyncio.Future()
|
future_result = asyncio.Future()
|
||||||
provided = asyncio.ensure_future(provided)
|
provided = asyncio.ensure_future(provided)
|
||||||
provided.add_done_callback(functools.partial(self._async_provide, future_result))
|
provided.add_done_callback(functools.partial(self._async_provide, future_result))
|
||||||
return future_result
|
return future_result
|
||||||
return provided[self.__item]
|
return provided[self.name]
|
||||||
|
|
||||||
def _async_provide(self, future_result, future):
|
def _async_provide(self, future_result, future):
|
||||||
provided = future.result()
|
provided = future.result()
|
||||||
result = provided[self.__item]
|
result = provided[self.name]
|
||||||
future_result.set_result(result)
|
future_result.set_result(result)
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -145,6 +145,16 @@ class LazyInitTests(unittest.TestCase):
|
||||||
self.assertIs(provider.set_provides(providers.Provider()), provider)
|
self.assertIs(provider.set_provides(providers.Provider()), provider)
|
||||||
self.assertIs(provider.set_name('__dict__'), provider)
|
self.assertIs(provider.set_name('__dict__'), provider)
|
||||||
|
|
||||||
|
def test_item_getter(self):
|
||||||
|
provides = providers.Object({'foo': 'bar'})
|
||||||
|
provider = providers.ItemGetter()
|
||||||
|
provider.set_provides(provides)
|
||||||
|
provider.set_name('foo')
|
||||||
|
self.assertIs(provider.provides, provides)
|
||||||
|
self.assertEqual(provider.name, 'foo')
|
||||||
|
self.assertIs(provider.set_provides(providers.Provider()), provider)
|
||||||
|
self.assertIs(provider.set_name('foo'), provider)
|
||||||
|
|
||||||
|
|
||||||
class ProvidedInstancePuzzleTests(unittest.TestCase):
|
class ProvidedInstancePuzzleTests(unittest.TestCase):
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user