-
Notifications
You must be signed in to change notification settings - Fork 530
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
Generic vs non-generic ResolutionExtension.TryGet overloads are inconsistent #378
Comments
Thanks for reporting. I'll take a look. |
Hmm.... There are some interesting tests in |
From my understanding, the "TryGet" seems very "kind" about the resolution process. |
As you can see, the name of the tests contains "ResolvesUsingFirstMatchingBinding" |
Whether or not I simply cannot conceive a reasonable explanation why All versions of Using As for the tests: They are currently disabled / skipped which (to me) tells me that somebody has realized this inconsistency before but never got around to actually addressing it. The tests literally show excactly how / where the different |
So it really depends on the definition of "TryGet". Literally, returning the first matched means we tried our best and we think the first one is the most probable candidate, while returning null is more consistent with "Get" but it hides two cases. One case is no binding found and not self-bindable, another case is multiple bindings found. |
Let me check with Microsoft Dependency Injection library and see what's their solution about GetService when there are multiple registrations. |
It looks like the Microsoft Dependency Injection library uses last descriptor when call GetService/GetRequiredService. |
There are three options here for
The relevant
We can provide a setting for this behavior to let user select what behavior they want. Anyway, I agree that we should make it consistent for all |
According to my understanding of the Ninject conventions, you should only use If you simply do not know if there are zero or more matching bindings, you should use Also... after (successfully, but painfully) implementing a Ninject integration for ASP.NET Core (https://github.com/lord-executor/Ninject.Web.AspNetCore/tree/bugfix/service-provider-resolve-latest/src/Ninject.Web.AspNetCore) and going through the implementation details of the Microsoft dependency injection code, I have come to the following conclusions:
I would even go so far as to argue that this temporal coupling aspect of extension methods calling each other all over the place is the worst feature of that DI system and consequently looking to that implementation for guidance would be unwise. Btw: Sorry.... I have what I like to refer to as "strong opinions" on topics where I have spent a lot of time analyzing and comparing different designs and Ninject vs. Microsoft.Extensions.DependencyInjection is one such topic. |
Run the following code in RoslynPad or in a simple .NET console application with minor adaptations.
To be precise, the exception is:
The only difference in the two calls is that one uses the generic version
TryGet<T>
while the other does not.The problem lies in the different parameters to
GetResolutionIterator
intrue
for isUniquefalse
for isUniqueTo me, this seems very obviously incorrect and from the code in
TryGet
which explicitly catches anActivationException
, the case seems quite clear: all overloads ofTryGet
should passtrue
for isUnique. That way, the method behaves as expected and just returns null if it cannot resolve the request to a uniquely defined service.I have not actually tested this, but from looking at the source code of the current master branch, I would say the problem exists there as well.
I can easily provide a PR for a fix, but it seems that there is really not a lot of activity on this project at the moment. If any one of the maintainers of this project is at least reading this, please give a sign.
The text was updated successfully, but these errors were encountered: