I have 4 projects in my solution, 1. MyApp.UI (MVC) 2. MyApp.Core (ClassLibrary) 3. MyApp.Data (ClassLibrary with EF implementation) and 4. MyApp.Tests
In my Data project I have 4 repository implementations and all 4 repositories are implemented IRepositoryBase interface and their own repository interface Example,
public class RepositoryA: IRepositoryBase, IRepositoryA
{
.....
}
public class RepositoryB: IRepositoryBase, IRepositoryB
{
.....
}
Now in my Data project I want to create abstract Repository Factory which returns the concrete implementations of corresponding repository interfaces and this class used only inside MyApp.Data project,
For example RepositoryFactory.GetRepository<IRepositoryA>()
must returns instance of RepositoryA class or RepositoryFactory.GetRepository<IRepositoryB>()
must returns instance of RepositoryB class
My concerns are ,
How I can achieve this ? I want to use RepositoryFactory to get the Repository implementations only inside MyApp.Data project.
Since my UI (MVC) application already doing the boot strap do i need to pass the container to MyApp.Data project or Data project need its own container registration logic?.
I also want to test my MyApp.Data project separately (without UI project dependency).
If possible please give an working code for this scenario.
Thanks in Advance
I found a solution to use AbstractFactory pattern to use in conjunction with simple-injector container class for this problem .
I still not sure whether this is a appropriate solution for this problem
DataRepositoryFactory implementations,
//Abstract data repository factory
public interface IDataRepositoryFactory
{
T GetDataRepository<T>() where T : IDataRepository;
}
public class DataRepositoryFactory : IDataRepositoryFactory
{
T IDataRepositoryFactory.GetDataRepository<T>()
{
return (T)DataBootStraper
.DataDIContainer
.GetInstance(typeof(T));
}
}
in MyApp.Data project I created static Bootstrap class which use to register the data layer dependencies.
public static class DataBootStraper
{
public static void BootStrap(Container container)
{
container.Register<IRepositoryA, RepositoryA>();
container.Register<IRepositoryB, RepositoryB>();
container.Register<IRepositoryC, RepositoryC>();
//Register the DataRepositoryFactory also with container
container.Register<IDataRepositoryFactory, DataRepositoryFactory>();
}
}
So this can be called from my Unit test cases as well as UI bootstraper.
Below is the example of the usage of factory
public class DataRepositoryFactoryTest
{
private readonly IDataRepositoryFactory _repositoryFactory;
public DataRepositoryFactoryTest(IDataRepositoryFactory repositoryFactory)
{
_repositoryFactory = repositoryFactory;
}
public IEnumerable<RepoAEntities> GetEntitiesFromRepoA()
{
return _repositoryFactory.GetDataRepository<IRepositoryA>().GetEntities();
}
public IEnumerable<RepoBEntities> GetEntitiesFromRepoB()
{
return _repositoryFactory.GetDataRepository<IRepositoryB>().GetEntities();
}
public IEnumerable<RepoCEntities> GetEntitiesFromRepoC()
{
return _repositoryFactory.GetDataRepository<IRepositoryC>().GetEntities();
}
}