Service Layer, Repository Layer and Entity Framework

4.6k views Asked by At

I'm designing a layered architecture (all layers are on same machine) with using Entity Framework (POCO entities), to use same layers with an ASP.Net MVC application, mobile application, etc; also to maintain testability...

I will have UI Layer > Service Layer > Repository Layer > Entity Framework > Database, with Dependency Injection, layer abstraction, and separation of concerns.

  • Assume that, I have two methods (Customer, Order are entity classes). Which layer I should place these methods?:

    • public IList GetOrdersByCustomerId(int CustomerId) that contains a LINQ query.
      (Repository layer, or Service Layer?)
    • public void RequestAnOrderAndStartTheShipmentProcess(Customer CustomerEntity, Order OrderEntity) that does some insert operations like orderRepository.Add(OrderEntity), shipmentRepository.Add(ShipmentEntity) etc...
      (a separate Business Logic Layer, or Service Layer?)
  • I will have IOrderService interface, and "OrderService : IOrderService" class for dependency injection, will the interface and class be positioned in same assembly, or should be positioned in separate assemblies?

Thanks

EDIT

Thanks for your answer. But in this case, four questions came to think about...
1. If UI has a reference to DataAccess assembly, the developers can access to DataAccess classes directly in UI code, and shouldn't it create an extra effort to make code reviews (e.g. if there's a junior developer in team)?
2. I understood that, I should have GetOrdersByCustomerId method both in Repository layer (doing the real querying) and Service Layer (calling GetOrdersByCustomerId method in OrderRepository class), is it correct?
3. Also I should do CRUD operations for (nearly) all tables to maintain them, and think about I have 96 tables in my current project (it's not too much but it's not few also), should I have Add, Update, Delete methods in Service layer too? Or should I think about more "behavioural" in my service layer?
4. I confused about, if I have GetOrdersByCustomerById, GetOrdersByStatus, etc... methods in my OrderRepository, isn't it be like a DAO class?

2

There are 2 answers

2
Gert Arnold On

My opinion (it's always a bit arbitrary):

  1. Repository, because it is a typical specified get operation on a single entity set.
  2. Service layer, because it orchestrates several operations on several entities.
  3. Separate assemblies, so you can add interface implementations from other assemblies without having to reference an assembly that already contains an implementation.
0
ThomasH On

You could consider an architecture, having three assemblies (layers):

Business
Containng your service classes (and also your RequestAnOrderAndStartTheShipmentProcess method). The business layer will contain all your core business rules, and therefore it is not very likely that you suddenly want to swap this layer out with a complete new one or add an alternative. Therefore I would keep both OrderService and IOrderService in this assembly. I would also put the POCO classes (have EF autogenerate these for you like this) and repository interfaces in this layer.

DataAccess
This is where you keep your EF repository implementations (and your GetOrdersByCustomerId method). This assembly references the business assembly, because it implements the repository interfaces found in that layer.

UI
Here you instantiate the repositories from the DataAccess assembly and inject these into the service classes of the Business layer using constructor injection. Thus this assembly has references to Business and DataAccess.

Using this architecture your business layer is nicely seperated from the other layers and easy to unit test. See this answer for more details in dependency injection.