python-dependency-injector icon indicating copy to clipboard operation
python-dependency-injector copied to clipboard

How to traverse containers up to find other provider

Open chbndrhnns opened this issue 3 years ago • 0 comments

I have not found a good explanation in the docs on how to achieve the following:

There is an application that is organised in bounded contexts which have no overlap, each has a set of controllers (to simplify). However, it should be possible to reference a controller from context "other" in the controllers container of context "one".

What can I do to make the test pass?

Click to toggle self-contained example
from types import SimpleNamespace

from dependency_injector import containers, providers


class Controller:
    def __init__(self, context):
        self.context = context


class OneContextControllers(containers.DeclarativeContainer):
    controller: providers.Singleton = providers.Singleton(Controller, "one")
    controller_from_other_context: providers.Singleton = providers.Singleton(
        lambda: SimpleNamespace(context="What to do here?")
    )


class OtherContextControllers(containers.DeclarativeContainer):
    controller: providers.Singleton = providers.Singleton(Controller, "other")


class OneContext(containers.DeclarativeContainer):
    controllers: providers.Provider[OneContextControllers] = providers.Container(
        OneContextControllers
    )


class OtherContext(containers.DeclarativeContainer):
    controllers: providers.Container[OtherContextControllers] = providers.Container(
        OtherContextControllers
    )


class AppContainer(containers.DeclarativeContainer):
    one_context: providers.Container[OneContext] = providers.Container(OneContext)
    other_context: providers.Container[OtherContext] = providers.Container(OtherContext)


app = AppContainer()


def test_controllers__ok():
    assert app.one_context.controllers.controller().context == "one"
    assert app.other_context.controllers.controller().context == "other"


def test_access_controller_from_other_context():
    assert (
        app.one_context.controllers.controller_from_other_context().context == "other"
    )

chbndrhnns avatar Mar 29 '22 08:03 chbndrhnns