I have a built an MVC application with a model layer containing entities, data mappers and service classes. So far so good. But now I have a controller that need to show a report containing data from multiple db tables with no relation to any entities in my model. The report is built from a advanced MySQL query containing joins, SUM/AVG-selects. All I want is an array of the data so be shown in the VIEW.
-
Can I mix methods in my service layer, some that returns entities (“getById()”) and some that just returns array of data from my database query (“getAdvancedReport()”)?
-
Is it OK to put the db-queries right in the service layer? If not, where should they go? The data mapper feel wrong because its job is just to map my entites to the db, not to retrieve custom data.
Maybe just “Coding bureaucracy” but i need to do this right.
Cant find anything on the net other than simple CRUD examples of the domain model.
You seem a bit confused about the point in having data mappers and even about domain object in general.
Data mappers are responsible for the information exchange between storage (which sometimes is an SQL database) and domain object. If you have even a bit normalized DB structure, the database entities and domain objects will not map 1:1. Mappers are made for specific domain object , not for the database tables. A single domain object can even have multiple mappers (for example: one mapper which stores data in DB, and one in session).
If your
Reportobject has no domain logic, you can even use an active record. The pragmatic approach is to use them when the potential domain object has only CRUD with no domain logic. If there is some computation, stick with domain object + data mapper pair.Service layer is for application logic, not storage logic. There should be no SQL in it. Service should mostly be governing the interaction between undetermined mix of domain objects and mappers. With the exception of mailing services and similar structures.
Also, usually on-line reports are dynamic. You can order the data, filter it and otherwise manipulate. You would end up with a service, which can manipulate the
Reportobject, apply filter to it or extract data from said object. All this tinkering is “application logic”.