Autofac Generic Service resolution at runtime - c#

Recently, Castle added support for interface factories with implementations provided by the kernel. I am wondering if there is a way to do this in autofac also. I have read about the delegate factories, but I think I might be missing something, and am unable to get it to work. Here is what I am thinking:
class Message { }
interface IHandle<T> {
void Handle(T message);
}
class Handle<Message> : IHandle<Message> {
...
}
class Bus {
.ctor (? lookup) {
_lookup = lookup;
}
void Send<T>(T message) {
_lookup.GetHandler<T>().Handle(message);
}
}
var builder = new ContainerBuilder();
builder.RegisterType<Handle<Message>>().As<IHandle<Message>>();
builder.RegisterType<Bus>();
var container = builder.Build();
container.Resolve<Bus>().Send<Message>(new Message());
What I'm trying to do is keep the container out of the bus (as I agree that service locator is an anti-pattern) or any other implementation. This problem is easy if I just feed the container to the bus, or create some class factory that wraps the container. Just trying to make sure there isn't a way to do this already.
Btw, the castle way iirc allows me to register something like this:
interface IHandlerFactory {
IHandle<T> GetHandler<T>();
}
container.Register<IHandlerFactory>().AsFactory();
Thanks,
Nick

You could isolate that coupling by creating a concrete IHandlerFactory, say AutofacHandlerFactory, which would receive the ILifetimeScope. That coupling seems inevitable since the container is the only one who can resolve the proper IHandler<T>.
Coupling with ILifetimeScope might be a bad idea, but then, the coupling is isolated inside the concrete IHandlerFactory, and the Bus just uses it through an interface. Let's say you change the container and starts using Ninject, you could just implement a NinjectHandlerFactory to do the job.

Seems like the answer is 'No'.
I've tried to use AggregateService which is supposed to do what you want, but it crashes during factory resolution with message 'The type "Castle.Proxies.IComponentFactoryProxy" from assembly "DynamicProxyGenAssembly2, Version=0.0.0.0, Culture=neutral, PublicKeyToken=null" has tried to implement an unaccessible interface.' (The original message is in Russian, I've translated it).
I can't figure out another approach that would work without a manual (yet quite simple) implementation. Maybe you should write to Nicholas Blumhardt.
In fact, I'd better do it this way:
public class Bus {
readonly ILifetimeScope _OwnScope;
// Autofac always provides ILifetimeScope that owns a component as a service to the component
// so it can be used as a dependency
public Bus(ILifetimeScope ownScope) {
_OwnScope = ownScope;
}
void Send<T>(T message) {
_OwnScope.Resolve<IHandler<T>>.Handle(message);
}
}
You will probably argue that coupling with ILifetimeScope is a bad idea. Well, it's quite a simple interface which might be wrapped into your own implementation. Or you may factor the code out into a simple factory class. Well, it seems like you know how to do this without my suggestions.

Related

How to instantiate outside of a constructor?

