-
-
Notifications
You must be signed in to change notification settings - Fork 9
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
Inject named Autowired params when named args already present #14
Inject named Autowired params when named args already present #14
Conversation
@@ -65,11 +65,12 @@ def autowired(func: T) -> T: | |||
def wrapper(*args, **kwargs): | |||
bound_arguments = signature.bind_partial(*args, **kwargs).arguments | |||
args = list(args) | |||
caller_passed_kwargs = len(kwargs) > 0 |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
detect any incoming named params
for parameter in autowired_parameters: | ||
if parameter.name in bound_arguments: | ||
continue | ||
dependency = parameter.annotation.inject() | ||
if parameter.kind is parameter.KEYWORD_ONLY: | ||
if caller_passed_kwargs or (parameter.kind is parameter.KEYWORD_ONLY): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
if we already have named params we need to inject as named
@@ -164,3 +164,24 @@ def f(a: AutowiredMockA, b: AutowiredMockB, c: AutowiredMockC): | |||
assert parameters["a"] is None | |||
assert parameters["b"] is AutowiredMockB.inject() | |||
assert parameters["c"] is None | |||
|
|||
def test__autowired__injects_named_autowired_args_when_named_args_defined_by_the_caller(self): |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
This is subtle variation on the previous test, reversing the b, c
args showed the issue fixed by this change
Hi @craigminihan, thanks for the Pull Request with a reproducible code and unit tests. I believe a regression test is suitable for this too though I can add it myself :) I was able to confirm the issue in injectable version 3.4.0 using Python 3.6.8. I'm currently reviewing your PR. Your report concerns me in that there may be other issues with positional-only and keyword-only args being marked for autowiring. I'll dig into it and finish reviewing your Pull Request later today. |
Kudos, SonarCloud Quality Gate passed! 0 Bugs No Coverage information |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@craigminihan this fix will be released in version 3.4.1 and should be available at PyPI today in a couple of minutes from now. Thanks for your help on this bug!
if parameter.kind is parameter.KEYWORD_ONLY: | ||
kwargs[parameter.name] = dependency | ||
else: | ||
if parameter.kind is parameter.POSITIONAL_ONLY: | ||
args.append(dependency) | ||
else: | ||
kwargs[parameter.name] = dependency |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@craigminihan I've inverted this logic to always inject parameters as named args except for when the parameter is positional only. This will fix the issue and play nicely with Python 3.8's positional-only args too.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@allrod5 nice work! I'll check out 3.4.1 shortly
Fix #15.
Fixes the following:
Previously
injectable
addedmy_dep
as a positional causing a duplicate parameter error to be thrown.