Ninject and DbContext - c#

Building a app with EF 6 and Ninject 3.2.2 I'm having some trouble wrapping my head around how to access the DbContext in a intelligent way.
As I understand in the newer versions of Ninject only constructor injection is encouraged. As EF 6, itself is repo and unit of work I'm not doing any abstractions on top of EF.
If would like to be able to use multiple small units of works so injecting the DbContext (uow) into every class that needs it is not going to work.
In a non IoC way I would do like this:
Using(var db = new DbContext){}
How do achieve this using Ninject as I no longer can do kernel.get in my using block...

I'd consider two approaches:
Create general DbContext, which can be hidden behind an interface:
public interface IPortalContext : IDisposable
{
DbSet<User> Users { get; }
DbContext Context { get; }
}
public class PortalContext : DbContext, IPortalContext
{
public PortalContext()
: base("PortalConnectionString")
{
}
public virtual DbSet<User> Users { get; set; }
}
then you can inject your context to the constructor without problem.
Create many small contexts which can be used in different scenarios and classes.
I don't think that first approach is bad since it only encapsulates your DbSets and DbContext making it easier to inject and test. You don't make any unnecessary layers above EF and whole interface seems quite transparent.
Anyway this approach is better than making whole IRepository<T> stuff to access another repository...

I'm not sure what you mean by "multiple small unit of works", but just for exposure, this is what I've done in a recent application:
Divided the domain in small bounded contexts (this is more of a conceptual step)
Each bounded context has: a context, a repository, a repository factory
Each context implements an IContext and a BaseContext that gives basic methods and common properties (IContext will be useful for mocking)
Each repository takes the relative context as a constructor paramenter
This is an example of a repository factory
public class CartRepositoryFactory : IRepositoryFactory
{
public IRepository Generate(CartContext ctx)
{
return new CartRepository(ctx);
}
}
At the application service layer, I inject a UoW and the repository factory that I need
If I want to work with several different context in one service, I simply create another service and combine the services that I need, injecting them
You might be asking, but why?!? This is madness!!
Well, because if the Repository manages the DbContext, then I can only do one operation per class instantiation. This allows me to open a DbContext and make several calls to the Repository.
Of course now you have the same problem at application service level, you can only call one method per instantiation, but it's far easier to manage.
Ultimately it all comes down to your taste: would you rather have a thin service or a thin repository?

Related

Simplifying composition interfaces in C#

In the code I am working on I have a structure where some portions of the code depend on the current software session. Software session contains multiple helper objects which are dependency injected by composition.
One example is IRepository injected to it, which contains access to the data repository. And the IRepository contains a DatabaseContext which writes to a database, via IDbContext again which is injected.
SoftwareSession is the only injected common infrastructure for accessing all the way to the database, acting as a gateway. This means when I want to write an object to database, for instance WriteCar I will have to implement 3 interfaces, 2 functions delegating to composed objects and 1 function with implementation. It is clarified in the code fragment below. The WriteCar signatures are defined the same in 3 interfaces (IRepository, ISoftwareSession, IDbContext), 2 places where it is not implemented (Repository, SoftwareSession) which simply calls composited objects related functions and 1 place of actual implementation (IDbContext)
This means when I want to refactor, move code, add functionality or change function signatures I will always have to change 6 places for one function.
I think this provides the best environment for improving testability and it follows best practices where software session wraps access to repository and repository wraps access to data contexts - yet I still am questioning if we can have some better way of writing it once, or do I have a misunderstanding of some concept in the code below?
What is the architecturally more maintainable way of implementing this? Maybe even using some clever way of lambdas or delegates to reduce the amount of code written for each new functionality? Or even some libraries (like automapper simplifies DTOs) or tools to ease generation of this code from some kind of templating mechanism using Visual Studio, Resharper, etc?
Please let me know if I am having some confusion of concepts here. I know some my colleagues have similar views, in which case it may be helpful to clarify misunderstandings of others as well.
public class SoftwareSession : ISoftwareSession
{
...
IRepository repository;
public void WriteCar(Car car){
repository.WriteCar(car);
}
...
}
public interface ISoftwareSession{
...
void WriteCar(Car car);
...
}
public class Repository : IRepository{
...
IDbContext context;
public void WriteCar(Car car){
context.WriteCar(car);
}
...
}
public interface IRepository{
...
void WriteCar(Car car);
...
}
public class MyDbContext : IDbContext{
...
public void WriteCar(Car car){
//The Actual Implementation here.
...
}
...
}
public interface IDbContext{
...
void WriteCar(Car car);
...
}
For one thing, your IDbContext and IRepository are the same. You would probably like to remove IDbContext, or at least to remove methods declared in IRepository from it.
Then, both MyDbContext and Repository would implement IRepository and Repository class would just be a wrapper around MyDbContext.
Then, if Repository is only forwarding calls to MyDbContext, then you probably don't need that class either.
Furthermore, I don't see that you are doing anything in the SoftwareSession apart from forwarding the call to the contained repository. Do you really need SoftwareSession, or would it make sense to pass IRepository directly to whoever is calling the session object?
Bottom line is that this implementation is swarming with duplication and forwarding. Remove that, and your entire model would become simple.
Without seeing your composition root, I'm not entirely sure how your implementation works, but I'd suggest looking into using an Inversion of Control (IoC) container. Since your ISoftwareSession implementation only depends on an IRepository instance, you only need to inject that in the class' constructor. The same goes for your IRepository implementation: you only need to inject your IDbContext into the constructor.
With the IoC container, you "register", i.e. wire up your interfaces to your implementation at application startup (in the composition root), and the container takes care of creating the required instances when you resolve the dependencies. Then all you have to do is get the instance of SoftwareSession from the container, and away you go.
So, you could change your SoftwareSession implementation like this:
public class SoftwareSession : ISoftwareSession
{
IRepository repository;
public SoftwareSession(IRepository repository)
{
this.repository = repository;
}
public void WriteCar(Car car)
{
repository.WriteCar(car);
}
}
And your Repository implementation like this:
public class Repository : IRepository
{
IDbContext context;
public Repository(IDbContext dbContext)
{
context = dbContext;
}
public void WriteCar(Car car)
{
context.WriteCar(car);
}
}
Then here is your composition root:
var ioc = new MyIocContainer();
// register your interfaces and their associated implementation types with the IoC container
ioc.Register<ISoftwareSession, SoftwareSession>();
ioc.Register<IRepository, Repository>();
ioc.Register<IDbContext, MyDbContext>();
// resolve the IoC container
ioc.Resolve();
// get your `ISoftwareSession` instance
var session = ioc.GetConcrete<ISoftwareSession>();
var newCar = new Car();
session.WriteCar(newCar);

