Injecting a list of dependencies with multiple interfaces in autofac - c#

I have this class where I'm trying to inject a list of qualifying objects:
public class BlingDispatcher : IBlingDispatcher
{
readonly IEnumerable<IDomainEventHandler> _domainEventHandlers;
#region IBlingDispatcher Members
public BlingDispatcher(IEnumerable<IDomainEventHandler> domainEventHandlers)
{
_domainEventHandlers = domainEventHandlers;
}
}
Classes like this get injected here and work great:
public class NotifyFrontEndSomethingHappened : IDomainEventHandler<SomethingHappened>
{
private readonly IFrontEndNotifier _frontEndNotifier;
public NotifyFrontEndAfterSomethingHappened(IFrontEndNotifier frontEndNotifier)
{
_frontEndNotifier = frontEndNotifier;
}
}
Classes like this do not:
public class NotifyFrontEndAfterEvent : IDomainEventHandler<SomethingHappened>,
IDomainEventHandler<SomethingElseHappened>,
IDomainEventHandler<MoreThingsHappened>,
IDomainEventHandler<AndYetMoreThings>
{
readonly IFrontEndNotifier _frontEndNotifier;
public void Handle(SomethingHappened #event)
{
_frontEndNotifier.Notify(#event, #event.CommanderId);
}
...
}
How can I get classes with multiple interfaces to be injected by autofac as well?
EDIT
More information:
public interface IDomainEventHandler
{
}
public interface IDomainEventHandler<in T> : IBlingHandler<T>, IDomainEventHandler
{
}
public interface IBlingHandler<in T>
{
void Handle(T #event);
}
Registering like this in bootstapper:
container.RegisterAssemblyTypes(AppDomain.CurrentDomain.GetAssemblies())
.Where(x => x.GetInterfaces().Any(i => i.Name.StartsWith("IBlingHandler")))
.AsImplementedInterfaces();

Related

Dependency Injection with factory method .net

I have a structure like below. I need ideas on how to clearly record all instances. Do you think Microsoft.Extensions.DependencyInjection library is suitable for these?
public interface IRules
{
void Do();
}
Implementation :
public class MyRules:IRules
{
public void Do()
{
//Something;
}
}
Businnes Interface:
public interface IRulesOperation
{
void Do();
}
Businnes class:
public class RulesOperation:IRulesOperation
{
private readonly IRules rules;
private readonly IConfiguration conf;
public RulesOperation(IRules rules,IConfiguration conf)
{
this.conf=conf;
this.rules = rules;
}
public void Do()
{
rules.Do();
}
}
Main Class:
public class App
{
IRulesOperation rules;
public App(IRulesOperation rules)
{
this.rules=rules;
}
}

Injecting dependency into base class

I have the following BaseClass:
public class BaseRepositorio : IDisposable
{
protected IDbConnection postgresql;
public BaseRepositorio(IDbConnection postgresql)
{
this.postgresql = postgresql;
}
public void Dispose()
{
}
}
What is the proper way to inject the dependency into the BaseClass?
public class RepositorioEmpresa : BaseRepositorio?!?!, IRepositorio<Empresa>
{
}
Inject it in the derived and use base constructor
public class RepositorioEmpresa : BaseRepositorio, IRepositorio<Empresa>
{
public RepositorioEmpresa(IDbConnection connection): base(connection)
{
}
}

How implement Strategy/Facade Pattern using Unity Dependecy Injection Web API

How tell to Unity.WebApi dependency injection framework, inject the correct class in the correct controller?
DI Project Container
public class UnityContainerConfig
{
private static IUnityContainer _unityContainer = null;
public static IUnityContainer Initialize()
{
if (_unityContainer == null)
{
_unityContainer = new Microsoft.Practices.Unity.UnityContainer()
.RegisterType<IMyInterface, MyClass1>("MyClass1")
.RegisterType<IMyInterface, MyClass2>("MyClass2")
}
}
-MVC PROJECT-
public static class UnityConfig
{
public static void RegisterComponents()
{
GlobalConfiguration.Configuration.DependencyResolver = new UnityDependencyResolver(DependencyInjection.UnityContainer.UnityContainerConfig.Initialize());
}
}
Controller 1:
private IMyInterface _myInterface
///MyClass1
public XController(
IMyInterface myInterface
)
{
_myInterface = myInterface
}
Controller 2:
private IMyInterface _myInterface
///MyClass2
public YController(
IMyInterface myInterface
)
{
_myInterface = myInterface
}
Rather than using a strategy or facade to solve this, a better solution would be to redesign your interfaces to be unique per controller. Once you have a unique interface type, your DI container will automatically inject the right service into each controller.
Option 1
Use a generic interface.
public interface IMyInterface<T>
{
}
public class XController
{
private readonly IMyInterface<XClass> myInterface;
public XController(IMyInterface<XClass> myInterface)
{
this.myInterface = myInterface;
}
}
public class YController
{
private readonly IMyInterface<YClass> myInterface;
public YController(IMyInterface<YClass> myInterface)
{
this.myInterface = myInterface;
}
}
Option 2
Use interface inheritance.
public interface IMyInterface
{
}
public interface IXMyInterface : IMyInterface
{
}
public interface IYMyInterface : IMyInterface
{
}
public class XController
{
private readonly IXMyInterface myInterface;
public XController(IXMyInterface myInterface)
{
this.myInterface = myInterface;
}
}
public class YController
{
private readonly IYMyInterface myInterface;
public YController(IYMyInterface myInterface)
{
this.myInterface = myInterface;
}
}

Resolving IEnumerable of generic interfaces from Autofac container

I'm not sure if this is possible, I've seen some other posts asking similar question but none have a satisfactory answer.
What I want to do is resolve a collection of interfaces with differing generic types from Autofac. So constructor of class would look something like this:
public class SomeClass<T> where T : class
{
private readonly IEnumerable<ITestInterface<T>> _testInterfaces;
public SomeClass(IEnumerable<ITestInterface<T>> testInterfaces)
{
_testInterfaces = testInterfaces;
}
}
Ideally, I'd just like to be able to register each instance individually like so:
builder
.RegisterType<ImplementationA>()
.As<ITestInterface<A>>();
builder
.RegisterType<ImplementationB>()
.As<ITestInterface<B>>();
I've tried various combinations of RegisterGeneric etc but the Enumerable just keeps coming through empty.
Any help would be appreciated.
I was able to resolve this after playing with inheritance & generic constraints. The solution I ended up with looks like this:
Base classes / interfaces:
public abstract class BaseClass
{
public abstract string IAM { get; }
}
public interface ITestInterface<out T> where T : BaseClass
{
T GetSomething();
}
Implemented classes:
public class A : BaseClass
{
public override string IAM => "I AM TYPE A";
}
public class AInterface : ITestInterface<A>
{
public A GetSomething()
{
return new A();
}
}
public class B : BaseClass
{
public override string IAM => "I AM TYPE B";
}
public class BInterface : ITestInterface<B>
{
public B GetSomething()
{
return new B();
}
}
Class we want to resolve:
public interface ISomeClass
{
void DoSomething();
}
public class SomeClass<T> : ISomeClass where T : BaseClass
{
private readonly IEnumerable<ITestInterface<T>> _testInterfaces;
public SomeClass(IEnumerable<ITestInterface<T>> testInterfaces)
{
_testInterfaces = testInterfaces;
}
public void DoSomething()
{
foreach (var t in _testInterfaces)
{
var something = t.GetSomething();
Console.WriteLine(something.IAM);
}
}
}
And finally, Autofac configuration:
var builder = new ContainerBuilder();
builder
.RegisterType<SomeClass<BaseClass>>()
.AsSelf();
builder
.RegisterType<AInterface>()
.As<ITestInterface<BaseClass>>();
builder
.RegisterType<BInterface>()
.As<ITestInterface<BaseClass>>();
builder
.RegisterType<SomeClass<BaseClass>>()
.As<ISomeClass>();
var container = builder.Build();
var x = container.Resolve<ISomeClass>();
x.DoSomething();
Outputs:
I AM TYPE A
I AM TYPE B
Hope this helps someone in the future.
RegisterGeneric should work fine :
builder.RegisterType<TestImplementationA>()
.As<ITestInterface<A>>();
builder.RegisterType<TestImplementationB>()
.As<ITestInterface<B>>();
builder.RegisterGeneric(typeof(SomeClass<>))
.As(typeof(ISomeClass<>));
or
builder.RegisterType<TestImplementationA>()
.As<ITestInterface<A>>();
builder.RegisterType<TestImplementationB>()
.As<ITestInterface<B>>();
builder.RegisterGeneric(typeof(SomeClass<>))
.AsSelf();
You will find below a working sample :
public interface ISomeClass<T> where T : class
{
Int32 Count { get; }
}
public class SomeClass<T> : ISomeClass<T> where T : class
{
private readonly IEnumerable<ITestInterface<T>> _testInterfaces;
public SomeClass(IEnumerable<ITestInterface<T>> testInterfaces)
{
_testInterfaces = testInterfaces;
}
public Int32 Count
{
get
{
return this._testInterfaces.Count();
}
}
}
public interface ITestInterface {}
public interface ITestInterface<T> : ITestInterface { }
public class A { }
public class B { }
public class TestImplementationA : ITestInterface<A> { }
public class TestImplementationB : ITestInterface<B> { }
class Program
{
static void Main(string[] args)
{
ContainerBuilder builder = new ContainerBuilder();
builder.RegisterType<TestImplementationA>()
.As<ITestInterface<A>>()
.As<ITestInterface>();
builder.RegisterType<TestImplementationB>()
.As<ITestInterface<B>>()
.As<ITestInterface>();
builder.RegisterGeneric(typeof(SomeClass<>))
.As(typeof(ISomeClass<>));
IContainer container = builder.Build();
var x = container.Resolve<ISomeClass<A>>();
Console.WriteLine(x.Count);
var z = container.Resolve<IEnumerable<ITestInterface>>();
}
}

Define custom conversion for structuremap to register Commands, CommandHandlers automatically

I'm using CQRS pattern in my recent project, so I defined some Commands that I call them CommandParameter and CommandHandlers.
For CommandParameters I have these Classes and Interfaces:
public interface ICommandParameter
{
}
public abstract class BaseEntityCommandParameter<T> : IAggregateRoot,ICommandParameter
where T : ModelEntitySuperType, new()
{
public T Entity { get; set; }
protected BaseEntityCommandParameter()
{
Entity = new T();
}
}
public class InsertCommandParameter<T> : BaseEntityCommandParameter<T>
where T : class, new()
{
}
And for CommandHandlers I defined these Classes and Interfaces:
public interface ICommandHandler<TCommandParameter>
where TCommandParameter :ICommandParameter
{
void Handle(TCommandParameter parameter);
string CommandCode { get; }
}
public class InsertCommandHandler<TCommandParameter, TEntity>
: ICommandHandler<TCommandParameter>
where TCommandParameter : BaseEntityCommandParameter<TEntity>, new()
where TEntity : ModelEntitySuperType, IAggregateRoot, new()
and I used them to make appropriate CommandParameters and CommandHandlers for each Entity for example for Order I have:
public class OrderInsertCommandParameter:InsertCommandParameter<Order>
{
}
public class OrderInsertCommandHandler
: InsertCommandHandler<OrderInsertCommandParameter, Order>
{
private readonly IUnitOfWorkFactory _factory;
public OrderInsertCommandHandler(IUnitOfWorkFactory factory,
IRepository<Order> repository)
: base(repository)
{
_factory = factory;
}
public override void Handle(OrderInsertCommandParameter parameter)
{
var uow = _factory.Create();
parameter.Entity.OrderCreationTime = DateTime.Now;
base.Handle(parameter);
uow.Commit();
}
}
I want to register these CommandParameters and appropriate CommandHandlers using structuremap automatically, How could I define a custom Conversion to do this?
The following should do the trick:
container.Configure(r =>
{
r.Scan(s =>
{
s.Assembly(typeof(ICommandHandler<>).Assembly);
s.ConnectImplementationsToTypesClosing(typeof(ICommandHandler<>));
});
});

Categories