Jan 5 2009

Inversion of Control Containers

Category: C# | Patternsfossmo @ 05:35

Inversion of Control Container is easily put a hash table. A hash table that has a bunch of interfaces versus concrete types. There are a lot of these containers on the web. Some of the most used ones is Windsor, Autofac, Structuremap, Ninject and Unity. I will use Unity later in this post. To try to explain the concept of a IOC container, I will create a very simple one. The two main reasons I use IOC containers is to create loosely coupled applications and it helps me unit test my applications in an easy way. The core concept of dependency inversion principle, which a IOC container is based on, is that high level modules should not depend on the low level ones, but they should both depend on abstractions. The abstraction in these cases are interfaces or abstract-based classes. I recommend that you read my previous blog post about dependency injection if you don't know what dependency inversion principle is.

Let's create the IOC container.

  1:     public class MyIocContainer
  2:     {
  3:         private static readonly IDictionary<Type, object> objDictornary = new Dictionary<Type, object>();
  4: 
  5:         public static T Resolve<T>()
  6:         {
  7:             return (T)objDictornary[typeof(T)];
  8:         }
  9: 
 10:         public static void Register<T>(object objToRegister)
 11:         {
 12:             objDictornary.Add(typeof(T), objToRegister);
 13:         }
 14:     }

In 14 lines of code we have a very simple IOC container. If you want to start using a IOC container, but you can't add a third party library to your project, this could be an easy way to get some of the benefits a IOC container can give you. But, you are of course missing out on a lot of the features a "real" IOC container can provide. Some of the valuable features this container don't contain is allowing different styles of configuration (XML or annotations), lifetime management and autowiring. I will look into autowiring in a later post.

In the first post about DI and IOC containers, I ended the post with doing a poor man's dependency injection (line 11 in the code example below). I think the technical term for this is constructor initialization. This is done if you only want to expose only one of the parameters to the user of your library.

  1:           public Butler(IWeapon weapon, ICommunicate communicate)
  2: 
  3:           {
  4: 
  5:               _weapon = weapon;
  6: 
  7:               _communicate = communicate;
  8: 
  9:           }
 10: 
 11:           public Butler(IWeapon weapon): this(weapon, new Communicate())
 12: 
 13:           {}

Poor man's dependency injection works great, but it will give me a tight coupling against the Communication class. How can we get rid of this tight coupling? We can do as the code example below shows. In stead of creating a object in the constructor initializer I input "objects" from MyiocContainer as parameters.

  1:         public Butler():this(MyIocContainer.Resolve<IWeapon>(), MyIocContainer.Resolve<ICommunicate>())
  2:         {}
  3: 
  4:         //public Butler(IWeapon weapon): this(weapon, new Communicate())
  5:         //{}

We need to create a interface for the communicate class, of course. This was done in the post about dependency injection, but I repeate it here for convinience.

  1:     public interface ICommunicate
  2:     {
  3:         void Speak(string phrase);
  4:     }

Now we have a interface for the communicate class. Let's see how we can use MyiocContainer in the program.

  1:        class Program
  2:        {
  3:            static void Main(string[] args)
  4:            {
  5:                MyIocContainer.Register<IWeapon>(new Poison());
  6:                MyIocContainer.Register<ICommunicate>(new Communicate());
  7:    
  8:               Butler butler = new Butler();
  9:               butler.Kill("The young man");
 10:               butler.Speak("Drink this if you dare, Sir!");
 11:               Console.ReadKey();
 12:           }
 13:       }

The output after running the code above, looks like this.

image

Cool. This is nice. I now have a application where the dependencies is mostly based on interfaces. I can insert a new communication class or a weapon class as long as they implement the interfaces ICommunication and IWeapon. But, now we have a coupling against the IOC container we created. I need to create a abstraction. Doing this I can choose another container later. If I want to use Unity, Structuremap or another IOC container, it won't be a problem.  Lets create the abstraction using the static gateway pattern.

  1:     public static class MyContainerAbstractor
  2:     {
  3:         private static IResolver _resolver;
  4:         public static T Resolve<T>()
  5:         {
  6:             return _resolver.Resolve<T>();
  7:         }
  8: 
  9:         public static void Init(IResolver resolver)
 10:         {
 11:             _resolver = resolver;
 12:         }
 13:     }
 14: 
 15:     public interface IResolver
 16:     {
 17:         T Resolve<T>();
 18:     }

