views:

428

answers:

2

Is there a way via xml configuration to denote a static factory method on an object?

A: 

Inversion of control/dependency injection and static do not mix well. Instead, do the following. Have an IFooFactory and a concrete implementation FooFactory:

public interface IFooFactory {
    Foo Create();
}

public class FooFactory : IFooFactory {
    public Foo Create() {
        Foo foo = // create Foo
        return foo;
    }
}

Then, register FooFactory as the concrete implementation of IFooFactory with ContainerControlledLifeTimeManager so that it acts like a singleton:

IUnityContainer container = new UnityContainer();
var manager = new ContainerControlledLifeTimeManager();
container.RegisterType<IFooFactory, FooFactory>(manager);

Then, when you need the factory:

IFooFactory factory = container.Resolve<IFooFactory>();
Foo foo = factory.Create();

If you can't alter the implementation of your factory so that it doesn't have static methods then you will need to create a wrapper:

public class FooFactoryWrapper {
    public Foo Create() {
        return FooFactoryTypeWithStaticCreateMethod.Create();
    }
}

and then register

container.Register<IFooFactory, FooFactoryWrapper>();

Of course, you can register FooFactory or FooFactoryWrapper as the concrete implementation of IFooFactory in XML too. Let me know if you need help with this.

The main point is get away from static.

That said, here's how you can register a static factory in Unity:

IUnityContainer container = new UnityContainer();
container.AddNewExtension<StaticFactoryExtension>()
         .Configure<IStaticFactoryConfiguration>()
         .RegisterFactory<IFoo>(container => FooFactory.Create());
var foo = container.Resolve<IFoo>(); // uses FooFactory

I can not figure out how to set this up using XML and after poking around using Reflector I do not think that it is possible. I can not find any classes in Microsoft.Practices.Unity.StaticFactory that could handle a configuration element. You probably have to add your own handler.

Jason
I agree with you on this but we are trying to take old code that uses Spring.NET and was implemented in this fashion. We are trying to minimally change the working code and replace the IOC. Only reason. WPF Project we are doing is currently slated to use Unity due to Prism and not wanting to write a new Bootstrapper.
cjibo
Okay, in that case I added how register a factory method in Unity. However, I can not figure out how to configure it via XML and I do not think that it is possible. You might have to create your own handler.
Jason
A: 

There is nothing out of the box. However, look here:

http://bitbucket.org/ctavares/unityfactoryconfig/overview

for an example of a config extension that lets you configure (limited) factories in XML in Unity 2.0.

Chris Tavares