How to ensure transient DI services are chained correctly - c#

Okay, so more than anything I think I either have a terminology issue here or otherwise I need some help understanding why what I'm thinking of is not such a good idea. Unfortunately, I'm self-taught so often my terminology is wrong or old-fashioned. I've no problem accepting that some of the code I produce contains quite a few smells, but I want to understand what makes it smelly so that I can attack the most risky parts first.
I've been making some use of the DI functionality baked into .NET in recent years, mostly for injection of singletons into MVC controllers. I'm now trying to make better and more expansive use of DI, and especially to stamp out the remaining places where I've got business logic directly in actions on controllers.
So currently, I have no issue getting an ILogger<ControllerType> and a singleton of IDatabase (not really called that but you get the idea) injected into controllers. Within the controller constructor, I then create an instance of, for example, ReallyUsefulHelper that takes an ILogger and an IDatabase in it's own constructor. That's very handy, as then the logging from within ReallyUsefulHelper has the controller scope and it's clear in the log output as to which controller the call inside ReallyUsefulHelper came from.
I'm aware though that controllers themselves are transient (new instance for every request) and some of my services like ImportantButLessCommonlyUsedHelper might be a little expensive to instantiate, so I want to inject ReallyUsefulHelper transiently, and perhaps her cousin ImportantButLessCommonlyUsedHelper scoped. Of course, there's many more different such services across the application but you get the idea.
My question is - is there some way to have the controller's ILogger<T> instance injected into the IHelper instance during instantiation by the DI container? If so, what would this approach be called, so I can read more about it? If there's something wrong with this, what is it so that I can understand better? It seems clunky to me to pass an ILogger to each method in the IHelper that needs it which would otherwise get the job done. I have seen lower level libraries that provide a delegate for you to attach your ILogger.Log() method to but this also seems clunky and unnecessary for my purpose.

Related

In IoC, what is the practice for loading an object by ID?