In the Butler class's constructor I do these changes.

  1: public Butler():this(ContainerAbstractor.Resolve<IWeapon>(), ContainerAbstractor.Resolve<ICommunicate>())

Then I need to change MyiocContainer to implement the interface I created and remove the static keywords.

  1:     public class MyIocContainer:IResolver
  2:     {
  3:         private readonly IDictionary<Type, object> objDictonary = new Dictionary<Type, object>();
  4: 

  5:         public T Resolve<T>()
  6:         {
  7:             return (T)objDictonary[typeof(T)];
  8:         }
  9: 
 10:         public void Register<T>(T obj)
 11:         {
 12:             objDictonary.Add(typeof(T), obj);
 13:         }
 14:     }

The main method will look like this after we have done the changes.

  1:     class Program
  2:     {
  3:         static void Main(string[] args)
  4:         {
  5:             MyIocContainer container = new MyIocContainer();
  6:             container.Register<IWeapon>(new Poison());
  7: 
  8:             container.Register<ICommunicate>(new Communicate());
  9:             container.Register<IButler>(new Butler());
 10:             
 11:             ContainerAbstractor.Init(container);
 12: 
 13:             IButler butler = new Butler();
 14:             butler.Speak("Drink this if you dare, Sir!");
 15:             butler.Kill("The young man");
 16:             Console.ReadKey();
 17:         }
 18:     }

Now we are using a abstraction against the IOC container. It's easy to use an other container if we want to do that. Let's create a abstraction against Unity.

  1:     public class MyUnityContainer:IResolver
  2:     {
  3:         readonly IUnityContainer myContainer = new UnityContainer();
  4: 
  5:         public T Resolve<T>()
  6:         {
  7:             return myContainer.Resolve<T>();
  8:         }
  9: 
 10:         public void Register<T>(object obj)
 11:         {
 12:             myContainer.RegisterInstance<T>((T)obj);
 13:         }
 14:     }

To run the program with the Unity container we can just replace one line of code in the main method. Replace

  1: MyIocContainer container = new MyIocContainer();

with

  1: MyUnityContainer container = new MyUnityContainer();

and we will get the same output as before

image

That's it for now. I recommend you to look into IOC containers if you already haven't done so.
In the next post I will show how to create a very simple autowiring mechanism in my home made IOC container.

Tags: , , ,

Currently rated 5.0 by 2 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Dec 23 2008

Murder mysteries and Dependency Injection

Category: C# | Patternsfossmo @ 07:50

 

imageTo try to explain Dependency Injection and Inversion of Control Containers, I'm going to get inspiration from some old detective novels. When I say old, I think of novels like the ones Agatha Christie wrote. This first post will explain Dependency Injection, and the second one will explain Inversion of Control Containers. To start our story we need some characters.

Please welcome:
The Colonel - This is the old guy with the white mustache and monocle.
The young man - He is in love with the woman, and is always trying to show his interest for her.
The woman - She is a countess and have a very rich father (probably the reason the young man got into her in the first place).
The butler - He is always the killer, likewise in this story. 
The detective - Always traveling around running into mysteries to solve.

We should probably have at least ten characters more, but this will do for our examples. They are all invited to a big mansion to spend the weekend there. 

To get our story going, we need a weapon. Let's create one.

  1:     public class Gun
  2:     {
  3:         public void UseWeaponOn(string target)
  4:         {
  5:             Console.WriteLine(string.Format("{0} is shot dead!", target));
  6:         }
  7:     }

In most of the "Agatha Christie-like" detective novels, the butler is the villain. In this story he is the villain to. Let's create a butler so he can start committing crimes (read: killing ;-) ).

  1:     public class Butler
  2:     {
  3:         private Gun _gun;
  4: 
  5:         public Butler()
  6:         {
  7:             _gun = new Gun();
  8:         }
  9: 
 10:         public void Kill(string target)
 11:         {
 12:             _gun.UseWeaponOn(target);
 13:         }
 14:     }

The butlers first target is the colonel:

  1:     class Program
  2:     {
  3:         static void Main(string[] args)
  4:         {
  5:             Butler butler = new Butler();
  6:             butler.Kill("The Colonel");
  7:             Console.ReadKey();
  8:         }
  9:     }

This is what happens after the code is run:

image

