Reputation: 3795
As EF6 is now fully mockable and we have the unit of work and repository built in - I'd like to move away from repository pattern.
However, how is one to share a single data context across an application. Should I have a base service which takes a datacontext in its constructor?
public class BaseService<T>:where T:class
{
public BaseService(DataContext myDataContext)
{
//....... code
}
}
and then have derived services, such as PersonService, OrderService and others using the datacontext to query, update and save data?
Or is there a better way?
Thanks
Upvotes: 2
Views: 637
Reputation: 230
However, how is one to share a single data context across an application. Should I have a base service which takes a datacontext in its constructor?
Like most things, it depends. How complex is your design? Are you applying domain driven design? Code-first or Db-first?
Generally, the solution you propose is fine. As your project grows more complex, you might adopt BoundedContexts as part of applying domain driven design. So having just one context that is part of some 'BaseService' may no longer make sense.
JotaBe referred to dependency injection and the lifecycle of the context, which is important. Are you using dependency injection? I prefer to have my IoC container look after the lifecycle of the context. As an example, for a web application, I would have the lifecycle bound to each web request.
Any mature IoC container should be able to support this. Here is a quick one-liner for Autofac.
builder.RegisterType<MyDbContext>().As<IMyDbContext>().InstancePerApiRequest();
Particularly with Db-first implementations I prefer to back the DbContext with an interface and use the interface to control what is being exposed to the caller.
public interface IMyDbContext {
//Only expose people, not orders for example
DbSet<Person> People { get; set; }
}
public partial class MyDbContext : IMyDbContext {
//the generated DbContext class satisfies the interface
}
public class PersonService {
private readonly IMyDbContext _context;
public PersonService(IMyDbContext context){
_context = context;
}
}
I've found the overhead to be small and helps scope the context to the actual objects your interested in, rather than creating multiple EDMX files. Helps lead into BoundedContexts when your domain grows in complexity.
Here's another example regarding bounded contexts and shrinking EF models
Upvotes: 1