Mvc – Sharing code logic between controllers, through the Model layer

asp.netdesign-patternsmvc

As I originally conceived my Model layer, it was only supposed to hold data and no code.
I receive DTOs from web-services, they are mapped into my Model objects. Those model objects usually end up being either composed or specialized into ViewModel objects.
In most cases, a controller calls some web-services and create a ViewModel object that it hands to the View. In reality, I sometimes have to create a class in the Model layer, next to my data objects, that hold some business logic. The reason for that is that this logic is shared between controllers. When some code is not specific at all and doesn't require much « configuration » I create short static methods, what I understand to be what one commonly calls « helpers ». I created a « Helpers » folder at the same level as my « Controllers », « Views », « Models », « ViewModels » folders. Is it right in terms of project structure ? Don't know.

Now it happens that I need to share some code, that requires some configuration, between controllers. For example, at some point, the business code has to call a web-service with various parameters related to the ongoing computation. Among thoses parameters is a session key. This session key therefore has to be configured to the business object before the treatment begins.

After the business code did his job, the controller hands the model to a view. This model, while not varying in terms of object class, could use data built by various business objects. In my case, I have a partial view showing a tree. The data of the tree can come from different web-services that require different inputs and yield different results. Only the resulting model has a constraint of object type.

In the beginning I had this…

Original structure

The controller retrieved the data from the web-service and then builded a tree structure with some treatment. This structure was handed to a ViewModel object, which was then handed to the view.

But then, as I needed to access the code building the tree structure from an other controller, I isolated this code in what I instinctivelly called a « builder ». This object was to be initialized by any controller that needed it, before calling the BuildHierarchy() method.
Now, I need to create a second tree building logic, based on other data from another web-service. But I wish to use the same view to display those data.

From a more general point of view, here is how I currently imagine the structure of such a code…
Future structure?

So I have two questions :

  • I read a bit about the Builder pattern, and I understand I shouldn't call my object a « builder » and that this pattern is not well suited to this case. Is there some pattern corresponding to what I wish to accomplish ?
  • In my project structure, where should I actually put those business objects ? Am I right to put them in the Model layer, or should it be somewhere else ?

Best Answer

I think you are missing 1 or maybe 2 layers in your design which is why you are not sure where to put business logic or 'builder' code. You should consider adding a service and possibly repository layer.

The service layer is a layer that interfaces between controllers and the model/repository. It may contain business logic or may just be a thin API layer. The repository layer is responsible for returning model objects to services or controllers (I think this is the builder concept you have mentioned).

Although, the extra layers add complexity, I prefer to separate out the responsibilities - it's usually easier to test that way and you have less problems later on when you want to replace your UI, add a web services interface etc.