I've just started learning about IoC, and I understand the general use of it, but so far, the loading process from AutoFac, Ninject and Zenject seem to be based on loading an object not based on data.
In other words, ConsoleLogger is created when ILogger is requested, which does not require any special ID's, and that makes sense. However, what about when I want to load IUser for Id 4? Is there a standard IoC for handling that, or are the interfaces supposed to carry methods for loading based on Id?
For instance, am I supposed to have IUserManager, with LoadUser(int id) as a method? or is there some IoC structure for this as well?
Thanks.
[note: I did search the web for this, but my queries did not seem to pull up relevant information and the similar question search yields too many generic questions to filter]
IoC containers rules the way we link object's by dependencies, dependencies means some logic under Iterfaces, so IoC mostly works on Type level rather then Instance level.
Please note that types which has no any dependencies, interfaces as well as special scope requirements may be legally created by using "new" keyword for e.g. Data Transfer Objects (dto's).
In your case, you probably need a some kind of factory that can realize by parameters what kind of object caller is needed.
However, I'll suggest to you separate data from business logic as much is it can be separated.

What good is Unity DI in MVC?

I'm slightly new to Unity and IoC, but not to MVC. I've been reading and reading about using Unity with MVC and the only really useful thing I'm consistently seeing is the ability to get free DI with the controllers.
To go from this:
public HomeController() : this(new UserRepository())
{
}
public HomeController(IUserRepository userRepository)
{
this.UserRepository = userRepository;
}
To this:
public HomeController(IUserRepository userRepository)
{
this.UserRepository = userRepository;
}
Basically, allowing me to drop the no parameter constructor. This is great and all and I'm going to implement this for sure, but it doesn't seem like it's anything really that great for all the hype about IoC libraries. Going the way of using Unity as a service locator sounds compelling, but many would argue it's an anti pattern.
So my question is, with service locating out of the question and some DI opportunities with Views and Filters, is there anything else I gain from using Unity? I just want to make sure I'm not missing something wonderful like free DI support for all class constructors.
EDIT:
I understand the testability purpose behind using Unity DI with MVC controllers. But all I would have to do is add that one extra little constructor, nix Unity, and I could UnitTest just the same. Where is the great benefit in registering your repository types and having a custom controller factory when the alternative is simpler? The alternative being native DI. I guess I'm really wondering what is so great about Unity (or any IoC library) besides Service Locating which is bad. Is free Controller DI really the ONLY thing I get from Unity?
A good IoC container not only creates the concrete class for you, it examines the couplings between that type and other types. If there are additional dependencies, it resolves them and creates instances of all of the classes that are required.
You can do fancy things like conditional binding. Here's an example using Ninject (my preferred IoC):
ninjectKernel.Bind<IValueCalculator>().To<LinqValueCalculator>();
ninjectKernel.Bind<IValueCalculator>().To<IterativeValueCalculator().WhenInjectedInto<LimitShoppingCart>();
What ninject is doing here is creating an instance of IterativeValueCalculator when injecting into LimitShoppingCart and an instance of LinqValueCalulator for any other injection.
Greatest benefit is separation of concern (decoupling) and testability.
Regarding why Service Locator is considered bad(by some guys) you can read this blog-post by Mark Seeman.
Answering on your question What is so good in Unity I can say that apart from all the testability, loosely-coupling and other blah-blah-blah-s everyone is talking about you can use such awesome feature like Unity's Interception which allows to do some AOP-like things. I've used it in some of last projects and liked it pretty much. Strongly recommended!
p.s. Seems like Castle Windsor DI container has similar feature as well(called Interceptors). Other containers - not sure.
Besides testing (which is a huge benefit and should not be under estimated), dependency injection allows:
Maintainability: The ability to alter the behavior of your code with a single change.
If you decide to change the class that retrieves your users across all your controllers/services etc. without dependency injection, you need to update each and every constructor plus any other random new instances that are being created, provided you remember where each one lives. DI allows you to change one definition that is then used across all implementations.
Scope: With a single line of code you can alter your implementation to create a singleton, a class that is only created on each new web request or on each new thread
Readability: The use of dependency injection means that all your concrete classes are defined in one place. As a developer coming onto a project, I can quickly and easily see exactly which concrete classes are mapped to which interfaces and know that there are no hidden implemetations. It means I can not only read the code better but empowers me to have the confidence to develop against the code
Design: I believe using dependency injection helps create well designed code. You automatically code to interfaces, your code becomes cleaner because you haven't got strange blocks of code to help you test
And let's no forget...
Testing: Testing is huge! Dependency injection allows you to test your code without having to write code specifically for tests. Ok, you can create a new constructor, but what is stop anyone else using that constructor for a purpose it has not been intended for. What if another developer comes along six months later and adds production logic to your 'test' constructor. Ok, so you can make it internal but this can still be used by production code. Why give them the option.
My experience with IoC frameworks has been largely around Ninject. As such, the above is based on what I know of Ninject, however the same principles should remain the same across other frameworks.
No the main point is that you then have a mapping somewhere that specifies the concrete type of IUserRepository. And the reason that you might like that is that you can then create a UnitTest that specifies a mocked version of IUserRepository and execute your tests without changing anything in your controller.
Testability mostly, but id suggest looking at Ninject, it plays well with MVC. To get the full benefits of IOC you should really be combining this with Moq or a similar mocking framework.
Besides the testability, I think you can also add the extensibility as one of the advantages. One of the best practices of Software Development is "working with abstractions, not with implementations" and, while you can do it in several ways, Unity provides a very extensible and easy way to achieve this. By using this, you will be creating abstractions that will define the contracts that your component must comply. Say that you want to change totally the Repository that your application currently uses. With DI you just "swap" the component without the need of changing a single line of code on your application. If you are using hard references, you might need to change and recompile your application because of a component that is external to it (In a different layer)
So, bottom line, IMHO, using DI helps you to have pluggable components in your application and have a SOLID application design

Busy constructors in Ioc - are they a code smell?

I have ended up with a constructor that looks like this whilst attempting to end up with an object i can easily test.
public UserProvider(
IFactory<IContainer> containerFactory,
IRepositoryFactory<IUserRepository> userRepositoryFactory,
IFactory<IRoleProvider> roleProviderFactory,
IFactory<IAuthenticationProvider> authenticationProviderFactory,
IFactory<IEmailAdapter> emailAdapterFactory,
IFactory<IGuidAdapter> guidAdapterFactory,
IRepositoryFactory<IVehicleRepository> vehicleRepositoryFactory,
IRepositoryFactory<IUserVehicleRepository> userVehicleRepositoryFactory,
IFactory<IDateTimeAdapter> dateTimeAdapterFactory)
This is all the dependencies the object will have and is the busiest constructor i have. But if someone saw this would it really raise a big wtf?
My aim was to end up with logic that is easy to test. Whilst it requires a good amount of mocks it is certainly very easy to verify my logic. However i am concerned that I may of ended up with too much of a good thing.
I am curious if this is normal for most people implementing ioc.
There are several simplifications I can make - such as I don't really need to pass in the factories for several of the adapters as i could just pass the adapter in directly as it has no internal state. But I am really asking in terms of the number of parameters.
Or more to the point i am looking for assurance that I am not going overboard ;)
But I am beginnign to get the impression that the UserProvider class should be broken down a bit - but then I end up with even more plumbing which is what is driving this concern.
I guess a sub question is maybe should I be considering using a service Locator pattern if I have these concerns?
When using DI and constructor injection violation of the SRP becomes very visible. This is acutally a good thing, and it is not DI / IOC's fault. If you were not using constructor injection, the class would have the same dependencies, it would just not be as visible.
What you could do in your concrete example is hide some of the related dependencies behind facades. For example IVehicleRepository and IUserVehicleRepository could be hidden behind an IVehicle facade. It might also make sense to put IUserRepository, IRoleProvider and IAuthenticationProvider behind a facade.
In my opinion that is a lot of parameters for a constructor. Here's how I would handle this to get good testability and reduce "code smell."
Instead of passing in the factories to create instances of your classes just pass in the classes themselves. This automatically cuts your dependencies in half because the UserProvider would not be concerned with creating any objects that it needs (and subsequently disposing of them if necessary) it would just use what is given to it instead of using the factories that it needs to create object instances that it needs.
Remove your adapters from the constructor and just create instances of these interfaces inside of the UserProvider. Think about how often are you going to need to change the way you format a guid for example. This would still be testable as long as your adapters don't have a lot of dependencies.
The point I'm making is to get a good balance of testability and practicality. When implementing Ioc try and determine where you've had trouble with testability in the past and where you've had issues maintaining and changing code because there were too many dependencies. That is where you'll see the most benefit.