The butler has killed his first victim. But, he has a problem. After killing the colonel, he have to find a new weapon for his next kill, because the detective is snooping around the mansion and he has found the murder weapon. This also gives us a problem. Since the gun is created inside the butler class's constructor, we have to modify the implementation of the class in order to make this change.

Coupling or dependency is the degree to which each program module (class) relies on each one of the other modules (classes). The butler class is tightly coupled to the gun class. When modules are tightly coupled, they cannot be replaced without altering their implementation. In order to avoid tightly coupled classes, we can use interfaces to provide a level of abstraction. Let's create an interface to represent a weapon.

  1:     public interface IWeapon
  2:     {
  3:         void UseWeaponOn(string target);   
  4:     }

Then we can implement the interface in the gun class.

  1:     public class Gun:IWeapon
  2:     {
  3:         public void UseWeaponOn(string target)
  4:         {
  5:             Console.WriteLine(string.Format("{0} is shot dead!", target));
  6:         }
  7:     }

And now we can change the butler class.

  1:     public class Butler
  2:     {
  3:         private IWeapon _weapon;
  4: 
  5:         public Butler()
  6:         {
  7:             _weapon = new Gun();
  8:         }
  9: 
 10:         public void Kill(string target)
 11:         {
 12:             _weapon.UseWeaponOn(target);
 13:         }
 14:     }

There is still a small problem with the coupling. The gun class is still created inside the butler class. How can we change this? Well, here is the solution:

  1:     public class Butler
  2:     {
  3:         private IWeapon _weapon;
  4: 
  5:         public Butler(IWeapon weapon)
  6:         {
  7:             _weapon = weapon;
  8:         }
  9: 
 10:         public void Kill(string target)
 11:         {
 12:             _weapon.UseWeaponOn(target);
 13:         }
 14:     }

We inject the weapon through the butler's constructor and create the gun object outside the butler class.

  1:     class Program
  2:     {
  3:         static void Main(string[] args)
  4:         {
  5:             IWeapon weapon = new Gun();
  6:             Butler butler = new Butler(weapon);
  7:             butler.Kill("The Colonel");
  8:             Console.ReadKey();
  9:         }
 10:     }

Now we have a butler class that is loose coupled to the gun class. It is now easy for us to create a new weapon when the butler starts killing people again. In every old detective novel there need to be a murder committed using poison. Arsenic, of course. We then need to create a new weapon class:

  1:     public class Poison:IWeapon
  2:     {
  3:         public void UseWeaponOn(string target)
  4:         {
  5:             Console.WriteLine(string.Format("{0} is killed by poisoning.", target));
  6:         }
  7:     }

To convince his victim to drink the poison, the butler needs to persuade the poor person to drink it. We need to create a communication class.

  1:     public class Communicate
  2:     {
  3:         public void Speak(string phrase)
  4:         {
  5:             Console.WriteLine(phrase);
  6:         }
  7:     }

To make this loose coupled, we create a interface for the communication class too.

  1:     public interface ICommunicate
  2:     {
  3:         void Speak(string phrase);
  4:     }

This means that we need to change the butler class to also inject the communication class.

  1:     public class Butler
  2:     {
  3:         private IWeapon _weapon;
  4:         private ICommunicate _communicate;
  5: 
  6:         public Butler(IWeapon weapon, ICommunicate communicate)
  7:         {
  8:             _weapon = weapon;
  9:             _communicate = communicate;
 10:         }
 11: 
 12:         public void Kill(string target)
 13:         {
 14:             _weapon.UseWeaponOn(target);
 15:         }
 16: 
 17:         public void Speak(string phrase)
 18:         {
 19:             _communicate.Speak(phrase);
 20:         }
 21:     }

The butler has found a new victim; the young man.

  1:     class Program
  2:     {
  3:         static void Main(string[] args)
  4:         {
  5:             IWeapon weapon = new Poison();
  6:             ICommunicate communicate = new Communicate();
  7:             Butler butler = new Butler(weapon, communicate);
  8:             butler.Speak("Please drink this, Sir!");
  9:             butler.Kill("The young man");
 10:             Console.ReadKey();
 11:         }
 12:     }

The output we get is this:

image 

After a few days the detective gathers all the people living, and working, in the mansion in the big living room. He then starts to explain who the killer is. The colonel was killed by a mistake. The real target was the young man.  It turns out that the butler is secretly in love with the woman, and wanted to get rid of all men interested in her. He killed the young man because he saw the woman get a bit intimate with him.

If the butler hadn't been stopped, he would continue to kill people that were interested in the woman. He would probably use a different weapon next time. A weapon that maybe didn't require him to speak. Instead of us creating a communication object and input a null value, we can do a Poor man's dependency injection. That means overloading the constructor this way:

  1:         public Butler(IWeapon weapon): this(weapon, new Communicate())
  2:         {}

Doing this, the communication object will be created automatically.

A nice quote that fit into this context is:

"It's OK to figure out murder mysteries, but you shouldn't need to figure out code. You should be able to read it."
- Steve McConnell (Code Complete)

In the next part I will try to explain what IoC containers are.

Tags:

Currently rated 5.0 by 5 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Dec 26 2007

Model View Presenter explained

Category: C# | Patterns | Scrum | Testingfossmo @ 18:36

I have used Model View Presenter (MVP) a lot the last months. It's a great pattern, but a lot of the people I talk to have problem understanding how it works, and how to use it. I will try to explain it simple in this blog post.

Passive View and Supervising controller
The creator of MVP, Martin Fowler, spilt the pattern into to new patterns. This was due to apparent confusions between Model View Controller and MVP. The new patterns is called Passive View and Supervising Controller. The main difference between this to patterns, is that Passive View puts all the view update behavior in the controller/presenter and Supervising Controller encourage the view to do most of the updating itself, and only brings in the presenter/controller when there's more complex logic involved. In my example application later in this blog post, I show Passive View.

When to use it
MVP is a great pattern to ease up unit testing the graphical user interface (GUI), and to decouple the GUI from the underlying model. MVP makes switching GUI a breeze.

Explained graphically
MVP is a pursuance of an other pattern called Model View Controller. In MVP, the view and the model don't know of each other, but in MVC the view knows of the model, and gets its updates from it.
I will cover MVC in a later post.

The figure below visually illustrates the pattern.

mvpgrap

More thoroughgoing, this is what happens:

1) The user executes a action. The action is forwarded to the presenter.
2) The presenter asks the database (model) for the data to view.
3) The model sends the data back to the presenter.
4) The presenter updates the view with the new data.

There are normally four main classes used in the MVP pattern. To be more specific,  three classes and a interface; the view, typical a WinForm, WebForm or XAML-file. The interface, witch describes the fields in the view. The presenter, witch executes the views actions and communicates with the model. And, of course,  the underlying model, e.g. a database.

Example application
I have created an application witch displays name, e-mail, state, etc. The application uses the MVP pattern. This is what the application does: You enter a name into the search text box and the program reads information from a textfile. Information about the user is displayed in the form. 

Application 
Shows the GUI in the application

Project
The solution consists of three projects. One view, one presenter and one model. If you wanted to have several forms, you would have to create more presenters and views. 

projectstructur
Shows the project structure

Interface
Let's look at the interface. It's found in the presenter project, and is named IPerson. It includes all the fields I want to display in the view.

interface

The last field in the interface is Message. You will find it in the lower part of Form1, displaying: "Data fetched.". If any error occurs in the application, it's shown there. The class Form1 (Form1.cs), implements the interface.

implemented interface   

Form1 implements all the properties in the interface. This is, as you know the startingpoint of the application. A instance of the presenter is created in the view. This way the presenter and view can communicate, and the presenter can update the GUI elements.

implementations
Shows some of the properties in Form1

When the search textbox is filled with a name, a event is triggered. It ends up in the method txtSearch_KeyUp in the class Form1:

keypressed

The presenters constructor, inputs the view and the class fetching data from the model, as parameters. Hence, the presenter has access to the view and the model. This way of doing things is called Dependency Injection.

presenter

In the method UpdateData (called from the view), data is fetched from the datasource, and the view is filled with the returning data. If a exception occurs the field message, in the view, displays the error message. If nothing happens, the field displays "Data fetched.".

ReadData

In the model (Data project), data is fetched from the file and put into a person object. Person object is returned to the presenter. If no data is found, an exception is thrown (witch is displayed in the message field in the GUI).

nodatafound

That is the course of events in the Model View Presenter pattern.
I recommend you to fire up Visual Studio and debug the sample application.

If you want to download the sourcecode for this example, you can find a link below.  

Tags: ,

Currently rated 5.0 by 5 people

  • Currently 5/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5