Should repositories be properties on the unit of work when using Entity Framework?

I have scoured the web looking for a good implementation of the Repository/Unit of Work pattern using Entity Framework. Everything I've come across is either tightly coupled at some point in the abstraction or assumes that the DbContext used by the Unit of Work and Repositories is shared and should live for the entire HTTP request (instance per request via dependency injection).
For example, assuming you are consuming repositories from the service layer, a service constructor might look like this:
public DirectoryService(IUnitOfWork unitOfWork, ICountryRepository countryRepo, IProvinceRepository provinceRepo)
{
/* set member variables... */
}
The unit of work constructor might look like:
public UnitOfWork(IDbContext context)
{
_context = context;
}
And a repository constructor might look like:
CountryRepository(IDbContext context)
{
_context = context;
}
This solution makes the blind assumption that the Dependency injection is setting up the Unit of Work and Repositories to share the same IDbContext using instance per request. Is that really a safe assumption to make?
If you are using dependency injection with instance per request, the same IDbContext will be injected into multiple units of work. The unit of work is no longer atomic, is it? I might have pending changes in one service that are then committed in another service because the context is shared across multiple units of work.
To me it seems to make more sense to set up a IDbContextFactory and get a fresh database context with each unit of work.
public interface IDbContextFactory
{
IDbContext OpenContext();
}
public class UnitOfWork
{
private IDbContextFactory _factory;
private IDbContext _context;
UnitOfWork(IDbContextFactory factory)
{
_factory = factory;
}
internal IDbContext Context
{
get { return _context ?? (_context = _factory.OpenContext()); }
}
}
The problem then becomes, how do I make my Unit of Work implementation available to the injected repositories? I don't want to assume instance per request because then I'm right back in the same boat I started in.
The only thing I can think of is to follow Entity Framework's lead and make the repositories (IDbSet<T>) part of the unit of work (DbContext).
So then I might have units of work that look like this:
public class DirectoryUnitOfWork : IDirectoryUnitOfWork
{
private IDbContextFactory _factory;
private IDbContext _context;
public DirectoryUnitOfWork(IDbContextFactory factory)
{
_factory = factory;
}
protected IDbContext Context
{
get { return _context ?? (_context = _factory.OpenContext()); }
}
public ICountryRepository CountryRepository
{
get { return _countryRepo ?? (_countryRepo = new CountryRepository(Context)); }
}
public IProvinceRepository ProvinceRepository
{
get { return _provinceRepo ?? (_provinceRepo = new ProvinceRepository(Context)); }
}
void Commit()
{
Context.SaveChanges();
}
}
Then my Directory service starts to look like this
public class DirectoryService : IDirectoryService
{
private IDirectoryUnitOfWork _unitOfWork;
public DirectoryService(IDirectoryUnitOfWork unitOfWork)
{
_unitOfWork = unitOfWork;
}
public GetCountry(int id)
{
return _unitOfWork.CountryRepository.GetById(id);
}
public GetProvince(int id)
{
return _unitOfWork.ProvinceRepository.GetById(id);
}
public void AddProvince(Province province)
{
_unitOfWork.ProvinceRepository.Create(province);
Country country = GetCountry(province.CountryId);
country.NumberOfProvinces++; // Update aggregate count
_unitOfWork.Commit();
}
/* ... and so on ... */
}
It seems like a lot of work, but using this method leaves everything loosely coupled and unit testable. Am I missing an easier way, or is this a good way to do it if I am going to abstract away Entity Framework?
You should never abstract an ORM (itself an abstraction), but you should abstract the Persistence. The only UoW I'm using is a db transaction and that's a persistence detail. You don't need to use UoW and Repository together. You should think if you really need all this stuff.
Personally, I'm using the repository by default because Persistence is the last thing I do in an app. I don't care about patterns per se , I do care about decoupling my BL or the UI from DAL. Your upper layers (everything except DAL, which is the lowest layer from a dependency point of view) should always know about an abstraction, so that you can go as wild as you want in the DAL implementation.
One trick a lot of devs don't know is that design patterns (especially architectural ones) should be treated as a high level principle first and as a technical know-how second. Simply put, the thing that matters the most is the benefit a pattern is trying to achieve (the principle, the bigger picture), not its actual implementation (the "low level" details).
Ask yourself why should the BL know about a UoW in the first place. The BL only knows about an abstraction dealing with business objects. And you never work with the whole BL as once, you're always in a specific BL context. Your DirectoryService seems to be doing way to much for its own good. Updating stats doesn't look like it belongs to the same context as adding a new Province. Also why do you need UoW for queries?
One mistake I see a lot is devs rushing to write whatever code (with a design pattern attached) when they aren't doing the most important part: the design itself. When you have the improper design, problems appear and you start looking for workarounds. One of them is this UoW with Repository properties, which require a high layer like BL to know more than business concerns. Now the BL needs to know that you're using a UoW, a lower level pattern which is great for the DAL, not so great for the BL.
Btw, UoW never makes sense for quering as you're dealing with a 'read' situation, UoW is only for 'writes'. I don't mention EF or any ORM because they don't really matter, your BL service (Directory Service) is already corrupted by an infrastructural detail required by improper design. Note that sometimes you do need to compromise in order to implement a solution, but this is not the case.
Proper design means you know about your bounded context (yeah, DDD concept you can apply it regardless how much DDD you want to do) and don't put everything that might use the same data in one place. You have specific contexts for use cases and counting provinces (a presentation/reporting detail) is really a different use case than adding Province.
Adding the province and then publishing an event which signals to a handler to update stats is a more elegant, maintainable solution. No UoW required either.
Your code would look like this
public class DirectoryService : IDirectoryService
{
public DirectoryService(IProvinceRepository repo, IDispatchMessage bus)
{
//assign fields
}
/* other stuff */
//maybe province is an input model which is used by the service to create a business Province?
public void AddProvince(Province province)
{
_repo.Save(province);
_bus.Publish( new ProvinceCreated(province));
}
}
public class StatsUpdater:ISubscribeTo<ProvinceCreated> /* and other stat trigger events */
{
public void Handle(ProvinceCreated evnt)
{
//update stats here
}
}
In a way it simplifies things, in other way you might thing it complicates stuff. Actually, this is a maintainable approach, because the stats updater can subscribe to many events but the logic stays in one class only. And the DirectoryService does only the things that are assumed it does (what part of the name AddProvince hints you that the method also updates stats?).
In conclusion, you need to design the BL better before rushing to complicate your life with UoW, DbContext, Repositories as properties etc
or assumes that the DbContext used by the Unit of Work and Repositories is shared and should live for the entire HTTP request
This is clearly wrong. Assuming that the context is shared between the UoW and Repositories doesn't mean that the context lifetime should depend on the HTTP request. Rather - you can create new instances of the context and the UoW that use it whenever you want. This is only a convenience to have a default UoW that lives for the HTTP request but creating new, local units of work could be handy.
On the other hand, if repositories are exposed from the UoW:
public class UnitOfWork
{
...
public IUserRepository UserRepo
{
get { ... }
}
public IAccountRepository AccountRepo
{
get { ... }
}
then not sharing the same context between repos could have unexpected results:
UoW uow = ....
var u1 = uow.User.FirstOrDefault( u => u.ID == 5 );
var u2 = uow.Account.FirstOrDefault( a => a.ID_USER == 5 ).User;
You would definitely expect these two to return the same instance of the user of the id 5 and what's more, sharing the same context would mean that the second query could retrieve the user from the 1st level cache. On the other hand, two different contexts for two repos means that you get two different instances.
This also means that this would not be possible
var u1 = uow.User.FirstOrDefault( u => u.ID == 5 );
var a1 = uow.Account.FirstOrDefault( a => a.ID == 177 );
a1.User = u1; // oops!
as mixing entites from different contexts would just raise an exception. But the above scenario is a common one!
The conclusion from these observations is that you should share the context between repos. But, if you need a fresh instance, you just create a local, fresh instance of the context, inject it into the UoW, from where it gets injected into repos, and dispose it at will.

How to use Simple injector for repository in business layer

I would like that in my MVC layer there will be no Repositories at all.
I've generic EFRepository, IRepository and PASContext (which inherits from DbContext) in my DAL project layer .
I've installed Simple Injector with quick start under my MVC project and thats allows me to get in the constructor of each controller the repository i want .
But in my solution i have also BLL project and i want MVC layer to talk only with the BLL layer, as this is the project architecture and in the future i would like to add logic in the classes within the BLL layer .
Also i don't want to create a context in my BLL layer, but the Repository has no constructor which takes 0 arguments, this is my ProductBLL class :
public class BLLProducts
{
IRepository<Product> ProductRepository;
public BLLProducts(EFRepository<Product> Repository)
{
ProductRepository = Repository;
}
public ICollection<Product> getAll()
{
return ProductRepository.All().ToList();
}
}
How can i initiate the BLLProduct class from a controller or from a unitTest without creating a repository/context ? so i can keep my abstraction here.
I know i need to use somehow the Simple injector here, i just dont know how .
From perspective of the controller, it's just a matter of injecting the BLLProducts into it, like this:
// constructor
public HomeController(BLLProducts products) {
this.products = products;
}
From a unit testing perspective, letting the controllers depend on concrete classes is suboptimal (it violates the Dependency Inversion Principle). This is sub optimal, since you now need to create a BLLProducts instance and instantiate it with a DbContext, but this DbContext is specific to Entity Framework, which depends on a database. This makes testing harder and slower. You want your unit tests to run without a database.
So the solution to this is to hide this BLLProducts class behind an abstraction. A simple way to do this is extract an interface out of this class:
public interface IBLLProducts {
ICollection<Product> getAll();
}
This makes unit testing the controllers much easier. The only thing you have to do is let it depend on this new interface:
public HomeController(IBLLProducts products) {
this.products = products;
}
You will need to register this IBLLProducts interface in Simple Injector:
container.Register<IBBLProducts, BLLProducts>();
This whole model still has some downsides to it. For instance, although Simple Injector can create and dispose a DbContext for you, where do you call SubmitChanges? Doing this when the web requests ends is a pretty bad idea. The only convenient solution I found for this is to move to a more SOLID architecture. For instance, take a look at this question.

How to dispose object context in repository pattern

I implemented a repository pattern to my application dat .
I have :
public class EFRepository<T>
{
DbContext // My db context
public IQureable<T> GetQuery()
{
DataContext.CreateQuery(...);
}
}
Now let say I have user repository :
public class UserRepository : EFRepository
{
public UserGetUserDetails(int userId)
{
GetQuery().Where(u=>u.Id = userId).First();
}
}
my problem is how to release the DbContext when I use the EF repository in derived repositories.
Lets say : UserRepository: EFRepository , and it uses the GetQuery then I have to dispose the context.
Any good idea how to make this in generic repository?
You should think about what unit of work you have. (there are many other tutorials on the internet). The idea is to keep the same dbcontext and to re-use it while being in the same unit of work. This way, entities will already be attached to the context when needing them, etc..
Now, this being a web application, your unit of work would be in this case a request. While in the same request, reuse your DBContext. There are many ways to do this and just off the top of my head - you will want something like 'OnActionExecuting' where you take care of your context.
But even better would be to use an Inversion of Control pattern (there are many frameworks out there that use this, i primarily use NInject . This will automatically create a new instance of a certain class, when needed, depending on the scope you suggested - in this case 'onRequestScope'. A lot more to say about IoC but not the scope of the question
I have used a similar pattern in the past and in my case I actually inherited from DbContext, which itself implements IDisposable. Provided you are using EFRepository or classes derived from it in a using block you should be fine.
If you would prefer a DbContext member variable, then EFRepository will need to implement IDisposable and call DbContext.Dispose() from its Dispose method.

I know how to use dependency injection but I recognize no practical advantage for it

It is about this (Inject the dependency)
private readonly ICustomerService _customerService;
public Billing(ICustomerService customerService)
{
_customerService = customerService;
}
versus this (Create the dependency)
private readonly ICustomerService _customerService;
public Billing()
{
_customerService = new CustomerService();
}
The latter sample so they say is bad because... it violates DI...of course nothing is injected... but what if DI would not exist, what is so bad that the CustomerService is created manually from the Billing class? I see no practical advantage concerning exchangeability of the Service interface.
I ask for a practical example with source code may it be a unit test or showing a practical solution why it is so much more loose coupling.
Anyone keen enough to show his DI muscles and why it has a practical right to exist and be applied?
UPDATE
So people have not to read all up I will write here my short experience:
DI as a pattern has a practical usage. To follow DI by not injecting all services manually (a poor mans DI tool so they say...) use a DI framework like LightCore/Unity but be sure you use the right tool for the appropriate job. This is what I did not;-) Developing a mvvm/wpf application I have other requirements the LightCore/Unity tool could not support they even were a barrier. My solutions was to use MEFEDMVVM with which I am happy. Now my services are automatically injected at runtime not at startup time.:-)
Understanding the how and understanding the why are very different things..
One of the biggest benefits of DI is for unit testing. In your second example it's impossible to unit test Billing without also testing CustomerService (and also testing any further dependencies in the chain). In that case you're not unit testing, you're integration testing! If you want a good rationale for using DI, you need not look any further than a rationale for unit testing..
Imagine that CustomerService connects to your CRM system and your database. It creates a whole bunch of network connections to retrieve data about the customer and maybe reads additional things from the database to augment that before returning the data to the Billing class to use in its calculation.
Now you want to unit test Billing to make sure the calculations it's making are correct (you don't want to send out wrong bills right?)
How will you unit test Billing if its constructor is tied to a class that requires connections to a real CRM system and database? Wouldn't it be better to inject that dependency as an interface, easily allowing you to provide a mock version for your tests?
That is why DI is useful.
DI Comes in useful, when you want to pass different implementations of the Interface to your class, for example: Unit Testing.
Say your Billing constructor is an MVC controller's constructor, and your CustomerService took some form of IDataContext as a parameter.
Global.asax
// Does the binding
ICustomerService binds to CustomerService
IDataContext binds to EntityFrameworkContext
CustomerService
private IDataContext _datacontext;
public CustomerService(IDataContext dataContext)
{
_dataContext = dataContext;
}
public AddCustomer(Customer entity)
{
this._dataContext.Customers.Add(entity);
this._dataContext.SaveChanges;
}
MVC Controller
private ICustomerService _customerService;
public Billing(ICustomerService customerService)
{
_customerService = customerService;
}
public ActionResult NewCustomer()
{
Customer customer = new Customer(){ Name = "test" };
this._customerService.AddCustomer(customer);
return View();
}
Say you wanted to unit test your Services, or Controllers. You would pass in the CustomerServices, but you would pass in a fake implementation of the EntityFrameWorkContext.
So a FakeDbContext, that implements IDataContext, is passed to customer services.
The FakeDbContext may just store the entities in Lists or a more elaborate storage mechanism, the point being, you can inject different implementations of dependencies, which allows you to alter the behaviour of one component without having to modify your code elsewhere.
In my experience it is not only about avoiding integration test (but that is a very important point too). Instantiating classes on the inside can create a lot of work unit testing. A class like CustomerService might depend on an open Database connection, configuration files, services being available and a lot of other stuff, that you should not have to know about, when your job is to test the Billing class only.
That being said, sometimes it is a pain always to inject everything. Injection frameworks might lighten that load, but I'm not at big fan. Another kind stackoverflow user pointed me to what he called "poor mans injection". Basically it consists of two constructor overloads: One constructor with the injected interface, and one without. The one without does nothing but instantiate a concrete class that implements the interface, and pass it to the other constructor. It goes something like this:
public class Billing
{
ICustomerService _customerService;
public Billing():this(new CustomerService()) {}
public Billing(ICustomerService customerService)
{
_customerService = customerService;
}
}
This way you have an way to inject when testing AND a way to construct the class with a default implementation of the interface. Not everybody loves this pattern, but I find it practical for some scenarios.

Categories