How to replicate this code with Autofac syntax?
public static class MenuConfig
{
public static void Initialize()
{
var _menuService = DependecyFactory.GetInstance<IMenuService>();
Parameters.Menu = _menuService.Menu();
}
}
Before calling this a "duplicate question" please note that I'm looking for an Autofac command. I CANNOT inject the interface anywhere and then call "Resolve". What I need to is perform an "InstancePerRequest" inline and uninjected so I don't have to do this:
var _service = new Service(new Dependency(new context()));
LightInject has a method that allows instantiation from an interface OUTSIDE of a constructor like this:
var _service = DependecyFactory.GetInstance<IService>();
What is the equivalent method for Autofac?
When calling containerBuilder.Build() you get back a container which implements IContainer and ILifetimeScope, whenever you get hold of one of these interfaces, you can resolve types from it:
container.Resolve<IService>();
If you want this container to be static, you could add the container as a static property to the Program or Startup class (depending if you're creating a Console or ASP.NET application).
Remember that the root container will be around for the entire duration of your application, so this can result in unwanted memory leaks when used incorrectly. Also see the warning in the documentation.
Still, it's perfectly possible to do the memory management yourself by resolving an Owned<> version from your interface:
using (var service = Program.Container.Resolve<Owned<IService>>())
{
service.Value.UseService();
}
Anyway, since you mention a static class in the comments, the best solution is to change that into a non-static class and register it as a singleton with Autofac. Then you can inject a Func<Owned<IService>> serviceFactory into that singleton and create/dispose an instance of the service wherever you need it.
using (var service = serviceFactory())
{
service.Value.UseService();
}
This is simply not possible with Autofac. All other solutions involving Autofac will require code refactoring which may potentially break software functionality. So unfortunately, the most elegant and least disruptive solution is this:
var _service = new Service(new Dependency(new context()));
Since this is an edge case addressing only one part of the software, this compromise is acceptable. It would be nice, however, if Autofac implemented this functionality in some future release.

Can't inject a delegate using ASP.NET Core DI

Say I've a MVC Core Controller like this:
public class SomeController
{
public SomeController(IConfiguration appConfig, Func<string> someDelegate)
{
}
}
Also, I'm using AutoFac to resolve injections. Object injections are working flawlessly while adding a delegate injection produces an ASP.NET Core exception which tells that Func<string> can't be injected because there's no component to inject with such type.
When I try to manually resolve SomeController using AutoFac I get the desired behavior.
Is there any way to support this scenario without using AutoFac to resolve controllers?
Controllers are not resolved via DI by default, they are constructed in the DefaultControllerFactory or so.
Update
Microsoft.Extensions.DependencyInjection doesn't support named components, discovery, auto registrations, decorators etc.
It's meant to be simple out of the box IoC and provide the base for DI for basic applications and offer easy way for 3rd party IoC containers (with advanced features such as auto discovery, decorators etc.) to be integrated (basically all they need is process the information in IServiceCollection and return their own implementation of IServiceProvider from Configure method).
Tag helpers, controllers and view components are different in this aspect as they have their own activators (the default one use activation utilities, which at some point further down the pipeline use the service provider). For that reasons AddControllersAsServices exists, because it replaces DefaultControllerActivator (which uses ActivationUtilities, see DefaultControllerActivator.cs) with ServiceBasedActivator (which uses IServiceProvider, see ServiceBasedControllerActivator).
Also see this related answer for details on how to resolve controllers, tag helpers and view components via DI.
var builder = services
.AddMvc()
.AddControllersAsServices() // this one for your case
.AddViewComponentsAsServices()
.AddTagHelpersAsServices();
I was just run into this issue myself so I thought I would share for future reference as I had one case where I wanted to resolve a delegate but including an additional library seemed like overkill.
Given the following defintions:
public interface ISomething { /*...*/ };
public interface ISomeService { /*...*/ }
public class SomeService : ISomeService { /*...*/ }
public class Something
{
public Something(ISomeService service, string key) { /*...*/ }
}
// I prefer using a delegate for readability but you
// don't have to use one
public delegate ISomething CreateSomething(string key);
The delegate can be registered like this:
var builder = services
.AddSingleton<ISomeService, SomeService>()
.AddTrasient<CreateSomething>(provider => key => new Something(provider.GetRequiredService<ISomeService>(), key));

Autofac multithreading issues

I'm trying to use autofac DI in my application. I created a wrapper class to abstract away all the autofac dlls:
FrameworkDependencyResolver : Logger, IFrameworkDependencyResolver
In this class I hold the container builder, and register all my dependencies in the application root. After registering my types I build it and hold the container:
Icontainer _container;
ContainerBuilder _builder
public FrameworkDependencyResolver()
{
_builder = new ContainerBuilder();
}
Deep in my application i want to use the FrameworkDependencyResolver object to resolve protocols and open connections to external applications, therefore I registered this object as IFrameworkDependencyResolver with the following code:
_builder.RegisterInstance(obj).As<T>();
Obj is thr FrameworkDependencyResolver, T is the interface
In my starter thread, I resolve object that takes the FrameworkDependencyResolver in his ctor, and it works perfectly, resolvings are fine, however when I resolve an inner layer(on new thread) that takes the FrameworkDependencyResolver in it's ctor and try to resolve a registered protocol object I face deadlock.
Exmaple:
main:
var rootResolver = new FrameworkDependencyResolver();
rootResolver.RegisterType<IClass3, Class3>(Lifecycles.Singleton);
rootResolver.RegisterType<IClass2, Class2>(Lifecycles.Singleton);
rootResolver.RegisterType<Container, TestContainer>(Lifecycles.Singleton);
rootResolver.RegisterObject<IFrameworkDependencyResolver, FrameworkDependencyResolver>(rootResolver);
rootResolver.BuildContainer();
rootResolver.Resolve<TestContainer>();
Console.ReadKey();
TestContainer code:
public TestContainer(IFrameworkDependencyResolver resolver) : base(resolver){}
protected override void InitializeContainer()
{
_class2 = DependencyResolver.Resolve<IClass2>();
Thread.Sleep(20000);
Console.WriteLine("Container initialize finished");
}
Class2 code:
public class2(IFrameworkDependencyResolver resolver)
{
_resolver = resolver;
var thread = new Thread(startMethod);
thread.Start();
Console.WriteLine("Class2 ctor ended");
}
void StartMethod()
{
_class3 = _resolver.Resolve<IClass3>();
Console.WriteLine("Start method finished");
}
The output of this simple example program is:
Class2 ctor ended
Container initialize ended
Start method finished
Meaning that the thread I created is waiting for the main thread to finish and only than it can resolve. I want to prevent this and make it possible to resolve anytime from every thread. Please help me understand what is causing this.
Thank you
Edit:
The problem is not solved because autofac resolves singletons from the root scope..I believe my problem is similar to the one described here : Autofac resolving a singleton creates a bottleneck
but I don't really understand the solution
Edit 2:
for the bottleneck issue I learned that ctors should not contain logic at all.
I also learned I probably shouldn't pass around my IFrameworkDependencyResolver object and should probably use Func<>.
My application structure:
I have a layer in my application that handles connection requests and for every kind of request creates a different kind of protocol (a different protocol object)
// For example lets say a protocol takes in ctor these 3 services + runtime configuration object:
public Protocol1(IFramingAgent, IFramingAlgorithm, IFramingParser, configObject configuration)
Each service is registered with key because each protocol uses a different one
And here is my terrible class:
public class ProtocolsLayer : Layer
{
private IFrameworkDependencyResolver _resolver;
private IConfigurationService _configService;
public ProtocolsLayer(IFrameworkDependencyResolver resolver, IConfigurationService configurationService)
{
_resolver = resolver;
_configService = configurationService;
}
void HandleConnection1()
{
// What I have at the moment (terrible):
// Resolve the fitting services (All keyed - key is received by the type, Resolve and ResolveWithParameters used here are my wrappers)
var agent = _resolver.Resolve<IFramingAgent>(typeof(Protocol1FramingAgent));
var algo = _resolver.Resolve<IFramingAlgorithm>(typeof(Protocol1FramingAlgorith));
var parser = _resolver.Resolve<IFramingParser>(typeof(Protocol1FramingParser));
// A parameter I get and pass to each protocol at runtime
var protocolConfig = _configService.GetConfig<Protocol1Configuration>();
// Finally resolve the protocol with it's parameters:
protocol = _resolver.ResolveWithParameters<IProtocol>(typeof(Protocol1), new List<object>{
agent, resolver, parser, protocolConfig
});
//...
// Theres gotta be a better way!!
}
void HandleConntection2()
{
// Same as in protocol1
}
void HandleConnection3()
{
// Same as in protocol1
}
}
Take in mind that I don't want references to autofac, meaning I can't use IIndex<> which I heard off.
Thanks!
I made a sample to reproduce your issue : https://dotnetfiddle.net/WOGwoD
If I summarize, your issue is that Autofac Resolve for only thread at a time.
Let take another code sample to reproduce the issue :
class Foo1
{
public Foo1()
{
Console.WriteLine("begin Foo1");
Thread.Sleep(1000);
Console.WriteLine("end Foo1");
}
}
class Foo2
{
public Foo2()
{
Console.WriteLine("begin Foo2");
Thread.Sleep(1000);
Console.WriteLine("end Foo2");
}
}
public class Program
{
public static void Main(string[] args)
{
ContainerBuilder builder = new ContainerBuilder();
builder.RegisterType<Foo1>().AsSelf().SingleInstance();
builder.RegisterType<Foo2>().AsSelf().SingleInstance();
IContainer container = builder.Build();
var t1 = Task.Run(() => container.Resolve<Foo1>());
var t2 = Task.Run(() => container.Resolve<Foo2>());
Task.WaitAll(t1, t2);
}
}
The output of this program is the following :
begin Foo1
end Foo1
begin Foo2
end Foo2
If you change the lifetime scope from SingleInstance to InstancePerDependency (the default one) for a single registration, the output will be :
begin Foo1
begin Foo2
end Foo1
end Foo2
We can see that Autofac lock the IContainer for Shared registration while it is activating a Shared registration.
The lock statement is Line 258 of LifetimeScope.cs.
I think this behavior is here to prevent issue with complex dependency graph. ie : What happens if Foo1 has a nested dependency on Foo2 ?
You won't be able to bypass this behavior of Autofac.
To change this behavior, you will need to change the way your code works. A constructor is not intended to take time. I recommend you to change your constructor to do only required things, if some of initialization process takes time I would defer it or refactor the code to ensure that constructor takes only few milliseconds to complete.
I created a wrapper class to abstract away all the autofac dlls
Your core code should not rely on dependency injection component. In your case, it looks like you use the IFrameworkDependencyResolver interface to lazy load component or to have a factory component. You should rely on Lazy<T> of Func<T> instead. See implicit relation type for more information.
I follow the same strategy in my application to wrap DI library with my classes to have ability to change it later on if I need to.
I followed the same approach, with only one difference
in your code you create ContainerBuilder in your class constructor and keep reference to it, this is the problem
instead, you may need remove away the ContainerBuilder instance, and just depend on Autofac.ILifetimeScope as constructor dependency for your FrameworkDependencyResolver, this dependency will be just injected by autofac runtime with correct lifetime scope.
then at any level on your code, you can just depend on FrameworkDependencyResolver as you need
EDIT
after i saw your update, i would recommend that you separate registration of your service from resolving instances, i.e make new class like FrameworkDependencyRegister and keep the other one for resolving and follow the steps answer above
in my opinion abstracting registration might be too much unneeded abstraction, you can just write one method to do this stuff using normal autofac APIs

Best approach for breaking dependencies in C#?

We are looking at adding unit tests to our C# code base. I am finding it easy to add unit tests to simple classes, but classes that interact with other dependencies are more difficult. I have been looking at mocking frameworks, but was wondering about the best approach to write classes in the first place to break external dependencies, like file system, database and messaging system dependencies.
To give an example, a routine listens on a socket for a message in a certain format - say MessageA. This is decoded, some calculations are done, this is re-encoded into a different binary format and the resulting message then sent, MessageB.
My current testing approach is as follows. I extract an interface for all socket interactions, and create a mock interface. I set the interface in a singleton. Then run the class against hard coded inputs. The class under test will use the interface in the singleton to send/receive.
I do a similar thing to test database interactions.
This does not seem like the most flexible approach, how would you go about improving this to make it easier to test? If a mocking framework is the answer, how would I design the classes?
Example code :
[SetUp]
public void init()
{
// set message interface in singleton as mock interface
CommAdapter.Instance.MessageAdapter = new MockMessage();
// build reference message from hard coded test variables
initialiseMessageA();
// set input from mock message socket
((MockMessage) CommAdapter.Instance.MessageAdapter).MessageIn = m_messageA;
}
[Test]
public void test_listenMessage_validOutput()
{
// initialise test class
MessageSocket tS = new MessageSocket();
// read from socket
tS.listenMessage();
// extract mock interface from singleton
MockMessage mm = ((MockMessage) CommAdapter.Instance.MessageAdapter);
// assert sent message is in correct / correstpoinding format
Assert.AreEqual(1000001, mm.SentMessageB.TestField);
}
Instead of using Singletons to set your component implementations, use a Dependency Injection, and a DI library like Ninject. This is exactly the type of scenario they were designed for.
Not pushing you to Ninject specifically, but they have a good tutorial :) The concepts will transfer to other frameworks (like Unity).
https://github.com/ninject/ninject/wiki
With DI alone, the code will look something like this:
class Samurai {
private IWeapon _weapon;
public Samurai(IWeapon weapon) {
_weapon = weapon;
}
public void Attack(string target) {
_weapon.Hit(target);
}
}
class Shuriken : IWeapon {
public void Hit(string target) {
Console.WriteLine("Pierced {0}'s armor", target);
}
}
class Program {
public static void Main() {
Samurai warrior1 = new Samurai(new Shuriken());
Samurai warrior2 = new Samurai(new Sword());
warrior1.Attack("the evildoers");
warrior2.Attack("the evildoers");
}
}
This looks clean now, but wait until your dependencies have dependencies, or further :) You can use a DI library to solve that, though.
With a library to handle the wiring up for you, it will look something like:
class Program {
public static void Main() {
using(IKernel kernel = new StandardKernel(new WeaponsModule()))
{
var samurai = kernel.Get<Samurai>();
warrior1.Attack("the evildoers");
}
}
}
// Todo: Duplicate class definitions from above...
public class WarriorModule : NinjectModule {
public override void Load() {
Bind<IWeapon>().To<Sword>();
Bind<Samurai>().ToSelf().InSingletonScope();
}
}
With either of these approaches, plus a mock object framework like Moq, your unit tests look something like this:
[Test]
public void HitShouldBeCalledByAttack()
{
// Arrange all our data for testing
const string target = "the evildoers";
var mock = new Mock<IWeapon>();
mock.Setup(w => w.Hit(target))
.AtMostOnce();
IWeapon mockWeapon = mock.Object;
var warrior1 = new Samurai(mockWeapon);
// Act on our code under test
warrior1.Attack(target);
// Assert Hit was called
mock.Verify(w => w.Hit(target));
}
You'll notice you can just pass mock instances straight into the code under test, and you don't have to mess around with setting singletons. This will help you avoid problems like needing to set up the state multiple times, or in between calls. It means no hidden dependencies.
You'll also notice I didn't use the DI container in the tests. If your code is well factored, it will only be testing a single class (and as often as possible, only a single method), and you will only need to mock out the direct dependencies of that class.
In addition to a DI container (I'm using MS Unity 2.0 currently but there are many to choose from) you will need a good mocking framework, my preference is MOQ. A common pattern/process for breaking concrete dependencies is:
define the dependency via an interface; you may luck out and already have an interface, like IDbConnection or you may need to use Proxy to wrap a concrete type and define your own interface.
resolve the concrete implementation via your DI container
inject your mock implementations into your DI container at test setup time (inject real impls. at system startup)

how to implement IOC without a global static service (non-service locator solution)?

we want to use Unity for IOC.
All i've seen is the implementation that there is one global static service (let's call it the the IOCService) which holds a reference to the Unity container, which registers all interface/class combinations and every class asks that object: give me an implementation for Ithis or IThat.
Frequently i see a response that this pattern is not good because it leads to a dependency from ALL classes to the IOCService (not to the Unity container because it is only known inside the IOCService).
But what i don't see often, is: what is the alternative way?
Michel
EDIT: found out that the global static service is called the service locator, added that to the title.
The alternative is to have a single instance of your container at the highest application level only, then use that container to resolve every object instance you need to create in that layer.
For example, the main method of most executables just looks like this (minus exception handling):
private static void main(string[] args) {
Container container = new Container();
// Configure the container - by hand or via file
IProgramLogic logic = container.Resolve<IProgramLogic>();
logic.Run();
}
Your program (represented here by the IProgramLogic instance) doesn't have to know anything about your container, because container.Resolve will create all its dependencies - and its dependencies' dependencies, on down to leaf classes with no dependencies of their own.
ASP.NET is a harder case, because web forms doesn't support constructor injection. I typically use Model-View-Presenter in my web forms applications, so my Page classes really only have one dependency each - on their presenter. I don't unit test them (everything interesting and testable is in my presenters, which I do test), and I don't ever substitute presenters. So I don't fight the framework - I just expose a container property on my HttpApplication class (in global.asax.cs) and use it directly from my Page files:
protected void Page_Load(object sender, EventArgs args) {
ICustomerPresenter presenter = Global.Container.Resolve<ICustomerPresenter>();
presenter.Load();
}
That's service locator of course - though the Page classes are the only thing coupled to the locator: your presenter and all of its dependencies are still fully decoupled from your IoC container implementation.
If you have a lot of dependencies in your Page files (that is, if you do not use Model-View-Presenter), or if it's important to you to decouple your Page classes from your Global application class, you should try to find a framework that integrates into the web forms request pipeline and use property injection (as suggested by Nicholas in the comments below) - or write your own IHttpModule and perform the property injection yourself.
+1 for knowing that Service Locator is a Bad Thing.
Problem is - Unity is not very sophisticated so I don't know how easy/hard is it to do IoC the right way with it.
I wrote few blogposts recently that you might find useful.
How I use IoC Containers
Pulling from the container
Instead of using the container explicitly, use it implicitly by leveraging constructor / property injection instead. Create a core class (or set of core classes) that depend on all the major pieces of your application.
Most containers will let you put ISomething[] in your constructor and it will inject all instances of ISomething into your class.
This way, when you bootstrap your application:
Instantiate your container
Register all your goodies
Resolve the core classes (this will pull in all the other dependencies you need)
Run the "main" part of the application
Now, depending on the type of application you are writing, there are different strategies for avoiding marking the IoC container as "static".
For ASP.NET web applications, you'll probably end up storing the container in the Application State. For ASP.NET MVC applications, you need to change out the Controller Factory.
For desktop applications, things get more complicated. Caliburn uses an interesting solution to this problem using the IResult construct (this is for WPF applications but could be adapted for Windows Forms as well.
In theory, to not have to worry about having a static IoC instance, you need to follow the Fight Club Rule - i.e. not to talk about the fight club - i.e. not to mention the IoC container.
This means that your components should largely be unaware about the IoC container. It should only be used at the topmost level when registering components. If a class needs to resolve something, it should really be injected as a dependency.
The trivial case is easy enough. If PaymentService depends on IAccount, the latter should be injected by IoC:
interface IAccount {
Deposit(int amount);
}
interface CreditCardAccount : IAccount {
void Deposit(int amount) {/*implementation*/}
int CheckBalance() {/*implementation*/}
}
class PaymentService {
IAccount account;
public PaymentService (IAccount account) {
this.account = account;
}
public void ProcessPayment() {
account.Deposit(5);
}
}
//Registration looks something like this
container.RegisterType<IAccount, CreditCardAccount>();
container.RegisterType<PaymentService>();
The not so trivial case is where you want to inject multiple registrations. This especialy applies when you are doing any sort of Converntion Over Configuration and creating an object from a name.
For our payment example, say you want to enumerate through all accounts and check their balances:
class PaymentService {
IEnumerable<IAccount> accounts;
public PaymentService (IEnumerable<IAccount> accounts) {
this.accounts = accounts;
}
public void ProcessPayment() {
foreach(var account in accounts) {
account.Chackbalance();
}
}
}
Unity has the ability to register multiple interface to class mappings (they have to have different names thought). It does not, however, automatically inject those into classes that take collections of those registered interfaces. So, the above example will throw a resolution failed exception at runtime.
If you don't care that those objects live forever, you can register PaymentService in a more static fashion:
container.RegisterType<PaymentService>(new InjectionConstructor(container.ResolveAll<IAccount>()));
The above code will register PaymentService and will use a collection of IAccount instances that is resolved at registration time.
Alternatively, you can pass an instance of the container itself as a dependency and let PaymentService perform resolution of accounts. This is not quite following the Fight Club Rule, but is slightly less smelly than static Service Locator.
class PaymentService {
IEnumerable<IAccount> accounts;
public PaymentService (IUnityContainer container) {
this.accounts = container.ResolveAll<IAccount>();
}
public void ProcessPayment() {
foreach(var account in accounts) {
account.Chackbalance();
}
}
}
//Registration is pretty clean in this case
container.RegisterType<IAccount, CreditCardAccount>();
container.RegisterType<PaymentService>();
container.RegisterInstance<IUnityContainer>(container);
If your concern is having a dependency on Unity throughout your application, you can combine the service locator with a facade to hide the IOC implementation. In this way, you do not create a dependency on Unity in your application, only on having something that can resolve types for you.
For example:
public interface IContainer
{
void Register<TAbstraction,TImplementation>();
void RegisterThis<T>(T instance);
T Get<T>();
}
public static class Container
{
static readonly IContainer container;
public static InitializeWith(IContainer containerImplementation)
{
container = containerImplementation;
}
public static void Register<TAbstraction, TImplementation>()
{
container.Register<TAbstraction, TImplementation>();
}
public static void RegisterThis<T>(T instance)
{
container.RegisterThis<T>(instance);
}
public static T Get<T>()
{
return container.Get<T>();
}
}
Now all you need is an IContainer implementation for your IOC container of choice.
public class UnityContainerImplementation : IContainer
{
IUnityContainer container;
public UnityContainerImplementation(IUnityContainer container)
{
this.container = container;
}
public void Register<TAbstraction, TImplementation>()
{
container.Register<TAbstraction, TImplementation>();
}
public void RegisterThis<T>(T instance)
{
container.RegisterInstance<T>(instance);
}
public T Get<T>()
{
return container.Resolve<T>();
}
}
Now you have a service locator that is a facade for IOC services, and can configure your service locator to use Unity or any other IOC container. The rest of the application has no dependency on the IOC implementation.
To configure your service locator:
IUnityContainer unityContainer = new UnityContainer();
UnityContainerImplementation containerImpl = new UnityContainerImplementation(unityContainer);
Container.InitializeWith(containerImpl);
For testing, you can create a stub of IContainer that returns whatever you want, and initialize Container with that.

Categories