Lately dependency injection has become a popular topic within the developer community. This may be caused (or be the cause for – a bit like chicken and egg) by the availability of respective containers. One of the first broadly used containers was probably Spring.NET (a .NET port of the java Spring Framework), the castle project came to my attention a few times, and the latest addition is the Policy Injection Application Block (PIAB) as part of the Enterprise Library 3.0 (Microsoft patterns & practices group).
If you are new to dependency injection, the castle project “getting started” does a good job of highlighting the gist. Since the PIAB is a relatively new addition to the Enterprise Library (and came quite as a surprise) you may want to have a look at the announcement with a general introduction or some implementation details.
Dependency injection as a basic concept that has its value on its own, yet it is also tied to some other concepts, namely factories (the usual way to realize dependency injection) and aspect oriented programming (AOP, aspects being just special dependencies to inject).
I have to admit that I am not exactly a big fan of AOP (to say the least). And dependency injection in all its broad beauty requires some real hard thinking during design, discipline during development, and a sound understanding of concept and design during maintenance. Some of these demands may be in short supply — which is neither surprising nor exactly a bad thing; different developers (especially corporate developers) simply have different backgrounds and different topic priorities. Therefore, despite the technical fanciness and the fact that dependency injection can boost flexibility, I really need a compelling reason to employ it.
Lower one’s sights
So what if dependency injection is considered too complex in a certain situation? Are we back to hardcoding? Certainly not! Enter factories.
I am a big fan of factories. Factories are a well know pattern since the advent of patterns in public awareness. They also have (the potential to have) more impact on software architecture than most other basic patterns. Did I mention that they may lay the foundation for more complex patterns, such as dependency injection and AOP?
I have used factories of a certain kind to great benefit with different patterns. Actually these patterns can be seen as degraded variants of dependency injection. (They may also have characteristics of AOP, but I won’t admit that :-) ). The primary purposes I use them for are:
- Layer separation
- (Framework) Extension points
Despite the fact that the actual factory patterns I use are quite simple and quite easy to grasp, my approach has several benefits, e.g.:
- Better layer interfaces/layer separation/separation of concerns
- The easy employment of simulators and mock objects allows independent development of layers and better testability
- “Chaining” or “call interception” (if needed!) can be used to add orthogonal functionality such as caching. Actually this works exactly like described in the PIAB, albeit not with tool support.
- The possibility to adorn common features with application specific features.
Of course all this (and probably more) can be done with fully fledged dependency injection. But at the cost of more complexity (and container dependency may be an issue, too). (And to prevent angry comments: I’m not saying dependency injection is bad — Au contraire! — I’m just presenting an alternative approach.)
I’m going to dig into the details in the following posts, concepts and code. But not today.