Problems faced when trying to apply good Dependency Injection practice

I've been using IoC (mostly Unity) and Dependency Injection in .NET for some time now and I really like the pattern as a way to encourage creation of software classes with loose coupling and which should be easier to isolate for testing.
The approach I generally try to stick to is "Nikola's Five Laws of IoC" - in particular not injecting the container itself and only using constructor injection so that you can clearly see all the dependencies of a class from its constructor signature. Nikola does have an account on here but I'm not sure if he is still active.
Anyway, when I end up either violating one of the other laws or generally ending up with something that doesn't feel or look right, I have to question whether I'm missing something, could do it better, or simply shouldn't be using IoC for certain cases. With that in mind here are a few examples of this and I'd be grateful for any pointers or further discussion on these:
Classes with too many dependencies. ("Any class having more then 3 dependencies should be questioned for SRP violation"). I know this one comes up a lot in dependency injection questions but after reading these I still don't have any Eureka moment that solves my problems:
a) In a large application I invariably find I need 3 dependencies just to access infrastructure (examples - logging, configuration, persistence) before I get to the specific dependencies needed for the class to get its (hopefully single responsibility) job done. I'm aware of the approach that would refactor and wrap such groups of dependencies into a single one, but I often find this becomes simply a facade for several other services rather than having any true responsibility of its own. Can certain infrastructure dependencies be ignored in the context of this rule, provided the class is deemed to still have a single responsibility?
b) Refactoring can add to this problem. Consider the fairly common task of breaking apart a class that has become a bit big - you move one area of functionality into a new class and the first class becomes dependent on it. Assuming the first class still needs all the dependencies it had before, it now has one extra dependency. In this case I probably don't mind that this dependency is more tightly coupled, but its still neater to have the container provide it (as oppose to using new ...()), which it can do even without the new dependency having its own interface.
c) In a one specific example I have a class responsible for running various different functions through the system every few minutes. As all the functions rightly belong in different areas, this class ends up with many dependencies just to be able to execute each function. I'm guessing in this case other approaches, possibly involving events, should be considered but so far I haven't tried to do it because I want to co-ordinate the order the tasks are run and in some cases apply logic involving outcomes along the way.
Once I'm using IoC within an application it seems like almost every class I create that is used by another class ends up being registered in and/or injected by the container. Is this the expected outcome or should some classes have nothing to do with IoC? The alternative of just having something new'd up within the code just looks like a code smell since its then tightly coupled. This is kind of related to 1b above too.
I have all my container initialisation done at application startup, registering types for each interface in the system. Some are deliberately single instance lifecycles where others can be new instance each time they are resolved. However, since the latter are dependencies of the former, in practice they become a single instance too since they are only resolved once - at construction time of the single instance. In many cases this doesn't matter, but in some cases I really want a different instance each time I do an operation, so rather than be able to make use of the built in container functionality, I'm forced to either i) have a factory dependency instead so I can force this behaviour or ii) pass in the container so I can resolve each time. Both of these approaches are frowned upon in Nikola's guidance but I see i) as the lesser of two evils and I do use it in some cases.
In a large application I invariably find I need 3 dependencies just to access infrastructure (examples - logging, configuration, persistence)
imho infrastructure is not dependencies. I have no problem using a servicelocator for getting a logger (private ILogger _logger = LogManager.GetLogger()).
However, persistence is not infrastructure in my point of view. It's a dependency. Break your class into smaller parts.
Refactoring can add to this problem.
Of course. You will get more dependencies until you have successfully refactored all classes. Just hang in there and continue refactoring.
Do create interfaces in a separate project (Separated interface pattern) instead of adding dependencies to classes.
In a one specific example I have a class responsible for running various different functions through the system every few minutes. As all the functions rightly belong in different areas, this class ends up with many dependencies just to be able to execute each function.
Then you are taking the wrong approach. The task runner should not have a dependency on all tasks that should run, it should be the other way around. All tasks should register in the runner.
Once I'm using IoC within an application it seems like almost every class I create that is used by another class ends up being registered in and/or injected by the container.*
I register everything but business objects, DTOs etc in my container.
I have all my container initialisation done at application startup, registering types for each interface in the system. Some are deliberately single instance lifecycles where others can be new instance each time they are resolved. However, since the latter are dependencies of the former, in practice they become a single instance too since they are only resolved once - at construction time of the single instance.
Don't mix lifetimes if you can avoid it. Or don't take in short lived dependencies. In this case you could use a simple messaging solution to update the single instances.
You might want to read my guidelines.
Let me answer question 3. Having a singletons depend on a transient is a problem that container profilers try to detect and warn about. Services should only depend on other services that have a lifetime that is greater than or equals to that of their own. Injecting a factory interface or delegate to solve this is in general a good solution, and passing in the container itself is a bad solution, since you end up with the Service Locator anti-pattern.
Instead of injecting a factory, you can solve this by implementing a proxy. Here's an example:
public interface ITransientDependency
{
void SomeAction();
}
public class Implementation : ITransientDependency
{
public SomeAction() { ... }
}
Using this definition, you can define a proxy class in the Composition Root based on the ITransientDependency:
public class TransientDependencyProxy<T> : ITransientDependency
where T : ITransientDependency
{
private readonly UnityContainer container;
public TransientDependencyProxy(UnityContainer container)
{
this.container = container;
}
public SomeAction()
{
this.container.Resolve<T>().SomeAction();
}
}
Now you can register this TransientDependencyProxy<T> as singleton:
container.RegisterType<ITransientDependency,
TransientDependencyProxy<Implementation>>(
new ContainerControlledLifetimeManager());
While it is registered as singleton, it will still act as a transient, since it will forward its calls to a transient implementation.
This way you can completely hide that the ITransientDependency needs to be a transient from the rest of the application.
If you need this behavior for many different service types, it will get cumbersome to define proxies for each and everyone of them. In that case you could try Unity's interception functionality. You can define a single interceptor that allows you to do this for a wide range of service types.

