1 MSDN, 2 contradicting MVC patterns, many people confused.
Some time ago I took part in developing a project that my former colleague started. It all seemed nice, until I noticed something weird — the model classes actually contained the logics to perform complex calculations, invoke external services AND to store the modified state somewhere.
I asked him where he got that “interesting implementation” of the MVC pattern from, and he proudly said “MSDN!”. Guess what, he was not lying.
When I say MVC, you immediately imagine the common, beloved and well known drawing of the Model-View-Controller pattern:
So the View displays the Model which is manipulated by the Controller.
The “model” component is usually a set of objects that represent the app’s state (User, Invoice, Car, etc)+ a PersistentStore layer (DAL). The logical units that perform actual calculations, requests to external APIs and so on should be in the Controller, correct?
Well, it depends. If you ask MSDN on this link, then the last statement is correct.
But if you look on MSDN right here, you will be confused. That page has the following statement:
“Model. The model manages the behavior and data of the application domain, responds to requests for information about its state (usually from the view), and responds to instructions to change state (usually from the controller).”
No, 1000 times no. The model should NOT manage the behaviour and data of the application domain. Other MSDN pages clearly state that the MODEL is uniquely responsible for storing the data and performing changes in the persistent store of the system. But “Managing the behavior”? no. The model does not do that. I have never seen a model class that makes calls to external APIs and awaits responses, and if I did — I would immediately fail it on CR.
So, what should we do? How to clarify this confusion?
As a comparison, let’s take a look at the MVVM pattern. Model-View-ViewModel.
A common mistake here is thinking that the Controller IS the ViewModel, while it actually is a separate component in the architecture.
If we looked at it like Model-View-ViewModel-Controller — it would make things a thousand times clearer and easier to understand.
Our Model — is the data objects and DAL layer.
View — the view. WebUI, game frontend, microwave display, etc.
ViewModel — The part that glues the UI to the Model. (Use different implementations to your own taste — BindableProperties, Observables, etc)
Controller — Performs the logical part of the system.
Let’s have an example to clarify:
A user clicks on the “Add item to cart” button in the view.
The ViewModel’s bindable property “Cart” is modified, thus triggering the Controller.
The controller knows that it now has to calculate the total value of the cart, including discounts and the existing coupon codes. So what does it do? It invokes it’s [float ICartCalculator.CalculateTotal(items)] method. This method actually performs the calculations, and returns the new total value of the cart.
Then, and only then should the Model be accessed by the Controller. It is modified and then updated in the PersistentStore (again, your choice: EntityFramework, MongoDB or Redis — doesn’t matter).
The new total is not displayed to the user, who is very happy that everything worked as expected.
Done, the flow is now completed. Easy and no confusion, clear separation of concerns, no 2 points of views that are “Open to interpretation” like with the explanation of MVC on MSDN.
Just keep in mind — if you read something on MSDN — it doesn’t necessary mean that it is 100% accurate. Read everything with an open mind (especially articles on Medium) and think about the information you receive. Process it, think about it, see if it seems reasonable to you, and try to think why. Maybe it is perfect, and maybe the author made a mistake. Or maybe there is a better way. Just don’t accept everything as a given.