Aliaksei has posted 3 posts at DZone. You can read more from them at their website. View Full User Profile

Is MVC Pattern a Dead End for Application Development?

02.20.2013
| 23609 views |
  • submit to reddit

In this article I would like to show you why using MVC pattern is not enough to be able to create agile and scalable applications. I will also suggest possible solutions to identified problems.

In the Model View Controller pattern nothing is wrong. It solves the problem it was invented for – to divide user request processing logic from presentation logic.


Before this pattern was invented, user request processing logic and presentation logic had been tightly-coupled together in one file. It made maintenance much more complicated and led to a number of bugs in the system.


MVC pattern is a good choice when application modules are more or less independent from each other.  For instance, they are called from the main menu.  Let’s imagine that to finish up the business process we need to pass step by step modules:  A. B, C, D. Entity created in module A becomes available in module B. Entity created in module B as well as entity created in module A become available in module C, etc.


In this case, the user should know the order of how to work with system modules to be able to make the necessary changes. Also, if the process of work with the system has changed (business or domain model has changed) the user can adjust to the new process with no changes in user interface.

Everything is fine until the system is used by a small number of people when it is still not a problem to train them in how to use it.  What about the system delivering to a great number of users?

In this case to simplify the work application should know how to work with it and lead the user through the system step by step opening up the further steps.

But here lies the cunning use of MVC pattern. As you can see from image below it is tempting to refer from module ‘A’  presentation(View) directly to module ‘B’ controller (Controller), from module ‘B’ to module ‘C’, from module ‘C’ to ‘D’, etc.  


(Or from controller of module ‘A’ to controller of module ‘B’. Or even worse from controller of module ‘A’ to presentation (View) of module ‘B’)

Business process will be tightly sewn in 3 views. I agree that it is a bit confusing. Since relationships are distributed across multiple files - to change business processes will be cumbersome.

And you have to hard-code business logic within if/else statements to be able to support different variations of A, B, C, D.  Unfortunately such approach is quite often used to build up applications.

How to return former loose coupling to system modules but to retain described business processes inside.


For this purpose you need to move configuration of business processes out of modules and place them separately. To ensure that users and all modules communicate via one Root or Front Controller. In this case controller will take from configuration what modules in what order to provide the user with. Modules will communicate through root controller by means of events to provide the loose coupling approach. 

Configuration of some basic flow can look like:

<?xml version="1.0"?>
<application initial="A">
    <module id="A">
        <on event="next" to="B"/>
    </module>
<module id="B" >
<on event="previous" to="A"/> <on event="next" to="C"/> </module>
<module id="C">
<on event="previous" to="B"/> <on event="next" to="D"/> </module>
<module id="D">
<on event="previous" to="C"/> <on event="finish" to="finish"/> </module>
<on event="cancel" to="cancel"/> <final id="finish" /> <final id="cancel" /> </application>

In this case is quite easy to change system behavior just by removing some steps from the configuration:

<?xml version="1.0"?>
<application initial="A">
    <module id="A">
<on event="next" to="D"/> </module>
<module id="D">
<on event="previous" to="A"/> <on event="finish" to="finish"/> </module>
<on event="cancel" to="cancel"/> <final id="finish" /> <final id="cancel" /> </application>

For configuring the module states and transitions between them is very convenient to use the state machines (Finite State Machine). After introducing inheritance and polymorphism into configuration it becomes a very powerful tool to describe business processes. For good visibility we used XML format of configurations files but it also can be some implementation of Domain Specific Language to be able to validate configuration on compile time.

As examples of such state machines in the Java world, can serve:

·  Spring Web Flow  – extension of Spring MVC and that’s why quite good to use with HTTP Request/Response model.

·  Lexaden Web Flow  – created especially for rapid development of flexible enterprise AJAX Vaadin applications.

The main difference is that Spring Web Flow  is mostly created for frameworks tightly coupled to HTTP Request/Response model and that’s why it might be cumbersome to use it with AJAX component frameworks such as Vaadin. The page will be refreshed all the time and benefits of AJAX will be ignored.

Lexaden Web Flow  instead gives you the whole power of described approach at the level of AJAX requests. Taking all the best from Vaadin component model it allows you creating flexible, scalable and very reliable enterprise applications.

P.S. the article Building An Advanced Navigation for Enterprise Applications describes in details the solution based on Lexaden Web Flow.

Published at DZone with permission of its author, Aliaksei Papou.

(Note: Opinions expressed in this article and its replies are the opinions of their respective authors and not those of DZone, Inc.)

Comments

Norman Cousineau replied on Wed, 2013/02/27 - 10:12am

These principles sound similar to what's used in the PureMVC framework, available in 15 languages. It uses events and "notifications". Notification interests are registered with the singleton (or multiton) "application facade", and this achieves very loose coupling. I can't compare it to other frameworks, but it has made my coding life pleasant.

Aliaksei Papou replied on Wed, 2013/02/27 - 12:08pm in response to: Norman Cousineau

Norman,

Using events in MVC sounds very promising, but what about a state management in the PureMVC framework? 

Can I receive events depending on the current state of the user interaction with the web application?


Thang Chung replied on Wed, 2013/02/27 - 11:38pm

Norman,

As you said, we have to move all business processing out of module, but what's happen if these business processing is just belong to those and cannot move out? I am working on a project that organize with module like this article mentioned, and find out the same problem in tightly coupling between this module to another. It is very hard to maintain and try to re-use the code at the will. But anw, thanks for your good idea on this case.

Marcel Huijkman replied on Thu, 2013/02/28 - 2:50am

 I would say that this "new" pattern is still what MVC is all about.

