mirror of
https://github.com/ets-labs/python-dependency-injector.git
synced 2025-02-07 07:00:49 +03:00
Update singleton provider docs, including API, and examples
This commit is contained in:
parent
fb6deaec96
commit
61e6f2db60
|
@ -268,9 +268,15 @@ class Factory(Provider):
|
||||||
|
|
||||||
|
|
||||||
class Singleton(Provider):
|
class Singleton(Provider):
|
||||||
"""Singleton provider.
|
""":py:class:`Singleton` provider returns same instance on every call.
|
||||||
|
|
||||||
Singleton provider will create instance once and return it on every call.
|
:py:class:`Singleton` provider creates instance once and return it on every
|
||||||
|
call. :py:class:`Singleton` uses :py:class:`Factory` for creation of
|
||||||
|
instance, so, please follow :py:class:`Factory` documentation to go inside
|
||||||
|
with injections syntax.
|
||||||
|
|
||||||
|
:py:class:`Singleton` is thread-safe and could be used in multithreading
|
||||||
|
environment without any negative impact.
|
||||||
"""
|
"""
|
||||||
|
|
||||||
__slots__ = ('instance', 'factory')
|
__slots__ = ('instance', 'factory')
|
||||||
|
@ -278,25 +284,90 @@ class Singleton(Provider):
|
||||||
def __init__(self, provides, *args, **kwargs):
|
def __init__(self, provides, *args, **kwargs):
|
||||||
"""Initializer."""
|
"""Initializer."""
|
||||||
self.instance = None
|
self.instance = None
|
||||||
|
"""Read-only reference to singleton's instance.
|
||||||
|
|
||||||
|
:type: object
|
||||||
|
"""
|
||||||
|
|
||||||
self.factory = Factory(provides, *args, **kwargs)
|
self.factory = Factory(provides, *args, **kwargs)
|
||||||
|
"""Singleton's factory object.
|
||||||
|
|
||||||
|
:type: :py:class:`Factory`
|
||||||
|
"""
|
||||||
|
|
||||||
super(Singleton, self).__init__()
|
super(Singleton, self).__init__()
|
||||||
|
|
||||||
|
@property
|
||||||
|
def provides(self):
|
||||||
|
"""Class or other callable that provides object for creation.
|
||||||
|
|
||||||
|
:type: type | callable
|
||||||
|
"""
|
||||||
|
return self.factory.provides
|
||||||
|
|
||||||
|
@property
|
||||||
|
def args(self):
|
||||||
|
"""Tuple of positional argument injections.
|
||||||
|
|
||||||
|
:type: tuple[:py:class:`dependency_injector.injections.Arg`]
|
||||||
|
"""
|
||||||
|
return self.factory.args
|
||||||
|
|
||||||
|
@property
|
||||||
|
def kwargs(self):
|
||||||
|
"""Tuple of keyword argument injections.
|
||||||
|
|
||||||
|
:type: tuple[:py:class:`dependency_injector.injections.KwArg`]
|
||||||
|
"""
|
||||||
|
return self.factory.kwargs
|
||||||
|
|
||||||
|
@property
|
||||||
|
def attributes(self):
|
||||||
|
"""Tuple of attribute injections.
|
||||||
|
|
||||||
|
:type: tuple[:py:class:`dependency_injector.injections.Attribute`]
|
||||||
|
"""
|
||||||
|
return self.factory.attributes
|
||||||
|
|
||||||
|
@property
|
||||||
|
def methods(self):
|
||||||
|
"""Tuple of method injections.
|
||||||
|
|
||||||
|
:type: tuple[:py:class:`dependency_injector.injections.Method`]
|
||||||
|
"""
|
||||||
|
return self.factory.methods
|
||||||
|
|
||||||
|
@property
|
||||||
|
def injections(self):
|
||||||
|
"""Read-only tuple of all injections.
|
||||||
|
|
||||||
|
:rtype: tuple[:py:class:`dependency_injector.injections.Injection`]
|
||||||
|
"""
|
||||||
|
return self.factory.injections
|
||||||
|
|
||||||
|
def reset(self):
|
||||||
|
"""Reset cached instance, if any.
|
||||||
|
|
||||||
|
:rtype: None
|
||||||
|
"""
|
||||||
|
self.instance = None
|
||||||
|
|
||||||
def _provide(self, *args, **kwargs):
|
def _provide(self, *args, **kwargs):
|
||||||
"""Return provided instance."""
|
"""Return provided instance.
|
||||||
|
|
||||||
|
:param args: tuple of context positional arguments
|
||||||
|
:type args: tuple[object]
|
||||||
|
|
||||||
|
:param kwargs: dictionary of context keyword arguments
|
||||||
|
:type kwargs: dict[str, object]
|
||||||
|
|
||||||
|
:rtype: object
|
||||||
|
"""
|
||||||
with GLOBAL_LOCK:
|
with GLOBAL_LOCK:
|
||||||
if not self.instance:
|
if not self.instance:
|
||||||
self.instance = self.factory(*args, **kwargs)
|
self.instance = self.factory(*args, **kwargs)
|
||||||
return self.instance
|
return self.instance
|
||||||
|
|
||||||
def reset(self):
|
|
||||||
"""Reset instance."""
|
|
||||||
self.instance = None
|
|
||||||
|
|
||||||
@property
|
|
||||||
def injections(self):
|
|
||||||
"""Return tuple of all injections."""
|
|
||||||
return self.factory.injections
|
|
||||||
|
|
||||||
|
|
||||||
class ExternalDependency(Provider):
|
class ExternalDependency(Provider):
|
||||||
"""External dependency provider.
|
"""External dependency provider.
|
||||||
|
|
Binary file not shown.
Before Width: | Height: | Size: 10 KiB After Width: | Height: | Size: 25 KiB |
Binary file not shown.
Before Width: | Height: | Size: 10 KiB After Width: | Height: | Size: 26 KiB |
|
@ -1,8 +1,10 @@
|
||||||
Singleton providers
|
Singleton providers
|
||||||
-------------------
|
-------------------
|
||||||
|
|
||||||
``di.Singleton`` provider creates new instance of specified class on first call
|
.. module:: dependency_injector.providers
|
||||||
and returns same instance on every next call.
|
|
||||||
|
:py:class:`Singleton` provider creates new instance of specified class on
|
||||||
|
first call and returns same instance on every next call.
|
||||||
|
|
||||||
Example:
|
Example:
|
||||||
|
|
||||||
|
@ -16,9 +18,9 @@ Example:
|
||||||
Singleton providers and injections
|
Singleton providers and injections
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
``di.Singleton`` providers use ``di.Factory`` providers for first creation of
|
:py:class:`Singleton` providers use :py:class:`Factory` providers for first
|
||||||
specified class instance, so, all of the rules about injections are the same,
|
creation of specified class instance, so, all of the rules about injections
|
||||||
as for ``di.Factory`` providers.
|
are the same, as for :py:class:`Factory` providers.
|
||||||
|
|
||||||
.. image:: /images/providers/singleton_internals.png
|
.. image:: /images/providers/singleton_internals.png
|
||||||
:width: 80%
|
:width: 80%
|
||||||
|
@ -26,29 +28,29 @@ as for ``di.Factory`` providers.
|
||||||
|
|
||||||
.. note::
|
.. note::
|
||||||
|
|
||||||
Due that ``di.Singleton`` provider creates specified class instance only on
|
Due that :py:class:`Singleton` provider creates specified class instance
|
||||||
the first call, all injections are done once, during the first call, also.
|
only on the first call, all injections are done once, during the first
|
||||||
Every next call, while instance has been already created and memorized, no
|
call, also. Every next call, while instance has been already created
|
||||||
injections are done, ``di.Singleton`` provider just returns memorized
|
and memorized, no injections are done, :py:class:`Singleton` provider just
|
||||||
earlier instance.
|
returns memorized earlier instance.
|
||||||
|
|
||||||
This may cause some problems, for example, in case of trying to bind
|
This may cause some problems, for example, in case of trying to bind
|
||||||
``di.Factory`` provider with ``di.Singleton`` provider (provided by
|
:py:class:`Factory` provider with :py:class:`Singleton` provider (provided
|
||||||
dependent ``di.Factory`` instance will be injected only once, during the
|
by dependent :py:class:`Factory` instance will be injected only once,
|
||||||
first call). Be aware that such behaviour was made with opened eyes and is
|
during the first call). Be aware that such behaviour was made with opened
|
||||||
not a bug.
|
eyes and is not a bug.
|
||||||
|
|
||||||
By the way, in such case, ``di.Delegate`` provider can be useful. It makes
|
By the way, in such case, :py:class:`Delegate` provider can be useful. It
|
||||||
possible to inject providers *as is*. Please check out full example in
|
makes possible to inject providers *as is*. Please check out full example
|
||||||
*Providers delegation* section.
|
in *Providers delegation* section.
|
||||||
|
|
||||||
Singleton providers resetting
|
Singleton providers resetting
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
Created and memorized by ``di.Singleton`` instance can be reset. Reset of
|
Created and memorized by :py:class:`Singleton` instance can be reset. Reset of
|
||||||
``di.Singleton``'s memorized instance is done by clearing reference to it.
|
:py:class:`Singleton`'s memorized instance is done by clearing reference to
|
||||||
Further lifecycle of memorized instance is out of ``di.Singleton`` provider's
|
it. Further lifecycle of memorized instance is out of :py:class:`Singleton`
|
||||||
control.
|
provider's control.
|
||||||
|
|
||||||
Example:
|
Example:
|
||||||
|
|
||||||
|
@ -58,13 +60,13 @@ Example:
|
||||||
Singleton providers delegation
|
Singleton providers delegation
|
||||||
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
|
||||||
|
|
||||||
``di.Singleton`` provider could be delegated to any other provider via any
|
:py:class:`Singleton` provider could be delegated to any other provider via
|
||||||
kind of injection. Delegation of ``di.Singleton`` providers is the same as
|
any kind of injection. Delegation of :py:class:`Singleton` providers is the
|
||||||
``di.Factory`` providers delegation, please follow
|
same as :py:class:`Factory` providers delegation, please follow *Factory
|
||||||
*Factory providers delegation* section for example.
|
providers delegation* section for example.
|
||||||
|
|
||||||
``di.Singleton`` delegate could be created obviously using
|
:py:class:`Singleton` delegate could be created obviously using
|
||||||
``di.Delegate(di.Singleton())`` or by calling ``di.Singleton.delegate()``
|
``Delegate(Singleton(...))`` or by calling ``Singleton(...).delegate()``
|
||||||
method.
|
method.
|
||||||
|
|
||||||
Example:
|
Example:
|
||||||
|
|
|
@ -1,6 +1,6 @@
|
||||||
"""`di.Singleton` providers example."""
|
"""`Singleton` providers example."""
|
||||||
|
|
||||||
import dependency_injector as di
|
from dependency_injector import providers
|
||||||
|
|
||||||
|
|
||||||
class UserService(object):
|
class UserService(object):
|
||||||
|
@ -8,7 +8,7 @@ class UserService(object):
|
||||||
|
|
||||||
# Singleton provider creates new instance of specified class on first call and
|
# Singleton provider creates new instance of specified class on first call and
|
||||||
# returns same instance on every next call.
|
# returns same instance on every next call.
|
||||||
users_service_provider = di.Singleton(UserService)
|
users_service_provider = providers.Singleton(UserService)
|
||||||
|
|
||||||
# Retrieving several UserService objects:
|
# Retrieving several UserService objects:
|
||||||
user_service1 = users_service_provider()
|
user_service1 = users_service_provider()
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
"""`di.Singleton` providers delegation example."""
|
"""`Singleton` providers delegation example."""
|
||||||
|
|
||||||
import dependency_injector as di
|
from dependency_injector import providers
|
||||||
|
|
||||||
|
|
||||||
# Some singleton provider and few delegates of it:
|
# Some singleton provider and few delegates of it:
|
||||||
singleton_provider = di.Singleton(object)
|
singleton_provider = providers.Singleton(object)
|
||||||
singleton_provider_delegate1 = singleton_provider.delegate()
|
singleton_provider_delegate1 = singleton_provider.delegate()
|
||||||
singleton_provider_delegate2 = di.Delegate(singleton_provider)
|
singleton_provider_delegate2 = providers.Delegate(singleton_provider)
|
||||||
|
|
||||||
# Making some asserts:
|
# Making some asserts:
|
||||||
assert singleton_provider_delegate1() is singleton_provider
|
assert singleton_provider_delegate1() is singleton_provider
|
||||||
|
|
|
@ -1,13 +1,13 @@
|
||||||
"""`di.Singleton` providers resetting example."""
|
"""`Singleton` providers resetting example."""
|
||||||
|
|
||||||
import dependency_injector as di
|
from dependency_injector import providers
|
||||||
|
|
||||||
|
|
||||||
class UserService(object):
|
class UserService(object):
|
||||||
"""Example class UserService."""
|
"""Example class UserService."""
|
||||||
|
|
||||||
# Users service singleton provider:
|
# Users service singleton provider:
|
||||||
users_service_provider = di.Singleton(UserService)
|
users_service_provider = providers.Singleton(UserService)
|
||||||
|
|
||||||
# Retrieving several UserService objects:
|
# Retrieving several UserService objects:
|
||||||
user_service1 = users_service_provider()
|
user_service1 = users_service_provider()
|
||||||
|
|
Loading…
Reference in New Issue
Block a user