I'm a beginner to ASP.net MVC. And liking it a lot more than WebForms.
So i decided to start a project which contains about 6 tables:
Gallery
Admins
Sessions
SessionImages
Offers
Info
I've created two projects : FP.WebUI and FP.Domain.
Inside my domain project i've created 3 folders Abstract, Concrete and Entities.
Inside Abstract folder there are 6 interfaces IGallery, ISessions.. etc. Each interface has something like this :
namespace FP.Domain.Abstract
{
public interface IGallery
{
IQueryable<Gallery> Gallery { get; }
}
}
And inside Concrete folder there are another 7 classes : EFDbGallery, EFDbSessions... and EFDbContext which inherites from DbContext class.
Each class of the above (except EFDbContext), implements each of the corresponding interface.
Now when i thought about it i found that i could make one interface which defines all the entities and only one class inside Concrete folder which implements that interface.
I really don't know what's better :
6 interfaces, 6 classes for each entity.
OR
1 interface, 1 class which returns all entities.
You seem to have stumbled upon the Repository pattern. The typical architectural decision is to create an interface
interface IRepository
{
IQueryable<Gallery> Query { get; }
}
Then have your ORM class implement the repository interface.
class MyDbContext : DbContext , IRepository
{
}
Now at this point, to answer your question, should I use 6 classes and 6 interfaces or 1 class and 1 interface the answer is categorically NO!
The typical pattern calls for a GENERIC interface (so in effect you have 6 interfaces, but a single interface source, if you need extra calls you can extend the generic).
//Actually this implementation is edging on
//Unit Of Work
interface IRepository<T>
{
IQueryable<T> Query { get; }
void Insert(T item);
void SaveChanges();
}
Then your EfContext exposes all of the interfaces. The reason being is that your controllers only typically need a single interface to work, and this makes mock/fake testing MUCH MUCH easier on your controllers (you don't need to create implementations of unused methods like an InfoQuery for a GalleryControllerTest).
If you find you need to have domain specific code for any interface you could extend the IRepository interface.
interface IGalleryRepository : IRepository<Gallery>
{
void SomeSpecialOperation(Gallery item);
}
Finally, implementation of this pattern will make life much easier if/when you start introducing Inversion of Control.
PS I typically refactor out the ACTUAL EF code (ie the concrete Repository) into a separate assembly, this is simply in case you ever decide to drop EF from your project.
I would use 7 classes because they will have different responsibilities.
.
Related
So I had a discussion with a coworker on implementing contract from a Base class to an interface.
We have the following structure with DDD, Api -> Application -> Domain -> Infrastructure.
In the infrastructure we use EF Core.
The following code example
Application
public interface IOrderRepository
{
IUnitOfWork UnitOfWork { get; }
Task AddOrderAsync(Order order);
}
Infrasctucture
public class OrderRepository : BaseRepository<Order, DbContext>, IOrderRepository
{
public OrderRepository(DbContext ctx) : base(ctx) { }
public async Task AddOrderAsync(Order order)
{
try
{
await AddAsync(order);
}
catch (Exception ex)
{
Log.Error($"Exception: {ex}");
throw ex;
}
}
/*
*
* Some other db methods
*
*/
}
public abstract class BaseRepository<T, U> where T : class where U : BaseDbContext, IUnitOfWork
{
protected readonly U _context;
public IUnitOfWork UnitOfWork
{
get
{
return _context;
}
}
public BaseRepository(U context)
{
_context = context;
}
protected virtual async Task AddAsync(T entity)
{
await _context.Set<T>().AddAsync(entity);
}
}
So I am arguing for, instead of implementing AddNAMEAsync methods in every repository to make AddAsync public virtual in the base class, and in corresponding interfaces and making use of the base class implementation. This way we also still have the possibility to orderride AddAsync if needed and also minimize unneccesary "duplicate code" in repositories.
My coworker on the other hand thinks that this will make the name too generic and when calling the repository you will not know which entity you are adding to the context by just reading the code. And aslo arguing on that we should not expose base class methods in interfaces, but that it instead should only be Parent -> Child exposure.
We are using SOLID principles and each handler only handles one entity/domain aggregate, we also have very clear naming on our variables/objects so you can easily see what you are adding to the context in the repository name as well as in the domain model
You can use AddAsync(T entity) method in BaseRepository, this will be provided reusable code for all your entities but this is already been implemented by Entity Framework Core. Do you really need to implement this structure again?
EF Core already provides the DbSet as base repository and DbSet<Order> as your order repository. Also provides DbContext as a unit of work implementation.
You don't need to create your generic base repository, repository, and unit of work classes if you don't use any other ORM tool or approach of persistence with EF Core. EF Core already provides these patterns as encapsulated.
What will encapsulating the classes and methods provided by EF Core solve in this way?
What are the differences between EF Core's DbSet and your BaseRepository?
See this sample project
In terms of naming you can, from my point-of-view, safely use "AddAsync()". The more important thing is that the client working with the repository uses a type of IOrderRepository. In this case, when looking at AddOrderAsync() the Order part could be seen as redundant in terms of naming because, first, you are calling it on a type that already indicates that everything is about orders, and second, you are passing an object of type Order which again indicates what you are going to add.
What you could still do is to make explicit that the generic methods are also part of an generic interface (e.g. IRepository) which IOrderRepository could extend. If you want to derive your infrastructure OrderRepository from a base class or if you want to pass it in some other object in terms of favouring composition over inheritance (e.g. a DbContext) is an implementation detail.
You can see an illustration of what I'm referring to here in the microservices reference application of Microsoft (eshopOnContainers).
I think you are right about implementing the AddAsync() method in a base class and inherit other classes from it. Because, when you want to use AddAsync() you will first inject the related class and then use it. (It will provide reusable code-base for you)
public class MyClass
{
private readonly OrderService _orderService;
//..
await _orderService.AddAsync(...);
}
There is no problem in terms of naming in this type of use, because the relevant service and what it will do are very clear.
Btw, CreateAsync or InsertAsync could be a better naming in my opinion to demonstrate database operation.
This question already has answers here:
Interface vs Abstract Class (general OO)
(36 answers)
Closed 7 years ago.
i have started career as support developer but i have dream to get a job for S/W dev.
i am learning OOPS with C#. often one thing bug me that is interface and abstract class usage. when to use interface and when to use abstract class. i search google on this topic but whatever the answer i browse and i saw all people try to explain what is abstract and interface but i am not after their definition rather i want see their real usage in real world program. here i like to highlight one code where interface is used but i think the full things can be design with abstract class too.
see the below code of repository design pattern where interface has been used
if i expose repository as interface
public interface IEmployeeRepository
{
Employee[] GetAll();
}
then advantage will be i could have as many implementations as i like as below
public class EmployeeRepositoryEF: IEmployeeRepository
{
public Employee[] GetAll()
{
//here you will return employees after querying your EF DbContext
}
}
public class EmployeeRepositoryXML: IEmployeeRepository
{
public Employee[] GetAll()
{
//here you will return employees after querying an XML file
}
}
public class EmployeeRepositoryWCF: IEmployeeRepository
{
public Employee[] GetAll()
{
//here you will return employees after querying some remote WCF service
}
}
see the above code which has one contract method GetAll()
and who ever will extend the interface then they can provide their own implementation. that is the advantage but my question can i write abstract class instead of interface here ?
suppose i have one abstract class
abstract class AbsEmployeeRepository
{
abstract public Employee[] GetAll();
}
now my all other repository will extend the abstract class AbsEmployeeRepository
and override the function GetAll() to give their own implementation.
now the question is if abstract class can solve my purpose then why we need interface in this scenario. where multiple inheritance is concern then interface will be preferred other wise we can complete job with abstract class.
looking for valuable comments and suggestions. thanks
You would use an abstract class, when you have
Code to be shared.
Default behaviour in methods, but want users of your class to be able to override it.
You would use an interface when
There is no shared code.
It needs to be applied to many objects, with no common base class.
To make the definitions of public methods clearer and provide documentation.
You wish the source code to be private.
Often you would use an abstract class (for shared code) together with an interface (for documentation).
Interface provides only "description" of your future classes, while abstract classes used when you need to have some "unfinished functionality". So if you want to have a class with some logic provided and some unimplemented functions - you should use abstract class, but if all the functions is not implemented - use interface instead.
You should use an abstract class IF all your implementation share a common code basis implementation. That means, the interface will guarantee, that all classes have the same members, but each one must have its own implementation for them.
If you have an abstract class as base, all inheriting classes share the same implementation unless they override it, which is in many cases not needed, often you need to implement only a hand full of members differently.
Interface - guarantee same members.
Abstract class - share common code basis.
Some nice thoughts about it got mentioned on my question for this, maybe this helps you out.
You use abstract classes when you need to provide more than just abstract members to implement but also some concrete member:
public abstract class A
{
protected abstract void DoSomeCheck();
public void DoStuff()
{
// You don't know how DoSomeCheck will be implemented but
// you know a derived class must implement it
DoSomeCheck();
}
}
Alternatively, you use interfaces to define contracts that must be fulfilled by implementers in order to ensure that they can work together with your code:
// This car accepts any engine that implements IEngine
public class Car
{
public IEngine Engine { get; set; }
}
public interface IEngine
{
void Start();
}
There're many other use cases for both abstract classes and interfaces, but covering them would require a to compose a book instead of a simple answer. I still think that above explanation should give you the required hint to learn more about the topic.
can i write abstract class instead of interface here ?
Technically, yes you can. Practically, you shouldn't.
In this particular case implementation of the repositories is likely to be different. If implementation is different, an interface will declare desired behaviour in a clear way. Use of an abstract class can be justified, if the implementation was the same for all your repositories, or some methods where the same. Therefore allowing you to move otherwise duplicated code into one shared place.
In your particular case I'd rather not use either tailored interface or abstract class. There's IEnumerable<T> that does all you want, do not re-invent the wheel:
public class EmployeeRepositoryEF: IEnumerable<Employee> {
...
}
public class EmployeeRepositoryXML: IEnumerable<Employee> {
...
}
whenever you want an array all you need do is ToArray():
EmployeeRepositoryEF myRepo = ...
Employee[] staff = myRepo.ToArray(); // <- just ask for array
As we know there are basically two important difference between Interface and Abstract class.
We can have function definitions in abstract class. This is advantageous when we want to add a function in a class without need to track down it's all implementations.
We can have multiple interface implementation.
I just came to know that we can differentiate between them in terms of Decoupling?
Your comments...
Also if you can you provide a very basic link that explains the Decoupling for Interface and Abstract class ?
We normally use Business Logic Layer, Data Access Layer(contains abstract functions) and DataAccess.SqlServer Layer. Right? Despite of the fact that we aware of the Business needs, why are we creating Data Access Layer(contains abstract functions), Why can't Business Logic layer directly access DataAccess.SqlServer Layer?
Decoupling
In programming and design, this is generally the act of making code which is re-usable with as few dependencies as possible.
Factory Pattern In This Context
When using the Factory Pattern, you have a centralized factory which can create objects without necessarily defining them itself. That would be up to the object's definition.
Abstract and Interface
Interface
Defining an interface is best practice, as it allows for a light weight type to be used for inference, and also provides a blueprint which all inheriting classes must abide by. For example, IDisposable must implement the Dispose method. Note that this is decoupled from the interface, as each class inheriting IDisposable will define its own function of the Dispose method.
Abstract
Abstract is similar to interface in that it is used for inheritance and inference, but it contains definitions which all classes will inherit. Something to the extent of every automobile will have an engine so a good abstract class for automobile could include a predefined set of methods for an engine.
Edit
Explanation
Here you will see a simple example of inheritance using an interface and an abstract class. The decoupling occurs when the interface is inherited by an abstract class and then it's methods are customized. This allows for a class to inherit the abstract class and still have the same type as the interface. The advantage is that the class inheriting the abstract class can be used when the expected type is the original interface.
Decoupling
That advantage allows for any implementation to be used which conforms to the expected interface. As such, many different overloads can be written and passed in. Here is an example of one.
Example
Interface Definition
public interface IReady
{
bool ComputeReadiness();
}
Inheritance
public abstract class WidgetExample : IReady
{
public int WidgetCount { get; set; }
public int WidgetTarget { get; set; }
public bool WidgetsReady { get; set; }
public WidgetExample()
{
WidgetCount = 3;
WidgetTarget = 45;
}
public bool ComputeReadiness()
{
if (WidgetCount < WidgetTarget)
{
WidgetsReady = false;
}
return WidgetsReady;
}
}
public class Foo : WidgetExample
{
public Foo()
{
this.WidgetTarget = 2;
}
}
public class Bar : IReady
{
public bool ComputeReadiness()
{
return true;
}
}
Decoupling
public class UsesIReady
{
public bool Start { get; set; }
public List<string> WidgetNames { get; set; }
//Here is the decoupling. Note that any object passed
//in with type IReady will be accepted in this method
public void BeginWork(IReady readiness)
{
if (readiness.ComputeReadiness())
{
Start = true;
Work();
}
}
private void Work()
{
foreach( var name in WidgetNames )
{
//todo: build name
}
}
}
Polymorphism
public class Main
{
public Main()
{
//Notice that either one of these implementations
//is accepted by BeginWork
//Foo uses the abstract class
IReady example = new Foo();
UsesIReady workExample = new UsesIReady();
workExample.BeginWork(example);
//Bar uses the interface
IReady sample = new Bar();
UsesIReady workSample = new UsesIReady();
workSample.BeginWork(sample);
}
}
I've been looking through the answers, and they all seem a little complicated for the question. So here is my (hopefully) simpler answer.
Interface should be used when none of the implementation details are available to the current scope of the code.
Abstracts should be used when some of the implementation details are available to you
And, for completeness, when all of the implementation details are available you should be using classes.
In terms of decoupling, while I somewhat agree with Shelakel, for the purposes of this question, and stating fully decoupled design practices, I would suggest the following:
Always use Interfaces to define external behaviour.
When you have some of the implementation details available, use
abstract classes to define them, but implement the interfaces on
the abstract classes, and inherit from those classes in turn.
This ensures that later if you need to change some obscure implementation detail in a new implementation you are able to do so without modifying the existing abstract class, and are also able to group different implementation types into different abstract classes.
EDIT: I forgot to include the link :)
http://www.codeproject.com/Articles/11155/Abstract-Class-versus-Interface
Abstract classes and interfaces are not MUTUALLY EXCLUSIVE choices. I often define both an Interface and an abstract class that implements that interface.
The interface ensure the maximum decoupling because it doesnt force your class to belong to a specific inheritance hierarchy, so your class may inherit from whichever other class. In other terms any class can inherit from an Interface, while classes that already inherits from other classes cannot inherit from an abstract class.
On the other side in an abstract class you can factor out code that is common to all implementations, while with Interfaces you are forced to implement everything from the scratch.
As a conclusion, often the best solution is using BOTH an abstract class and an Interface, so one can move from re-using the common code contained in the abstract class, if possible, to re-implementing the interface from the scratch, if needed.
Decoupling for the sake of decoupling is a futile exercise.
Interfaces are meant to be used for integration where the specifics aren't required to be known to be of use (ex. SendEmail()). Common uses include components, services, repositories and as markers for IOC and generic implementations.
Extension methods with generic type constraints that include interfaces allow functionality similar to traits found in Scala with similar composability.
public interface IHasQuantity { double Quantity { get; } }
public interface IHasPrice { decimal PricePerUnit { get; } }
public static class TraitExtensions
{
public static decimal CalculateTotalPrice<T>(this T instance)
where T : class, IHasPrice, IHasQuantity
{
return (decimal)instance.Quantity * instance.PricePerQuantity;
}
}
In my opinion, abstract classes and class inheritance is overused.
SOLID design principles teach us that Liskov's substitution principle implies that class inheritance should only be used if the inherited class is substitutable for the ancestor. This means that all methods should be implemented (no throw new NotImplementedExeption()) and should behave as expected.
I personally have found class inheritance useful in the case of the Template Method pattern as well as for state machines. Design patterns such as the builder pattern are in most cases more useful than deep chains of inheritance.
Now back to your question; interfaces should be used most if not all of the time. Class inheritance should be used internally and only externally for purposes of definition, whereafter an interface should be used for interaction and the concrete implementation provided via a factory or to be injected via an IOC container.
Ideally when using external libraries, an interface should be created and an adapter implemented to expose only the functionality required. Most of these components allow to be configured beforehand or at runtime to be resolved via an IOC container.
In terms of decoupling, it is important to decouple the application from its implementations (especially external dependencies) to minimize the reasons to change.
I hope that my explanation points you in the right direction. Remember that it's preferred to refactor working implementations and thereafter interfaces are defined to expose functionality.
I'm not going to discuss what are the pros/cons of these two constructs in general, as there are enough resources on that.
However, In terms of 'decoupling' a component from another, interface inheritance is much better than abstract classes, or class inheritance in general (In fact I don't think being abstract or not does not make much difference in terms of decoupling as all abstract does is prevent the class being instantiated without a concrete implementation).
Reason for above argument is, interfaces allow you to narrow down the exposure to absolute minimum of what required by the 'dependent component', if it requires a single method interface can easily do that, or even be a marker interface without any method. This might be difficult with a base class (abstract or concrete) as it should implement all the 'common' functionality for that base. Because of this a component dependent on the 'base type' will automatically 'see' all the common functionality even it does not need them for it's purposes.
Interfaces also gives you the best flexibility as even classes inheriting from bases which have nothing in common, can still implement an interface, and be used by the component expecting that interface. Good example of this is IDisposable interface.
So, my conclusion is for decoupling concern have all your components depend on interfaces than base types, and if you find most of your classes implementing that interface has a common implementation then have a base class implementing that interface and inherit other classes from that base.
The core difference is this:
Interfaces expose zero or more method signatures which all descendants must in turn implement (otherwise code won't even compile).
Interface-exposed methods can either be implemented implicitly (every type derived from the interface has access to them) or explicitely (methods can be accessed only if you typecast the object to the interface type itself). More details and an example can be found in this question.
Abstract classes expose zero or more full-fledged methods, which descendants can either use or override, providing their own implementation. This approach allows you to define a customizable, "default" behavior. Abstract classes allows you to easily add new methods with no issues (NotImplementedException really shines when adding methods to abstract classes), whereas adding a method to an interface requires you to modify all the classes implementing it.
The final point is, that a class can implement more than one interface simultaneously.
Some real-world example might be:
A hard drive which provides both USB and LAN ports is a good demonstration of multiple interface inheritance
A Laptop which has a LED marked "bluetooth" but no bluetooth hardware on board is a good analogy of the concept of not implementing an abstract method (you have the LED, you have the little B symbol, but there's nothing under the roof).
Edit 1
Here's a MSDN link explaining how to choose between interface and classes.
Defining a contract using an abstract class means that your implementers must inherit from this abstract class. Since C# doesn't support multiple inheritance, these implementers will not be able to have an alternate class hierarchy, which can be pretty limiting for some. In other words, an abstract class basically otherwise robs the implementer of the class hierarchy feature, which is often needed to get or use some other capabilities (of a framework or class library).
Defining a contract using an interface leaves the class hierarchy free for your implementers to use any way they see fit, in other words, providing much more freedom of implementation.
From a perspective of evaluation criteria, when we talk about coupling here we can speak to concerns of three separable authors, the client using (calling) the API/contract, the definer of the API/contract, and the implementer of the API/contract; we can speak to freedom (the fewer restrictions, the better), encapsulation (the less awareness necessary, the better), and resilience in the face of change.
I would offer that an interface results in looser coupling than an abstract class, in particular, between the definer and the implementer, due to higher freedom offered the implementer.
On the other hand, when it comes to versioning, you can at least add another method to the abstract class without necessarily requiring updates to subclass implementations, provided the added method has an implementation in the abstract class. Versioning interfaces across DLL boundaries usually means adding another interface, much more complex to roll out. (Of course, this is not a concern if you can refactor all the implementations together (say, because they're all in the same DLL)).
The best way to understand and remember difference between interface and abstract class, it's to remember that abstract class is a normal class and you can do everything with abstract class that you can do with the normal class with two exceptions.
You can't instantiate an abstract class
You can have abstract method only in abstract class
Coding to interface provides reusability and polymorphism.As far as class implements interface,the interface or abstract class can be passed to parameter instead of class that implements the interface.Urs common technical problem is handled vis designing interface and abstract class and implementing it and giving subclass the specific functionality implementation.Imagine its like framework.Framework define interface and abstract class and implement it that is common to all.And those that are abstract is implemented by client according to its own requirement.
public interface Polymorphism{
void run();
Void Bark();
Energy getEnergy(Polymorphism test);
Public abstract class EnergySynthesis implements Polymorphism{
abstract void Energy();
Void Bark(){
getEnergy(){
}
void run(){
getEnergy();
}public EnegyGeneartion extends EnergySynthesis {
Energy getEnergy(Polymorphism test){
return new Energy( test);
}
MainClass{
EnegyGeneartion test=new EnegyGeneartion ();
test.getEnergy(test);
test.Bark()
.
.
.
.
.
//here in Energy getEnergy(Polymorphism test) any class can be passed as parameter that implemets interface
While trying to create a data access layer for a new project, I ran into what I can only imagine as an OOP/Design/Generics problem (using EF 4.3 to access the database).
Mainly I wanted to achieve two things with this data layer:
Different Context objects I have on my project should share the same connection string.
Abstract repository class with common implementation.
For some reason, I cannot compile my solution without referencing EntityFramework on the service layer. What I'm looking for is a way to fix this. Here's what I have:
//Project/Namespace BusinessLogicLayer.DomainClasses
//POCO classes mapped on Entity Framework.
//Project/Namespace DataAccessLayer.Base
//Base classes and interfaces for all data access layer, such as:
public abstract class BaseContext<TContext> : DbContext where TContext : DbContext
{
//To allow multiple contexts sharing the same connection string
protected BaseContext(): base("name=MyConnectionString") {}
}
//Generic interface for a read-only repository
public interface IReadOnlyRepository<T> : IDisposable where T : class
//Generic interface for a read/write repository
public interface IRepository<T> : IReadOnlyRepository<T> where T : class
//Basic implementation for a read-only repository
public abstract class BaseReadOnlyRepository<C, T> : IReadOnlyRepository<T>
where T : class
where C : BaseContext<C>, new()
{
}
//Basic implementation for a read/write repository
public abstract class BaseRepository<C, T> : IRepository<T>
where T : class
where C : BaseContext<C>, new()
{
}
//Project DataAccessLayer.AccountContext/ Namespace DataAccessLayer
//Context class:
public class AccountContext : BaseContext<AccountContext> {}
//With this, I can have simple repositories:
public class UserRepository : BaseRepository<AccountContext, User>
{ //All implementation comes from the base abstract class, unless I need to change it (override methods)
}
I have a service layer between data access and the application (Windows Forms). Because I have a generic repository, it seemed a good and logic idea to have generic services. In the end, very similar to the repository structure:
//Project/Namespace BusinessLogicLayer.Services
//Service layer supposed to reference only the repository project and not Entity Framework.
//Generic interface for a read-only service working with a read-only repository
public interface IReadOnlyService<T> where T : class {}
//Generic interface for a read/write service working with a read/write repository
public interface IService<T> : IReadOnlyService<T> where T : class
//Base implementation for a read-only service
public abstract class BaseReadOnlyService<T, R> : IReadOnlyService<T>
where T : class
where R : IReadOnlyRepository<T>, new()
{
}
//Base implementation for a read/write service
public abstract class BaseService<T, R> : IService<T>
where T : class
where R : IRepository<T>, new()
{
}
//Concrete sample service
public class UserService : BaseService<User, UserRepository>
{ //As with the repository I can change the default behavior of implementation overriding methods
}
With this setup, the only way to compile is to reference Entity Framework on the service layer project.
How can I avoid the need to reference Entity Framework there?
At this point, I'm willing to even throw it all out and rebuild everything but this is the only way I found to make it work given my needs (DbContext sharing connection strings, generic repository to avoid replication of code).
Appreciate any help. Thanks.
--Edit--Including here some extra steps I did 3 hours after I posted the question--
In order to figure this out, I started to create a sample project with the same code above plus some implementation to mimic the results on the original project as much as possible.
I created the domain classes project, the whole base data layer project and then the context project. I noticed I need to reference Entity Framework on the context project even though the context class does not derive directly from DbContext. Instead, it derives from an abstract class that derives from DbContext. This is ok though since my context will have DbSets and any other implementation related to DbContext.
Next is the repository project. Needs to reference all other three (domain, base data layer and context). My repository has no code. All funcionality lies on the ancestor. I try to compile the repository project and VS requires me to referente Entity Framework. I wonder if it's really just a matter of embedding libraries. If this is confirmed, it's going to be a surprise. Entity Framework library is present on the output of the other projects. Why would I need to reference it here too? What's making VS require this?
Anyway, for testing purposes, I added the reference. After all, I'm inside the data layer. I can live with that. Moving on to the service layer. For the sake of simplicity, I put all of the service classes into the same project.
One possible flaw is that one of the constraints for the service abstract classes is the repository interface. That requires me to add a reference to the base data layer on my service layer. Perhaps already here there is something I can do that allows me to use only the repository reference. I have no option but to reference base data layer.
Lastly, my concrete service is created and VS gives me the following error message: The type 'System.Data.Entity.DbContext' is defined in an assembly that is not referenced. You must add a reference to assembly 'EntityFramework, Version=4.3.1.0, Culture=neutral, PublicKeyToken=b77a5c561934e089'.
So, in the end, the only way to keep going is to reference Entity Framework on the service layer. And at some point, when building the Windows Forms App, I will also have to reference Entity Framework.
What should I do to avoid having these references? What improvements can I have on this structure?
What I know is that my app certainly doesn't have to know that Entity Framework is involved anywhere on the other layers. Neither does the service layer. Services will only consume repositories. Repositories can even be providing fake data for tests.
In case anyone is interested, I uploaded the project I created while writing this. It's a 1,17Mb zip file with no binaries whatsoever (except the Entity Framework 4.3.1 dll that I got through Nuget). Link: http://www.mediafire.com/?b45zkedy2j7eocc.
Again, thanks for helping.
Instead of having abstract BaseContext in your BusinessLogicLayer, declare an interface. Then implement it in your Data Access Layer.
public interface IDataContext : IDisposable
{
int SaveChanges();
}
//Generic interface for a read-only repository
public interface IReadOnlyRepository<T> : IDisposable where T : class
//Generic interface for a read/write repository
public interface IRepository<T> : IReadOnlyRepository<T> where T : class
//Basic implementation for a read-only repository
public abstract class BaseReadOnlyRepository<C, T> : IReadOnlyRepository<T>
where T : class
where C : IDataContext
{
}
//Basic implementation for a read/write repository
public abstract class BaseRepository<C, T> : IRepository<T>
where T : class
where C : IDataContext
{
}
public interfaces IAccountContext : IDataContext
{
//other methods
}
Then in the data access layer
public abstract class BaseContext : DbContext, IDataContext
{
//To allow multiple contexts sharing the same connection string
protected BaseContext(): base("name=MyConnectionString") {}
}
public class AccountContext : BaseContext, IAccountContext {}
//With this, I can have simple repositories:
public class UserRepository : BaseRepository<AccountContext, User>
{ //All implementation comes from the base abstract class, unless I need to change it (override methods)
}
You can use DI/Ioc to inject the Context and the Repository to the services instead of instantiating the context inside the repository.
This decoupling will remove the need for referencing EF assembly in your business logic layer but remember that your domain entities are not completely independent of EF. For example navigational properties, relationship fix-ups will not work outside EF context. So in a way you are actually hiding a dependency!!
All I am trying to find out the correct definition of the repository pattern.
My original understanding was this (extremely dumbed down)
Separate your Business Objects from your Data Objects
Standardize access methods in data access layer.
I have really seen 2 different implementation, and there are no formal examples online, the ones i have seen are tucked away in books.
Implementation 1 :
public Interface IRepository<T>{
List<T> GetAll();
void Create(T p);
void Update(T p);
}
public interface IProductRepository: IRepository<Product> {
//Extension methods if needed
List<Product> GetProductsByCustomerID();
}
Implementation 2 :
public interface IProductRepository {
List<Product> GetAllProducts();
void CreateProduct(Product p);
void UpdateProduct(Product p);
List<Product> GetProductsByCustomerID();
}
Notice the first is generic Get/Update/GetAll, etc, the second is more of what I would define "DAO" like.
Both share an extraction from your data entities. Which I like, but i can do the same with a simple DAO. However the second piece standardize access operations I see value in, if you implement this enterprise wide people would easily know the set of access methods for your repository.
Am I wrong to assume that the standardization of access to data is an integral piece of this pattern ? If both are correct why would one choose to do implementation 2?
Rhino has a good article on implementation 1, and of course MS has a vague definition and an example of implementation 2 is here.
I second the Fowler quote cited by oded. I want to point out that he said "collection-like" interface. How you implement the collection like interface is certainly up to you, but neither can nor should you try to hide the fact it represents a remote datasource. It therefore differs significantly from an in-memory collection, which does not need to flush changes to a remote data store. The change tracking mechanism of your ORM or your roll-your-own solution determines how transparent this can be made to the caller. Deletes usually need to be marked explicitly, inserts are discoverable (persistence by reachability) and updates sometimes need to be marked explicitly too. Combine this with the complicated dependencies of your aggregate roots and you'll see that's not very collection like.
There is no such thing as "the cannonical repository implementation".
There is a constant battle going on between the advocators of a generic repository base class and those who prefer implementing each repository on its own. While the generic implementation is appealing in simple scenarios, you will very often find it to be a very leaky abstraction. For example some of your aggregates may only be soft-deleted (cistomizable via virtual method overrides) while others may not support a delete operation at all.
Make sure you understand the implications of each approach before deciding which route to take. Greg Young has a good post on the merits of generic repositories.
https://web.archive.org/web/20090204223739/http://codebetter.com/blogs/gregyoung/archive/2009/01/16/ddd-the-generic-repository.aspx
From Martin Fowler "Patterns of Enterprise Application Architecture", the definition of the Repository Pattern is:
Mediates between the domain and data mapping layers using a collection-like interface for accessing domain objects.
So, both approaches are correct.
I am a great fan of the generic repository pattern but I think you should strongly consider not directly inheriting from the interface as it can become a very large limitation especially since many times the code for the generic interface will be the same that it could be defined in an abstract base class that you will no longer be able to have more than 1 generic repository inside a class.
I recommend having your IProductRepository implementer access the generic IRepository<Product> through delegation and inject that in through the constructor so you can compose your class of possibly many IRepositories and group them behind a single interface in a way that makes sense.
I wrote a blog on this topic while it specifically references NHibernate this pattern can be applied to any type of repository: Creating a common generic and extensible NHiberate Repository version 2
With the introduction of LINQ in .NET, a generic repository pattern becomes much easier to realize:
public interface IRepository<T> : IQueryable<T>
{
void Add(T item);
void Remove(T item);
}
To qualify as a repository, it merely needs to be able to access data in the underlying store (easily provided by IQueryable) and modify the contained data.
You can provide extensions to the base interface to provide hooks for more entity-specific behaviour (such as wiring into a stored procedure call for a SQL-based repository), but the majority of operations can be completed by the simple interface.
In addition to your generic repository interface (implementation 1) and your variation on the role-specific repository (implementation 2) you can also consider a generic method repository:
public interface IRepository
{
void Save<ENTITY>(ENTITY entity) where ENTITY : DomainEntity;
ENTITY Load<ENTITY>(Guid id) where ENTITY : DomainEntity;
IQueryable<ENTITY> Query<ENTITY>() where ENTITY : DomainEntity;
IQueryable<ENTITY> Query<ENTITY>(IDomainQuery<ENTITY> whereQuery)
where ENTITY : DomainEntity;
}
This third version comes from this blogpost by Jimmy Bogard, where he also expresses preference for the generic repository interface.
I usually follow that with a generic repository baseclass which implements this interface; that way, I only have to implement the stuff that is different for each domain entity.
I usually use the generic repository with composition instead of inheritance. That gives me the advantage of a generic implementation, with the control of which methods to expose.
Something like this:
public Interface IRepository<T>{
List<T> GetAll();
void Create(T p);
void Update(T p);
}
public interface IProductRepository {
//Extension methods if needed
List<Product> GetProductsByCustomerID();
List<T> GetAll();
void Create(T p);
//Let assume here you should not be able to update the products
}
public ProductRepository : IProductRepository {
private IRepository _repository;
public ProductRepository(IRepository repository) {
this._repository = repository;
}
List<T> GetAll()
{
_repository.GetAll();
}
void Create(T p)
{
_repository.Create(p);
}
List<Product> GetProductsByCustomerID()
{
//..implementation goes here
}
}
The repository pattern is one of the most used pattern in software development. The are many post that can be marked as answer to your question.
Something that i like to highlight is the fact that a good repository implementation will be improved if you use IoC (Autofac, Windsor, etc...). I have been playing long time ago with some ADO.NET based frameworks (LinqToSql, EF) and NHibernate. You always can have benefits from a generic implementation if you use IoC.
You can define interfaces for your specific repositories and resolve when you really need some specific actions.