mirror of
https://github.com/ets-labs/python-dependency-injector.git
synced 2025-02-15 11:00:50 +03:00
Add implementation
This commit is contained in:
parent
ce6d3df72c
commit
41f8009811
File diff suppressed because it is too large
Load Diff
|
@ -35,6 +35,7 @@ class Container:
|
||||||
def __setattr__(self, name: str, value: Union[Provider, Any]) -> None: ...
|
def __setattr__(self, name: str, value: Union[Provider, Any]) -> None: ...
|
||||||
def __delattr__(self, name: str) -> None: ...
|
def __delattr__(self, name: str) -> None: ...
|
||||||
def set_providers(self, **providers: Provider): ...
|
def set_providers(self, **providers: Provider): ...
|
||||||
|
def set_provider(self, name: str, provider: Provider) -> None: ...
|
||||||
def override(self, overriding: C_Base) -> None: ...
|
def override(self, overriding: C_Base) -> None: ...
|
||||||
def override_providers(self, **overriding_providers: Provider) -> None: ...
|
def override_providers(self, **overriding_providers: Provider) -> None: ...
|
||||||
def reset_last_overriding(self) -> None: ...
|
def reset_last_overriding(self) -> None: ...
|
||||||
|
|
|
@ -69,7 +69,7 @@ class DynamicContainer(Container):
|
||||||
self.declarative_parent = None
|
self.declarative_parent = None
|
||||||
self.wired_to_modules = []
|
self.wired_to_modules = []
|
||||||
self.wired_to_packages = []
|
self.wired_to_packages = []
|
||||||
self.__self__ = providers.Object(self)
|
self.__self__ = providers.Self(self)
|
||||||
super(DynamicContainer, self).__init__()
|
super(DynamicContainer, self).__init__()
|
||||||
|
|
||||||
def __deepcopy__(self, memo):
|
def __deepcopy__(self, memo):
|
||||||
|
@ -102,7 +102,7 @@ class DynamicContainer(Container):
|
||||||
|
|
||||||
:rtype: None
|
:rtype: None
|
||||||
"""
|
"""
|
||||||
if isinstance(value, providers.Provider) and name != '__self__':
|
if isinstance(value, providers.Provider) and not isinstance(value, providers.Self):
|
||||||
_check_provider_type(self, value)
|
_check_provider_type(self, value)
|
||||||
self.providers[name] = value
|
self.providers[name] = value
|
||||||
super(DynamicContainer, self).__setattr__(name, value)
|
super(DynamicContainer, self).__setattr__(name, value)
|
||||||
|
@ -154,6 +154,19 @@ class DynamicContainer(Container):
|
||||||
for name, provider in six.iteritems(providers):
|
for name, provider in six.iteritems(providers):
|
||||||
setattr(self, name, provider)
|
setattr(self, name, provider)
|
||||||
|
|
||||||
|
def set_provider(self, name, provider):
|
||||||
|
"""Set container provider.
|
||||||
|
|
||||||
|
:param name: Provider name
|
||||||
|
:type name: str
|
||||||
|
|
||||||
|
:param provider: Provider
|
||||||
|
:type provider: :py:class:`dependency_injector.providers.Provider`
|
||||||
|
|
||||||
|
:rtype: None
|
||||||
|
"""
|
||||||
|
setattr(self, name, provider)
|
||||||
|
|
||||||
def override(self, object overriding):
|
def override(self, object overriding):
|
||||||
"""Override current container by overriding container.
|
"""Override current container by overriding container.
|
||||||
|
|
||||||
|
@ -282,6 +295,10 @@ class DeclarativeContainerMetaClass(type):
|
||||||
|
|
||||||
def __new__(type mcs, str class_name, tuple bases, dict attributes):
|
def __new__(type mcs, str class_name, tuple bases, dict attributes):
|
||||||
"""Declarative container class factory."""
|
"""Declarative container class factory."""
|
||||||
|
self = mcs.__fetch_self(attributes)
|
||||||
|
if self is None:
|
||||||
|
self = providers.Self()
|
||||||
|
|
||||||
containers = {
|
containers = {
|
||||||
name: container
|
name: container
|
||||||
for name, container in six.iteritems(attributes)
|
for name, container in six.iteritems(attributes)
|
||||||
|
@ -291,7 +308,7 @@ class DeclarativeContainerMetaClass(type):
|
||||||
cls_providers = {
|
cls_providers = {
|
||||||
name: provider
|
name: provider
|
||||||
for name, provider in six.iteritems(attributes)
|
for name, provider in six.iteritems(attributes)
|
||||||
if isinstance(provider, providers.Provider)
|
if isinstance(provider, providers.Provider) and not isinstance(provider, providers.Self)
|
||||||
}
|
}
|
||||||
|
|
||||||
inherited_providers = {
|
inherited_providers = {
|
||||||
|
@ -312,7 +329,8 @@ class DeclarativeContainerMetaClass(type):
|
||||||
|
|
||||||
cls = <type>type.__new__(mcs, class_name, bases, attributes)
|
cls = <type>type.__new__(mcs, class_name, bases, attributes)
|
||||||
|
|
||||||
cls.__self__ = providers.Object(cls)
|
self.set_container(cls)
|
||||||
|
cls.__self__ = self
|
||||||
|
|
||||||
for provider in six.itervalues(cls.providers):
|
for provider in six.itervalues(cls.providers):
|
||||||
_check_provider_type(cls, provider)
|
_check_provider_type(cls, provider)
|
||||||
|
@ -375,6 +393,28 @@ class DeclarativeContainerMetaClass(type):
|
||||||
"""Return providers traversal generator."""
|
"""Return providers traversal generator."""
|
||||||
yield from providers.traverse(*cls.providers.values(), types=types)
|
yield from providers.traverse(*cls.providers.values(), types=types)
|
||||||
|
|
||||||
|
@staticmethod
|
||||||
|
def __fetch_self(attributes):
|
||||||
|
self = None
|
||||||
|
alt_names = []
|
||||||
|
|
||||||
|
for name, value in attributes.items():
|
||||||
|
if not isinstance(value, providers.Self):
|
||||||
|
continue
|
||||||
|
|
||||||
|
if self is not None and value is not self:
|
||||||
|
raise errors.Error('Container can have only one "Self" provider')
|
||||||
|
|
||||||
|
if name != '__self__':
|
||||||
|
alt_names.append(name)
|
||||||
|
|
||||||
|
self = value
|
||||||
|
|
||||||
|
if self:
|
||||||
|
self.set_alt_names(alt_names)
|
||||||
|
|
||||||
|
return self
|
||||||
|
|
||||||
|
|
||||||
@six.add_metaclass(DeclarativeContainerMetaClass)
|
@six.add_metaclass(DeclarativeContainerMetaClass)
|
||||||
class DeclarativeContainer(Container):
|
class DeclarativeContainer(Container):
|
||||||
|
@ -448,9 +488,21 @@ class DeclarativeContainer(Container):
|
||||||
container = cls.instance_type()
|
container = cls.instance_type()
|
||||||
container.provider_type = cls.provider_type
|
container.provider_type = cls.provider_type
|
||||||
container.declarative_parent = cls
|
container.declarative_parent = cls
|
||||||
container.set_providers(**providers.deepcopy(cls.providers))
|
|
||||||
|
copied_providers = providers.deepcopy({ **cls.providers, **{'@@self@@': cls.__self__}})
|
||||||
|
copied_self = copied_providers.pop('@@self@@')
|
||||||
|
copied_self.set_container(container)
|
||||||
|
|
||||||
|
container.__self__ = copied_self
|
||||||
|
for name in copied_self.alt_names:
|
||||||
|
container.set_provider(name, copied_self)
|
||||||
|
|
||||||
|
for name, provider in copied_providers.items():
|
||||||
|
container.set_provider(name, provider)
|
||||||
|
|
||||||
container.override_providers(**overriding_providers)
|
container.override_providers(**overriding_providers)
|
||||||
container.apply_container_providers_overridings()
|
container.apply_container_providers_overridings()
|
||||||
|
|
||||||
return container
|
return container
|
||||||
|
|
||||||
@classmethod
|
@classmethod
|
||||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -27,6 +27,11 @@ cdef class Object(Provider):
|
||||||
cpdef object _provide(self, tuple args, dict kwargs)
|
cpdef object _provide(self, tuple args, dict kwargs)
|
||||||
|
|
||||||
|
|
||||||
|
cdef class Self(Provider):
|
||||||
|
cdef object __container
|
||||||
|
cdef tuple __alt_names
|
||||||
|
|
||||||
|
|
||||||
cdef class Delegate(Provider):
|
cdef class Delegate(Provider):
|
||||||
cdef object __provides
|
cdef object __provides
|
||||||
|
|
||||||
|
|
|
@ -85,6 +85,14 @@ class Object(Provider[T]):
|
||||||
def __init__(self, provides: T) -> None: ...
|
def __init__(self, provides: T) -> None: ...
|
||||||
|
|
||||||
|
|
||||||
|
class Self(Provider[T]):
|
||||||
|
def __init__(self, container: Optional[T] = None) -> None: ...
|
||||||
|
def set_container(self, container: T) -> None: ...
|
||||||
|
def set_alt_names(self, alt_names: _Iterable[Any]) -> None: ...
|
||||||
|
@property
|
||||||
|
def alt_names(self) -> Tuple[Any]: ...
|
||||||
|
|
||||||
|
|
||||||
class Delegate(Provider[Provider]):
|
class Delegate(Provider[Provider]):
|
||||||
def __init__(self, provides: Provider) -> None: ...
|
def __init__(self, provides: Provider) -> None: ...
|
||||||
@property
|
@property
|
||||||
|
|
|
@ -458,6 +458,62 @@ cdef class Object(Provider):
|
||||||
return self.__provides
|
return self.__provides
|
||||||
|
|
||||||
|
|
||||||
|
cdef class Self(Provider):
|
||||||
|
"""Self provider returns own container."""
|
||||||
|
|
||||||
|
def __init__(self, container=None):
|
||||||
|
"""Initialize provider."""
|
||||||
|
self.__container = container
|
||||||
|
self.__alt_names = tuple()
|
||||||
|
super().__init__()
|
||||||
|
|
||||||
|
def __deepcopy__(self, memo):
|
||||||
|
"""Create and return full copy of provider."""
|
||||||
|
copied = memo.get(id(self))
|
||||||
|
if copied is not None:
|
||||||
|
return copied
|
||||||
|
|
||||||
|
copied = self.__class__()
|
||||||
|
copied.set_container(deepcopy(self.__container, memo))
|
||||||
|
copied.set_alt_names(self.__alt_names)
|
||||||
|
|
||||||
|
self._copy_overridings(copied, memo)
|
||||||
|
|
||||||
|
return copied
|
||||||
|
|
||||||
|
def __str__(self):
|
||||||
|
"""Return string representation of provider.
|
||||||
|
|
||||||
|
:rtype: str
|
||||||
|
"""
|
||||||
|
return represent_provider(provider=self, provides=self.__container)
|
||||||
|
|
||||||
|
def __repr__(self):
|
||||||
|
"""Return string representation of provider.
|
||||||
|
|
||||||
|
:rtype: str
|
||||||
|
"""
|
||||||
|
return self.__str__()
|
||||||
|
|
||||||
|
def set_container(self, container):
|
||||||
|
self.__container = container
|
||||||
|
|
||||||
|
def set_alt_names(self, alt_names):
|
||||||
|
self.__alt_names = tuple(set(alt_names))
|
||||||
|
|
||||||
|
@property
|
||||||
|
def alt_names(self):
|
||||||
|
return self.__alt_names
|
||||||
|
|
||||||
|
@property
|
||||||
|
def related(self):
|
||||||
|
"""Return related providers generator."""
|
||||||
|
yield from super().related
|
||||||
|
|
||||||
|
cpdef object _provide(self, tuple args, dict kwargs):
|
||||||
|
return self.__container
|
||||||
|
|
||||||
|
|
||||||
cdef class Delegate(Provider):
|
cdef class Delegate(Provider):
|
||||||
"""Delegate provider returns provider "as is".
|
"""Delegate provider returns provider "as is".
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user