8

Some background:

A colleague and myself have different interpretations of MVC which means, given the same problem, we are coming up with radically different solutions. He comes from a Java background where every component of MVC may traditionally model an object and I come from a Haskell background and have little or no experience with OOP.

The problem space:

The problem we are trying to model acts a little bit like a desktop environment. We have a notion of the users session (perhaps their login, their desktop background) and the processes on their desktop (say iTunes, Finder, etc) which each have their own model properties (minimised, etc).

We agree on the following point: we think HMVC is the best representation. We agree that we have two MVC objects, Session (desktop) and Process (application) and that we don't want a Process to have a notion of Session or a backlink.

Once place we disagree on however is the core meaning of MVC and how that affects where we keep the list of processes on the users desktop.

His interpretation:

He argues a very valid point which traditionally is easy to model in code and in our rendering system. He says that the list of processes should be a list of ProcessController objects within SessionController which in turn have their models as separate objects inside them. This means that there is a significant amount of state within both SessionController and SessionModel which is relevant to what SessionView needs to render.

This seems to be very much in harmony with what we were able to read on the internet in a brief search.

My interpretation:

My interpretation requires the largest architectural change and seems harder to implement in the code, but I believe it is more conceptually correct. I would like somebody to explain why this is not the case, or present a different model (if not MVC) that aligns with this interpretation and highlight some strengths and weaknesses for both patterns so we can make the most informed decision (neither of us have a strong background in software architecture).

I see MVC as a triad with three interchangeable components: the Model, the Controller and the View. This agrees with what I am able to read on the internet, and some sources will say things along the lines of like 'views, controllers and models with the same interface should be interchangeable to different effect'. The way I imagine this to work is as follows:

  • When you swap the model, you are changing the way data is validated or stored
  • When you swap the controller, you are changing how the page behaves, but not anything which could alter the conceptual data content of the page
  • When you swap the view, you are changing the way the page is displayed

From this, I reasoned that given any Model and View, swapping only the controller should not change the data the page initially renders because the controller should change only the behaviour and not the 'content' of the page. I think this aligns with the conceptual visualisation of the controller as a 'station controller' in a rail system, a plan of the rail road as the model and the actual physical manifestation and look/feel of the tracks (in different flavours, say 'Real' or 'Virtual 3D') as the view.

Here's where we disagree:

I argue that because the data that will be displayed to the user in the SessionView is changed by the different processes on the desktop (I model the processes as relevant data), the SessionModel should contain the list of instances of ProcessModel. This means that using any random SessionController with the same SessionView should conceptually show the same data (processes on the desktop).

He argues that it makes more sense for a Model to never know about another model. This means that the SessionController would have a list of ProcessControllers within it and each Controller object has a link to its model. Given a SessionView and the same SessionModel but a different SessionController the data displayed to the user should be radically different.

Please argue for/against each interpretation and help us to reach the most informed outcome.

Thanks for your time!

  • 1
    Swapping the controller may cause the controller method to render a different view, or return a different object. So your argument probably only makes sense if the controller you are swapping out conforms to a specific interface/contract. Thus, there is no guarantee that the new controller would render the same data to the view; the controller is only obligated to render or return that which it is programmed to render or return. – Robert Harvey Dec 6 '14 at 0:23
  • So the entry point to the render should be the controller and not the view (with the controller as an argument)? – kvanberendonck Dec 6 '14 at 1:18
  • 1
    You, coming from Haskell, should relate to the following: I think that MVC is just an abstract model of relationships between parts of a program, but which parts should play the role view, model or controller depends on the problem you're confronted with. Likewise, Category Theory is just a set of rules to help formalize relationships between objects, but there's no rigid definition of which actual objects may be used with these rules. CT itself can be formalized with CT. HMVC is a good example of that idea, as you can use MVC within MVC (though it's not the same kind of recursion). – didierc Dec 6 '14 at 2:04
  • 1
    There are also other rules which dictate how things should be written: DRY, SOLID, KISS. They're not conflicting with MVC, and should certainly be applied as much (if not more). – didierc Dec 6 '14 at 2:09
6

The key in understanding MVC lies in the separation of the responsibilities, as MVC is simply SRP applied to UI code. It separates what data has to be displayed, from how to display it, from how to handle screen events. But an important (and often missed) detail of the original definition of MVC is that it was designed for a far more granular level. For instance, you'd have ButtonModel, ButtonView and ButtonController objects, "just" to present a single button on a screen. Missing this detail is what causes so many different opinions on the subject. You can check the Java Swing architecture to see what I mean.

The point of MVC is to allow the code that serves each responsibility to be changed without affecting the code for the others. For instance, you would be able to switch the rendering of (a component on) the screen without having to touch the data representation nor the event-handling logic. So, to a degree, this goes along with what you say here:

From this, I reasoned that given any Model and View, swapping only the controller should not change the data the page initially renders because the controller should change only the behaviour and not the 'content' of the page. I think this aligns with the conceptual visualisation of the controller as a 'station controller' in a rail system, a plan of the rail road as the model and the actual physical manifestation and look/feel of the tracks (in different flavours, say 'Real' or 'Virtual 3D') as the view.

However, in your context, the level of granularity is off; you have a SessionView that seems to be responsible for a whole screen. At this level, the responsibilities get too coupled to fully separate as intended by MVC, thus it may not provide the full benefits.

Your problem is in separating the three UI responsibilities (rendering, the data and the event-handling) for both sessions and processes, a total of six. Because of the level of granularity of the components (whole screen), this becomes impossible, and causes the dissonance you find yourselves into.

You want to separate the rendering and event-handling responsibilities for both Sessions and Processes, but you'd couple their data. Your colleague wants to decouple the data, but couple the event-handling.

So in the end, this is an SRP problem. My way out would be to decrease the level of granularity down to a point where you can clearly separate Sessions from Processes. If you can't do that due to economics, you guys simply have to weight both sides of the trade-off, choose the least worst, and sign it off as technical debt. This is, after all, what design decisions are all about. :)

  • Thanks for your time and well thought-out comment. We have a lot to think about here! I hope you don't mind if I leave this open for a little while before choosing an answer as not to discourage others from sharing their POV. – kvanberendonck Dec 6 '14 at 2:44
  • I was thinking about this today and came across an interesting question: what does the render look like if the Processes are in the Session model? How does a SessionView get access to the ProcessControllers to hand to the ProcessView? – kvanberendonck Dec 7 '14 at 11:37
  • 1
    Well, with MVC, either you separate Sessions from Processes completely (more granular than your example), or you create a single Model, View and Controller for the whole screen, and treat sessions and processes as one big thing (more coarse). Your problem is the current granularity of your objects, where you try to separate things, but it doesn't allow for a clean separation. Other patterns, such as MVP or MVVM, work better for "whole screens", as opposed to MVC which is meant for the small elements on the screen. – MichelHenrich Dec 7 '14 at 15:25

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.