You signed in with another tab or window. Reload to refresh your session.You signed out in another tab or window. Reload to refresh your session.You switched accounts on another tab or window. Reload to refresh your session.Dismiss alert
I believe this is a long-known inconsistency of BoDi, but I believe there's an opportunity to improve it with Reqnroll.
IMHO, user expectation is "I can use IsRegistered() to determine whether I can Resolve() something. If it returns true, I can resolve it. If it returns false, I can't."
This is not how the DI works today. IsRegistered() could return false for a particular dependency, even though a Resolve() operation would work because the dependency was registered at a higher level! In other words, Resolve() will walk up the inheritance chain to see if a dependency has been registered at the Feature or Global level. IsRegistered() simply looks at the current level.
This has lead me to introduce this extension method for my project:
/// <summary>/// Checks if a type is registered at any level in the container hierarchy./// </summary>publicstaticboolIsRegisteredAtAnyLevel<T>(thisIObjectContainercontainer,string?name=null){do{if(container.IsRegistered<T>(name)){returntrue;}}while(containerisObjectContainerc&&(container=c.BaseContainer)!=null);returnfalse;}
I could understand if you didn't want to introduce a breaking change by updating the current behavior of IsRegistered()... There might be some valid use-cases where you truly only want to check the current level. But I'm logging this Issue to argue that a method similar to the above should be incorporated directly into Reqnroll, so users don't have to implement it themselves!
Steps to Reproduce
[BeforeFeature]publicstaticvoidRegisterFeatureDependencies(IObjectContainercontainer){container.RegisterInstanceAs(newMyDependency());}// -----[When("I use my dependency")]publicvoidUseMyDependency(){if(!container.IsRegistered<MyDependency>()){// This will throw!thrownewException("Cannot use MyDependency!");}// Even though the dependency *is* registered (at the Feature level) and would resolve just fine...vardep=container.Resolve<MyDependency>();dep.DoStuff();}
This example is a bit contrived, but in my project we're attempting to provide more human-readable errors to guide users into doing the right thing. For example, we have common step definitions like "Given I am an authorized user", which will grab an auth token and register some things with DI. And for perf reasons, we register those things at the feature level so we don't have to grab a new auth token for every single scenario.
So rather than have an error message like "Couldn't resolve AuthToken", we're trying to proactively use IsRegistered() and hand-written exception messages to guide users into doing the right thing. E.g. "No auth token available. Please ensure your scenario specifies \"Given I am an authorized user\"".
I know this is a niche use-case, but I wanted to provide an example of situations where having an IsRegistered() variant that behaves like Resolve() would be useful 🙂
Link to Repro Project
No response
The text was updated successfully, but these errors were encountered:
Reqnroll Version
2.2.1
Which test runner are you using?
MSTest
Test Runner Version Number
2.2.1
.NET Implementation
.NET 8.0
Test Execution Method
Visual Studio Test Explorer
Content of reqnroll.json configuration file
(shouldn't be necessary for this issue)
Issue Description
I believe this is a long-known inconsistency of BoDi, but I believe there's an opportunity to improve it with Reqnroll.
IMHO, user expectation is "I can use
IsRegistered()
to determine whether I canResolve()
something. If it returnstrue
, I can resolve it. If it returnsfalse
, I can't."This is not how the DI works today.
IsRegistered()
could returnfalse
for a particular dependency, even though aResolve()
operation would work because the dependency was registered at a higher level! In other words,Resolve()
will walk up the inheritance chain to see if a dependency has been registered at the Feature or Global level.IsRegistered()
simply looks at the current level.This has lead me to introduce this extension method for my project:
I could understand if you didn't want to introduce a breaking change by updating the current behavior of
IsRegistered()
... There might be some valid use-cases where you truly only want to check the current level. But I'm logging this Issue to argue that a method similar to the above should be incorporated directly into Reqnroll, so users don't have to implement it themselves!Steps to Reproduce
This example is a bit contrived, but in my project we're attempting to provide more human-readable errors to guide users into doing the right thing. For example, we have common step definitions like
"Given I am an authorized user"
, which will grab an auth token and register some things with DI. And for perf reasons, we register those things at the feature level so we don't have to grab a new auth token for every single scenario.So rather than have an error message like
"Couldn't resolve AuthToken"
, we're trying to proactively useIsRegistered()
and hand-written exception messages to guide users into doing the right thing. E.g."No auth token available. Please ensure your scenario specifies \"Given I am an authorized user\""
.I know this is a niche use-case, but I wanted to provide an example of situations where having an
IsRegistered()
variant that behaves likeResolve()
would be useful 🙂Link to Repro Project
No response
The text was updated successfully, but these errors were encountered: