views:

796

answers:

1

Howdy,

I am new to using Unity and IoC/DI concepts. I started with the concept by rolling my own via James Kovacs' show on dnrTV in a test.

His example had the Container run as a singleton accessed through a static method in an IoC class so you could register types at a startup and resolve the type throughout your application.

I know this was not full featured and was to mainly show the concepts of IoC.

I am now attempting to use Unity in a project.

In my Main() I create a new container, but once my WinForms opens, the container falls out of scope and is disposed. Later on in the program, when I try to resolve a type I no longer have the original container and its registered types.

Is there a concept or implementation construct I am missing?

My current thought is to create something like this:

public static class Container
{
    private static readonly object syncRoot = new object();
    private static volatile IUnityContainer instance;

    public static IUnityContainer Instance
    {
        get
        {
            if (instance == null)
            {
                lock (syncRoot)
                {
                    if (instance == null)
                    {
                        instance = new UnityContainer();
                    }
                }
            }
            return instance;
        }
    }
}

I'm pretty sure this will work, it just doesn't seem right.

Thank you,
Keith

+1  A: 

I use a static class for just that same reason - to avoid it going out of scope.

The one difference I make to you is that I wrap all the unity calls and add checks to see if unity is already configured, as you'll see here:

using System.Configuration;
using Microsoft.Practices.Unity;
using Microsoft.Practices.Unity.Configuration;

namespace Utilities
{
    public static class ServiceLocator
    {
     private static IUnityContainer container = new UnityContainer();
     private static bool isConfigured;

     public static void Clear()
     {
      container = new UnityContainer();
     }

     private static IUnityContainer Container
     {
      get
      {
       if (!isConfigured)
       {
        ConfigureContainer();
       }
       return container;
      }
     }

     public static T Resolve<T>()
     {
      return Container.Resolve<T>();
     }

     public static T Resolve<T>(string name)
     {
      return Container.Resolve<T>(name);
     }

     public static void AddInstance<T>(object instance)
     {
      Container.RegisterInstance(typeof (T), instance);
     }

     private static void ConfigureContainer()
     {
       UnityConfigurationSection section = (UnityConfigurationSection) ConfigurationManager.GetSection("unity");
       section.Containers.Default.Configure(container);
       isConfigured = true;  
     }
    }
}
Richard Banks
Thank you, I am not configuring my container in the Static Class. I think this gives me flexibility to change the configuration in a Testing situation without having the "production" configuration automatically injected when it is used in a test.
Keith Sirmons
Fair enough. Of course, with unit testing you shouldn't really require the container anyway.I understand the need in an integration test scenario however.
Richard Banks