Question on DI and how to solve some problems

I'm a newbie to Dependency Injection. I have never used and never even undestood what it is exatcly all about, but after my last attack on this topic I found out that is a way of uncoupling an object and its dependencies, once they are not responsible for instantiating the concrete versions of its dependencies anymore, as now the container will do it for us and deliver the ready object in our hands.
Now the point is; "when should I use it?", ALWAYS??? Actually, as I'm a newbie and have never even seen a project that uses this pattern I can't undestand how I should apply it to my domain objects!!! It seems to me that I will nevermore instantiate my objects and the container will always do it for me, but then comes some doubts...
1) What about oobjects that part of its dependencies comes from the UI, for example;
public class User(String name, IValidator validator)
Say that I get the user name from the UI, so how will the conatiner know it and still delliver this object for me?
2) Theres other situation I'm facing; if a dependency is now an object that is already instantiated, say... a SINGLETON object, for example . I saw theres settings regarding out the scope of life of the dependency beign injected (im talking about Spring.NET, eg; http request scope)... BUT, request and other web related things are on my presentation layer, so how could I link both my presentation layer and my domain layer without breaking any design rule (as my domain should be totally unaware of where its is being consumed, not to have layer dependency, etc)
Im eager to hear from you all. Thanks very much.
In general, once you go IoC, you tend to want to register EVERYTHING with IoC and have the container spit out fully-hydrated objects. However, you bring up some valid points.
Perhaps a definition of "dependency" is in order; at its broadest, a dependency is simply a set of functionality (interface) that a given class requires a concrete implementation of in order for the class to work correctly. Thus, most non-trivial programs are full of dependencies. To promote ease of maintenance, loose coupling of all dependencies is generally preferred. However, even when loosely coupled, you don't need to automate instantiation of dependencies if those objects require specialized information that you don't want to pollute your IoC registry with. The goal is to loosely couple usage, not necessarily creation.
Concerning point 1, some IoC frameworks don't do well with being given external parameters. However, you can usually register a delegate as a factory method. That delegate may belong to an object like a Controller that is given external information by the UI. Logins are a perfect example: Create an object, say a LoginController, and register it with IoC as your ILoginController. You'll reference that controller on your Login page, it will be injected when the Login page is instantiated, and the login page will pass it the credentials entered. The Controller will then perform authentication, and will have a method GetAuthenticatedUser() that produces a User object. You can register this method with IoC as a Factory for Users, and whenever a User is needed, the factory delegate will either be evaluated, or passed wholesale to the dependent method which will call it when it really needs the User.
On point 2, setting up a single instance of an object is a strength of the IoC pattern. Instead of creating a true singleton, with a private instance constructor, static instance and static constructor to produce an instance, you simply register the class with IoC and tell it to only instantiate it once and use that one instance for all requests. The strength is the flexibility; if you later want there to be more than one instance, you just change the registration. You won't break any design pattern rules either way; the view will always have a Controller injected, whether that Controller is the same for all pages or a new instance per request.
1) this contructor is probably not the right one to use, may be you are injecting the validator in the wrong place/way.
2)Neighter View nor Model and nor Controller should be aware of there is an IoC, it should lie in the background architecture ( where MVC components are actually instantiated )
You should use IoC when you feel the architecture can became complex and has to be mantained by many people. If you are writing an enterprise application, or a UI you think to extend with plugins, you probably need it, if you are writing a command line utility, probably not.
You should use dependency injection whenever you want any of the following benefits:
The ability to replace modules easily
The ability to reuse modules between parts of the application, or different applications
When you want to do parallel development, so that components of a system can be developed in isolation and in parallel because they depend on abstractions
When you want easier maintenance of a system because of loose coupling
When you want testability (a specialisation of replacing modules). This is one of the biggest reasons for using DI
To answer your other questions:
1) You can configure many IoC containers so that certain constructor parameters can be specified, whilst others are resolved by the container. However, you may need to think about refactoring that piece of code, as a UserFactory may be more appropriate which takes the validator dependency, and has a NewUser method which takes a user name and returns a new user (either instantiating it directly or resolving from the container).
2) Each application you build will have a composition root, where your container is configured, and the root object is resolved. Each app will therefore have its own IoC configuration, so there is an expected link between the application type and the configuration settings. Any common abstraction registrations can be placed in configuration code which can be shared amongst all applications.

Categories

Resources