The "man in the middle" controller is still the first controller from MVC, but can handle communications to child controllers. There isn't just the "man in the middle" controller, there's also a accompanying view.

This is MVC people, so for sure it isn't a dead end pattern, it's clean separation. That's why it's there.

Aliaksei Papou replied on Thu, 2013/02/28 - 4:07am in response to: Marcel Huijkman

Marcel,You are right. The root controller should have one root layout view at least . But how the "man in the middle" will handle communications to child controllers?Usually root controllers in the most MVC frameworks allow a very limited ability for customization.

Marcel Huijkman replied on Thu, 2013/02/28 - 5:55am

 It could be as you suggested, that it is externally configurated, which looks flexible.

However, a system with fixed code is never flexible, and so is behavioural flow. So the "man in the middle" could be hard-wired to childs.

---==---

From a developers point of view, I would say, there is no difference in configuration over programming. It's both coding ;-)

The only advantage would be, when the configuration is not deployed within the jar/war/ear.

Otherwise, it's just a different way and even a more complex way to do the same.

I like KISS, so and that light I would say: the "man in the middle" is some kind of traffic agent who knows about it's childs and that logic is programmed, not configurated.

Naveen Ravindran replied on Thu, 2013/02/28 - 5:58am

Thanks Alexey Popov for the article. It is very informative to a budding programmer like me learning MVC to a get different view.

Aliaksei Papou replied on Thu, 2013/02/28 - 8:53am in response to: Marcel Huijkman

Marcel,

> So the "man in the middle" could be hard-wired to childs. 

No. It does not. In our case the "man in the middle" will be loosely coupled with children. 

We provide a state based event-driven dependency injection of child views within the root view. 

> From a developers point of view, I would say, there is no difference in configuration over programming. It's both coding ;-)

Our solution is not for every project. Our target market is large agile and ready to grow applications. For such applications our solution is following KISS principle. ;-)

For small projects it doesn't matter what technology to choose. ;-)

Solomon Duskis replied on Thu, 2013/02/28 - 6:08pm

Overall, this article was good food for thought.  Thanks for posting.  I do have a partially formed response, and I hope that it's constructive.

I've use quite a bag of tricks to get web MVC to do what I needed to it to do.  Those tricks worked quite well for me, and with them the projects I work on leverage MVC as a clean method of separating concerns.  In the bag of tricks, I use web flow techniques for very specific use cases (i.e. complex user input wizards).  It's a tried and true approach; it has pitfalls like any other approach and should be used appropriately

I don't recall ever came across a usage of the Tightly Coupled Controllers use in any of my projects (if I did, I block it out due to the horror); it's definitely an anti-pattern.  I don't quite see how MVC is Dead due to that anti-pattern.

In terms of events in MVC: events should be core to MVC in rich UIs, JS rich UIs included.  Events were rightfully part of the original Xerox Parc conception of MVC.

Vine Rustia replied on Fri, 2013/03/01 - 12:45am

This event -driven design flow somehow is similar to aspect oriented in goals they want to accomplish, to decouple different modules and yet being able to configure the coupling easily in a configuration file or by annotation. The only difference is event-driven modules are bounded apparently by events/state, while aspect oriented method binds modules by reflection and IoC, but they are similar in their goals. Another difference is events could/could not be fired depending if the trigger is fired which is the condition. I think this is  new insight for me in seeing how an application not just the MVC design could utilize your idea for reusability and maintainability. Im just thinking what if there come in a situation where there will be lots of events to be called? As the system gets complicated, and lots of decoupled events started to show up, one module could be connected to lots of events and therefore it could be hard to trace or debug as lots of events in possible various sequences combination could confuse a developer. But probably improving this concept would be able to cover those problems and by standardizing this design could prevent those complications. So far, keep up the good work, and if you have improved and enhanced your design, kindly provide a follow-up post for everyone's benefit especially to those who are interested to your ideas. Thanks!

Aliaksei Papou replied on Fri, 2013/03/01 - 6:17am in response to: Solomon Duskis

Solomon,

Thanks for your very constructive comment.

Our approach is not just for complex user input wizards.

In my understanding wizards are just a small step towards a language between human and a program.

We consinder wizards as a very formal conversation between them. Our approach provides informal conversation with the whole system.

In this case the system is treated as one BigWizard. And you can start the conversation from any entry point in the system.

The language of this conversation is Lexaden Web Flow. It combines asynchronus execution state with functional approach and object oriented principles.

You can watch the video how it looks like:

http://www.youtube.com/watch?v=zTjHcLG35Gs 


Aliaksei Papou replied on Fri, 2013/03/01 - 4:46am in response to: Vine Rustia

Vine Tech,Thank you very much for very deep analysis and very constructive recomendations.

Our current solution allows solving quite complicated problems for big systems already now but the problems you mentened may come up if to speak about systems at least ten times bigger then we can build now.
I'm sure step by step Lexaden Web Flow will be polished and will evolve to the framework taking into account mentioned problems as well.

Gustavo Freitas replied on Wed, 2013/03/06 - 12:09pm

 Firstly, this is an interesting approach and a great article!

Actually, I think your decision is more about modularization than MVC pattern. Did I lose the point?
Theses days, modules communication may gives an insight about how hard this can be. A few months ago I worked with a JavaEE application where we need a common way for passing information between modules. One of the feasible approaches we found was: "web services", providing a kind of internal API for modules communication.

I'll try to get in details about your proposal and see nearer how it definitely works.

Thanks!

Android Example replied on Thu, 2013/10/03 - 4:59am

very nice dude.... i have also found one good example here Use MVC Pattern To Create Very Basic Shopping Cart - Android Example

Comment viewing options

Select your preferred way to display the comments and click "Save settings" to activate your changes.