Skip to content

provide default for a dependencies container from another dependencies container #356

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Closed
shaunc opened this issue Jan 13, 2021 · 5 comments
Assignees

Comments

@shaunc
Copy link

shaunc commented Jan 13, 2021

Here is a case that is sort of a mix of other recipes you have provided: I would like to provide a default value for a dependencies container by taking it from another dependencies container:

from dependency_injector import containers, providers

class PV(containers.DeclarativeContainer):

    foo = providers.Object("foo")

PV_SPEC = dict(foo = providers.Dependency(instance_of = str))

class HasPV(containers.DeclarativeContainer):

    pv = providers.DependenciesContainer(**PV_SPEC)

HasPVSpec = dict(pv = providers.DependenciesContainer(**PV_SPEC))

class HasPV2(containers.DeclarativeContainer):

    has_pv = providers.DependenciesContainer(**HasPVSpec)
    pv = providers.DependenciesContainer(**PV_SPEC)
    pv.override(has_pv.pv)

This gives:

src/dependency_injector/providers.pyx in dependency_injector.providers.DependenciesContainer.override()

src/dependency_injector/providers.pyx in dependency_injector.providers.DependenciesContainer._override_providers()

src/dependency_injector/providers.pyx in dependency_injector.providers.Provider.override()

Error: Provider <dependency_injector.providers.Dependency(<class 'str'>) at 0x7fda702c96d0> could not be overridden with itself
@shaunc
Copy link
Author

shaunc commented Jan 14, 2021

Also tried:

...
HasPVSpec = dict(pv = providers.Dependency(instance_of=containers.DynamicContainer))

class HasPV2(containers.DeclarativeContainer):

    has_pv = providers.DependenciesContainer(**HasPVSpec)
    pv = providers.DependenciesContainer(**PV_SPEC)
    pv.override(has_pv.pv.provided)

Without the "provided" this gives AttributeError: 'dependency_injector.providers.Dependency' object has no attribute 'providers', With the "provided" the error is Error: Dependency is not defined

Update -- sure would be nice if DependenciesContainer took an optional "instance_of" -- even if the instance bound wasn't an actual instance (it could use declarative_parent to sniff for the instance class). Then it wouldn't be necessary to maintain these specs, and also could type check on binding.

@rmk135 rmk135 self-assigned this Jan 14, 2021
@rmk135
Copy link
Member

rmk135 commented Jan 14, 2021

Didn't get to that one today. Will take a look tomorrow.

@rmk135
Copy link
Member

rmk135 commented Jan 15, 2021

Seems #357 feature helps to resolve this one too:

from dependency_injector import containers, providers


class PV(containers.DeclarativeContainer):

    foo = providers.Object('foo')


class HasPV(containers.DeclarativeContainer):

    pv = providers.DependenciesContainer(**PV.dependencies)


class HasPV2(containers.DeclarativeContainer):

    has_pv = providers.DependenciesContainer(**HasPV.dependencies)
    pv = providers.DependenciesContainer(**PV.dependencies)
    pv.override(has_pv.pv)


if __name__ == '__main__':
    haspv2 = HasPV2(pv=PV(foo='bar'))
    print(haspv2.pv.foo())  # prints: bar

What do you think?

@shaunc
Copy link
Author

shaunc commented Jan 19, 2021

Looks good too! -- Thanks!

@shaunc shaunc closed this as completed Jan 19, 2021
@rmk135
Copy link
Member

rmk135 commented Jan 19, 2021

Good, thanks!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants