Skip to content

Issue a warning if the decorated function doesn't use Provide arguments #654

Closed
@warvariuc

Description

@warvariuc

When a function is decorated with @inject the wrapped function is inspected for Provide[...] arguments:

signature = inspect.signature(fn)

But if multiple decorators are used like this

@inject
@some_other_decorator
def my_func(...):

and some_other_decorator doesn't use functools.wraps, the Provide arguments are not found.

Here is a reproducible example:

import functools
from dependency_injector import containers, providers
from dependency_injector.wiring import Provide, inject


    
def some_other_decorator(func):
    @functools.wraps(func)
    def wrapped(*args, **kwargs):
        return func(*args, **kwargs)
    return wrapped



class Service:
    ...


class Container(containers.DeclarativeContainer):
    service = providers.Factory(Service)


@inject
@some_other_decorator
def main(service: Service = Provide[Container.service]) -> None:
    print(service)


if __name__ == "__main__":
    container = Container()
    # btw, this doesn't work: container.wire(modules=[__name__])
    # copied from https://github.com/ets-labs/python-dependency-injector/blob/master/examples/wiring/example.py
    container.wire(modules=[__name__])
    main()

If we comment out the @functools.wraps(func) line, we get printed:

<dependency_injector.wiring.Provide object at 0x10ae99fd0>

Issuing a warning inside _fetch_reference_injections if the decorated function doesn't have Provide arguments would help:

  1. When such a decorator is used
  2. When someone is using @inject and Provide was removed as unnecessary.

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions